ここで説明されているものと同様のマルチテナント ビュー エンジンを実装しました。
次のように、ビューの検索場所をオーバーライドできます。
MasterLocationFormats = new[]
{
"~/Views/%1/{1}/{0}.cshtml",
"~/Views/%1/Shared/{0}.cshtml",
"~/Views/Default/{1}/{0}.cshtml",
"~/Views/Default/Shared/{0}.cshtml",
};
は%1
、アクティブなテナントの正しいフォルダーに置き換えられます。これは、1つの問題を除いてうまく機能しています。ビューでレイアウト パスを次のように定義すると、次のようになります。
Layout = "~/Views/Default/Shared/_MyLyout.cshtml";
レイアウト ページの正確な場所をハード コーディングする必要があるため、マルチテナンシーを使用するという目的が無効になります。私はこのようなことができるようにしたい:
Layout = "~/Views/%1/Shared/_MyLyout.cshtml";
テナントが 1 つのレイアウト ページを持つことを許可したい場合、これをどのようにサポートしますか?
オーバーライドしたビュー エンジン メソッドをいじってみました。
- CreatePartialView
- CreateView
- ファイルが存在しています
しかし、レイアウト ページを動的に指定できるようになるとは思えません。
アップデート:
これが私がこれまで取り組んできたことです。この質問への回答https://stackoverflow.com/a/9288455/292578を少し変更して HTML ヘルパーを作成しました。
public static string GetLayoutPageForTenant( this HtmlHelper html, string LayoutPageName )
{
var layoutLocationFormats = new[]
{
"~/Views/{2}/{1}/{0}.cshtml",
"~/Views/{2}/Shared/{0}.cshtml",
"~/Views/Default/{1}/{0}.cshtml",
"~/Views/Default/Shared/{0}.cshtml",
};
var controller = html.ViewContext.Controller as MultiTenantController;
if( controller != null )
{
var tenantName = controller.GetTenantSchema();
var controllerName = html.ViewContext.RouteData.Values["Controller"].ToString();
foreach( var item in layoutLocationFormats )
{
var resolveLayoutUrl = string.Format( item, LayoutPageName, controllerName, tenantName );
var fullLayoutPath = HostingEnvironment.IsHosted ? HostingEnvironment.MapPath( resolveLayoutUrl ) : System.IO.Path.GetFullPath( resolveLayoutUrl );
if( File.Exists( fullLayoutPath ) ) return resolveLayoutUrl;
}
}
throw new Exception( "Page not found." );
}
これは、サラバナンが提案したものと似ています。次に、次のコードを使用してビューにレイアウトを設定できます。
Layout = Html.GetLayoutPageForTenant( "_Home" );
残念ながら、これはカスタム ビュー エンジンが行っている作業と重複しており、間違った方法のように思われます。