シンプルな多言語ウェブサイトを作ろうとしています。言語に基づいてファイルを取得するために FindView をオーバーライドするのは簡単です。私の問題はルーティング部分にあります。
私がやりたいことは次のとおりです:(2つの言語のWebサイトを持っています-pt-brとen-us、省略してonlu ptとen-デフォルトはPTになります)
ユーザー タイプ www.mysite.com -> ユーザー ヘッダー リクエストで言語を検索し、ユーザーがそれらのいずれも持っていない場合、デフォルトの PT にリダイレクトされるため、最終結果は www.mysite.com になります。ポルトガル語で。彼が en を持っている場合、彼は www.mysite.com/en/ にリダイレクトされ、結果は英語で表示されます。
ユーザーが www.mysite.com/pt/ と入力した場合 -> 彼がデフォルトを望んでいることを確認し、ポルトガル語で www.mysite.com にリダイレクトします。
言語に基づいて正しいビューを取得するために、カスタム エンジンを作成しました。しかし、ルーティングの問題のため、100% は機能していません。
私の場合、ルーティングしようとしています
routes.MapRoute(
"Localization", // Route name
"{lang}/{controller}/{action}", // URL with parameters
new { lang = "pt", controller = "Home", action = "Index" } //defaults
);
しかし、これにより、誰かが /pt/ と入力しても、サイトのルートにリダイレクトされません。
ルートに関するもう 1 つの問題は、コントローラー名を入力したくないということです。アクションが必要なだけです。私の Web サイトには、アクションがほとんどない Home コントローラーが 1 つしかありません。
もう 1 つの問題は、英語の CONTACT とポルトガル語の CONTATO のように、別のアクション名が必要なことです。それらは www.mysite.com/Contato または www.mysite.com/en/Contact のようにアドレス バーに表示されるはずです。
Mu Engine このソリューションに基づいて作成しましたhttp://www.counity.at/blog/2012/asp-net-mvc3-localization-using-culture-dependent-views/ by Guido Breitenhuber
これは、いくつかの調整を加えたコードです (まだ 100% は機能していません)。
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using System.Globalization;
namespace Ala.MultiLanguage
{
public class LocalizedViewLocation : RazorViewEngine
{
private static readonly string[] _emptyLocations = new string[0];
public string[] LocalizedViewLocationFormats { get; set; }
public string[] LocalizedMasterLocationFormats { get; set; }
protected string[] LocalizedPartialViewLocationFormats { get; set; }
public LocalizedViewLocation()
{
// Define the localized view locations
// 0: Language
// 1: View name
// 2: Controller name
LocalizedViewLocationFormats = new[] {
"~/Views/{0}/{2}/{1}.cshtml",
"~/Views/Shared/{0}/{1}.cshtml"};
MasterLocationFormats = new[] {
"~/Views/{0}/{2}/{1}.cshtml",
"~/Views/Shared/{0}/{1}.cshtml"};
LocalizedPartialViewLocationFormats = new[] {
"~/Views/{0}/{2}/{1}.cshtml",
"~/Views/Shared/{0}/{1}.cshtml"};
}
public override ViewEngineResult FindPartialView(ControllerContext controllerContext, string partialViewName, bool useCache)
{
if (controllerContext == null)
throw new ArgumentNullException("controllerContext");
if (String.IsNullOrEmpty(partialViewName))
throw new ArgumentException("Parameter partialViewName is null or empty.", "partialViewName");
string[] searched;
var controllerName = controllerContext.RouteData.GetRequiredString("controller");
var partialPath = GetPath(controllerContext, LocalizedPartialViewLocationFormats, partialViewName, controllerName, out searched);
if (String.IsNullOrEmpty(partialPath))
{
var baseRes = base.FindPartialView(controllerContext, partialViewName, useCache);
if (baseRes.View != null)
return baseRes;
return new ViewEngineResult(searched.Union(baseRes.SearchedLocations));
}
return new ViewEngineResult(CreatePartialView(controllerContext, partialPath), this);
}
public override ViewEngineResult FindView(ControllerContext controllerContext, string viewName, string masterName, bool useCache)
{
if (controllerContext == null)
throw new ArgumentNullException("controllerContext");
if (String.IsNullOrEmpty(viewName))
throw new ArgumentException("Parameter viewName is null or empty.", "viewName");
string[] viewLocationsSearched;
string[] masterLocationsSearched;
var controllerName = controllerContext.RouteData.GetRequiredString("controller");
var viewPath = GetPath(controllerContext, LocalizedViewLocationFormats, viewName, controllerName, out viewLocationsSearched);
var masterPath = GetPath(controllerContext, LocalizedMasterLocationFormats, masterName, controllerName, out masterLocationsSearched);
if (String.IsNullOrEmpty(viewPath) || (String.IsNullOrEmpty(masterPath) && !String.IsNullOrEmpty(masterName)))
{
var baseRes = base.FindView(controllerContext, viewName, masterName, useCache);
if (baseRes.View != null)
return baseRes;
return new ViewEngineResult(viewLocationsSearched.Union(masterLocationsSearched).Union(baseRes.SearchedLocations));
}
return new ViewEngineResult(CreateView(controllerContext, viewPath, masterPath), this);
}
private string GetPath(ControllerContext controllerContext, string[] locations, string name, string controllerName, out string[] searchedLocations)
{
searchedLocations = _emptyLocations;
if (String.IsNullOrEmpty(name))
return String.Empty;
if (IsSpecificPath(name))
return String.Empty;
return GetPathFromGeneralName(controllerContext, locations, name, controllerName, ref searchedLocations);
}
private static bool IsSpecificPath(string name)
{
char c = name[0];
return (c == '~' || c == '/');
}
private string GetPathFromGeneralName(ControllerContext controllerContext, string[] locations, string name, string controllerName, ref string[] searchedLocations)
{
var result = String.Empty;
searchedLocations = new string[locations.Length];
for (int i = 0; i < locations.Length; i++)
{
var location = locations[i];
var virtualPath = string.Format(CultureInfo.InvariantCulture, location, CultureInfo.CurrentUICulture.TwoLetterISOLanguageName, name, controllerName);
if (FileExists(controllerContext, virtualPath))
{
searchedLocations = _emptyLocations;
result = virtualPath;
break;
}
searchedLocations[i] = virtualPath;
}
return result;
}
}
}