• 企业400电话
  • 网络优化推广
  • AI电话机器人
  • 呼叫中心
  • 全 部 栏 目

    网站建设 商标✡知产 微网小程序 电商运营 彩铃•短信 增值拓展业务
    ASP.NET MVC的Localization本地化多语言支持
    POST TIME:2021-10-18 02:19

    一、ASP.NET MVC的本地化支持

    ASP.NET MVC的是基于ASP.NET运行,所以由ASP.NET提供的所有功能,都可以在MVC里使用,例如缓存,会话状态和本地化。 在传统的ASP.NET Web窗体时代我们使用资源文件存储不同语言中的内容和使用由Visual Studio自动生成的ResourceManager类来检索它们。在ASP.NET MVC他们一样有效的。

    让我创建一个标准的ASP.NET MVC的一个示例应用程序。该网站是中文的,我们可以看到所有的内容都是在视图和控制器类里写死的。

    我使用的框架是mvc3的基于Razor模板的网站。

    使用Visual Studio 2010 创建 MVC3的Web应用程序,在随后出现的选择中选择Internet 应用程序,视图引擎为Razor;

    可以看出来现在网站是中文的,而且我们可以看到所有的内容在视图和控制器里都是硬编码的。

    现在我需要做的是把所有的内容从页面和控制器里分离出来,Asp.Net给我们一个名为App_GlobalResources的文件,它里面包含各种语言的全局资源文件。我们只需要在解决方案管理器里的Web项目上右击鼠标,添加->添加至Asp.Net文件夹->App_GlobalResources

    我创建了中文、英文两个语言的资源文件,中文是程序的默认语言,所以我先创建Global.resx文件,然后是Global.en.resx,中间的“en”是英语的Culture Name。如果你需要法语,那么你只需要再创建Global.fr.resx文件,Visual Studio会自动生成对应的类。

    现在让我在资源文件里添加一些内容,在主页上我们需要替换三处:标题、消息还有描述,所以我们在这两个资源文件里添加3个项。

    标题和描述都在视图页面里定义了,所以我将更改视图。

    复制代码 代码如下:

    @{
        ViewBag.Title = Resources.Global.Home_Index_Title;
    }
    h2>@ViewBag.Message/h2>
    p>
    @Resources.Global.Home_Index_Desc
    a href="http://asp.net/mvc" title="@Resources.Global.Home_Index_DescLink">http://asp.net/mvc/a>。
    /p>

    复制代码 代码如下:

    public ActionResult Index()
    {
        ViewBag.Message = Resources.Global.Home_Index_Message;
     
        return View();
    }

    二、通过URL指定语言

    我们已经把内容转移到了资源文件,但是我们的程序还不支持本地化,因为没有任何地方我们可以设置指定语言的地方。为了简单起见,我们将使用url来标明选择使用的语言(就类似微软网站),意思就是如果我的URL是http://localhost/en-US/Home/Index ,则网站会体现为英文;而http://localhost/zh-CN/Home/Index 则是简体中文。用户可以在任何停留的页面更改语言,而且 当他想共享网址的时候也会保留语言设置。

    为了达到效果,我更改了程序的路由,在最前头新增一个名为“lang”的路由规则:

    复制代码 代码如下:

    public static void RegisterRoutes(RouteCollection routes)
    {
        routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
        routes.MapRoute(
            "Localization", // 路由名称
            "{lang}/{controller}/{action}/{id}", // 带有参数的 URL
            new { controller = "Home", action = "Index", id = UrlParameter.Optional }//参数默认值
            );
        routes.MapRoute(
            "Default", // 路由名称
            "{controller}/{action}/{id}", // 带有参数的 URL
            new { controller = "Home", action = "Index", id = UrlParameter.Optional } // 参数默认值
        );
    }

    要注意,代码里并没有设置lang的默认值,而且没有删除默认的路由,这个是为了防止如 http://localhost/ and http://localhost/Home/Index之类地址时程序无法解析。

    因为我们需要URL设置语言,所以我们需要在每个action执行前执行写逻辑处理,这里ActionFilter将是个不错的解决方案。

    复制代码 代码如下:

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    using System.Web.Mvc;
    using System.Threading;
    using System.Globalization;
     
    namespace ShaunXu.MvcLocalization
    {
        public class LocalizationAttribute : ActionFilterAttribute
        {
            public override void OnActionExecuting(ActionExecutingContext filterContext)
            {
                if (filterContext.RouteData.Values["lang"] != null
                         !string.IsNullOrWhiteSpace(filterContext.RouteData.Values["lang"].ToString()))
                {
                    ///从路由数据(url)里设置语言
                    var lang = filterContext.RouteData.Values["lang"].ToString();
                    Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture(lang);
                }
                else
                {
                    ///从cookie里读取语言设置
                    var cookie = filterContext.HttpContext.Request.Cookies["ShaunXu.MvcLocalization.CurrentUICulture"];
                    var langHeader = string.Empty;
                    if (cookie != null)
                    {
                        ///根据cookie设置语言
                        langHeader = cookie.Value;
                        Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture(langHeader);
                    }
                    else
                    {
                        ///如果读取cookie失败则设置默认语言
                        langHeader = filterContext.HttpContext.Request.UserLanguages[0];
                        Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture(langHeader);
                    }
                    ///把语言值设置到路由值里
                    filterContext.RouteData.Values["lang"] = langHeader;
                }
     
                /// 把设置保存进cookie
                HttpCookie _cookie = new HttpCookie("ShaunXu.MvcLocalization.CurrentUICulture", Thread.CurrentThread.CurrentUICulture.Name);
                _cookie.Expires = DateTime.Now.AddYears(1);
                filterContext.HttpContext.Response.SetCookie(_cookie);
     
                base.OnActionExecuting(filterContext);
            }
        }
    }

    我创建了一个继承自ActionFilterAttribute的"LocalizationAttribute"并重写了OnActionExecuting方法的属性,首先检查路由里的值,如果包含了语言设置,则设置当前进程的当前区域值,它指示资源管理器(Visual Studio根据资源文件自动生成)获取相关的值。如果找不到路由里的语言值,则读取cookie值来设置,否则使用默认语言。最后把值放进路由,并保存到cookie里。

    我在home控制器里使用这个属性这样所有action都可以执行我的本地化逻辑。

    复制代码 代码如下:

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    using System.Web.Mvc;
    using ShowLocal.Models;
     
    namespace ShowLocal.Controllers
    {
        [Localization]
        public class HomeController : Controller
        {
            public ActionResult Index()
            {
                ViewBag.Message = Resources.Global.Home_Index_Message;
                return View();
            }
     
            public ActionResult About()
            {
                return View();
            }
        }
    }

    选择我们可以启动网站然后添加语言在URL上看看结果

    您可能感兴趣的文章:
    • asp.net web页面元素的多语言化(多国语化)实现分享
    • asp.net 支持多语言站点的实现方法
    • asp.net 2.0多语言网站解决方法
    • Asp.Net Core MVC项目实现多语言实例(Globalization/Localization)
    上一篇:ASP.NET Core配置教程之读取配置信息
    下一篇:ASP.NET过滤类SqlFilter,防止SQL注入 原创
  • 相关文章
  • 

    关于我们 | 付款方式 | 荣誉资质 | 业务提交 | 代理合作


    © 2016-2020 巨人网络通讯

    时间:9:00-21:00 (节假日不休)

    地址:江苏信息产业基地11号楼四层

    《增值电信业务经营许可证》 苏B2-20120278

    X

    截屏,微信识别二维码

    微信号:veteran88

    (点击微信号复制,添加好友)

     打开微信