[原]ASP.NET MVC 3 Razor 多國語言參考解決方案 補充四

來源:互聯網
上載者:User

前四回(1,2,3,4)介紹了在ASP.NET MVC 3使用Razor ViewEngine時實現多國語言的解決方案,本以為就夠用了,沒料到今天居然在使用時又遇到新問題了。

先說需求,最近做了一套全新的頁面樣式,基本思路是在iframe中顯示內容,那麼毫無疑問,這些內容頁就是MVC的視圖了,但是首頁以何種形式存在呢?.html?.cshtml?.aspx?如果是.html的話,最主要的問題就是實現多圖語言,伺服器端不處理,難道使用js不成?而且不知道未來還會不會有必須伺服器端參與處理的事情呢;.aspx我也不願意,說實話,我不喜歡aspx那繁瑣的生命週期,更不喜歡.aspx那種自以為是,老是替你作決定;於是決定使用.cshtml。

在之前建的Website項目中,我發現能添加.cshtml的檔案,那在MVC的項目中,想必也能使用單獨的.cshtml來作頁面了,於是建立一個.cshtml頁面,把之前html頁面複製進去,運行,發現果然如願開啟了頁面,接下來把html中的預留位置換成資源檔,如:

<a href="#">歡迎: </a>

換成

@Html.Lang("Welcome")

但是發現Html下面居然沒有Lang擴充方法,在我的記憶中,view中輸入@Html,自動完成列表中就會出現Lang方法了,為啥不行呢,擴充方法出不來的第一原因就是沒有引入命名空間,於是在檔案最上面加入

@using System.Web.Mvc

但是還是不行,想想也不行,@Html都有了,沒有理由不出現擴充方法啊, 要麼換一種方法調用,直接調用靜態方法:

@LocalizationHelper.Lang(Html, "Welcome")

這下總行了吧,結果輸入完成就發現問題不對勁了,這行代碼下居然告訴我參數不匹配,就這麼兩個參數,一個Html屬性,一個string,居然還不對,看了半天沒有看出端倪,乾脆我讓VS自動產生匹配的方法,到底是啥樣的方法簽名,結果這一產生終於發現問題所在了:

        public static object Lang(WebPages.Html.HtmlHelper htmlHelper, string p)        {            throw new NotImplementedException();        }

這個HtmlHelper的命名空間是WebPages.Html,而我之前定義的方法中參數HmtlHelper的命名空間是System.Web.Mvc!怪不得呢,原來不是一個東西啊,看起來使用RazorEngine時,視圖和頁面不是同一種類型

本打算那就使用這個HtmlHelper類型當參數吧,又發現這個類型中只有一些輔助方法,沒有Request、Response、Server之類的對象執行個體,基於我在Lang方法內部是需要請求詳細資料的,於是我打算使用將頁面本身(WebPageBase)作為參數,於是修改為下面的樣子:

public static string Lang(this WebPageBase page, string key){}

接下來就是重構,最終LocalizationHelper變成了下面的樣子:

using System;using System.Collections.Generic;using System.Linq;using System.Text;using System.IO;using CleverSoft.WebUtil;using System.Runtime.Caching;using System.Resources;using System.Collections;using System.Web.WebPages;namespace System.Web.Mvc{    public static class LocalizationHelper    {        public static string Lang(this HtmlHelper htmlhelper, string key)        {            return Lang(htmlhelper.ViewDataContainer as WebViewPage, key);        }        private static IEnumerable<DictionaryEntry> GetResx(string resxKey)        {            ObjectCache cache = MemoryCache.Default;            IEnumerable<DictionaryEntry> resxs = null;            if (cache.Contains(resxKey))            {                resxs = cache.GetCacheItem(resxKey).Value as IEnumerable<DictionaryEntry>;            }            else            {                if (File.Exists(resxKey))                {                    resxs = new ResXResourceReader(resxKey).Cast<DictionaryEntry>();                    cache.Add(resxKey, resxs, new CacheItemPolicy() { Priority = CacheItemPriority.NotRemovable });                }            }            return resxs;        }        public static string Lang(this WebPageBase page, string key)        {            var pagePath = page.VirtualPath;            var pageName = pagePath.Substring(pagePath.LastIndexOf('/'), pagePath.Length - pagePath.LastIndexOf('/')).TrimStart('/');            var filePath = page.Server.MapPath(pagePath.Substring(0, pagePath.LastIndexOf('/') + 1)) + "App_LocalResources";            var langs = page.Request.UserLanguages != null ?                page.Request.UserLanguages.Union<string>(new string[] { "" }).ToArray<string>() : new string[] { "" };            IEnumerable<DictionaryEntry> resxs = null;            foreach (var lang in langs)            {                var resxKey =                    string.IsNullOrWhiteSpace(lang) ? string.Format(@"{0}\{1}.resx", filePath, pageName) : string.Format(@"{0}\{1}.{2}.resx", filePath, pageName, lang);                resxs = GetResx(resxKey);                if (resxs != null) { break; }            }            return (string)resxs.FirstOrDefault<DictionaryEntry>(x => x.Key.ToString() == key).Value;        }    }}

最終在Razor頁面使用

@this.Lang("Welcome")

終於出現結果了

最終經過測試,在視圖中使用@Html.Lang()也正常工作

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.