1

我安装了启用多租户模块并设置了 2 个租户的 Orchard CMS。两个租户都使用相同的主题。

我想要的是能够创建视图替代以针对每个租户,例如:

~/Themes/MyTheme/Views/Content.Tenant1.cshtml将针对租户 1 和 ~/Themes/MyTheme/Views/Content.Tenant2.cshtml租户 2。

我意识到我可以使用 2 个不同(但非常相似)的主题来做到这一点,但这感觉就像是不必要的重复。

4

2 回答 2

1

我试图在上面实现你的代码,但它只适用于形状。

我想查看 Index-tennant-[TenantName].cshtml 以覆盖 Index.cshtml

为此,我必须覆盖 RazorViewEngineProvider,然后添加额外的路径供 ViewEngine 查找。我使用了 [OrchardSuppressDependency...],因为我不喜欢更改实际的 Orchard CMS 代码,因为这会使以后的任何升级变得更加痛苦。

我希望这可以帮助任何遇到果园多租户问题的人。

[UsedImplicitly]
[OrchardSuppressDependency("Orchard.Mvc.ViewEngines.Razor.RazorViewEngineProvider")]
public class RazorViewEngineProvider : Orchard.Mvc.ViewEngines.Razor.RazorViewEngineProvider, IViewEngineProvider, IShapeTemplateViewEngine
{
    private readonly string _tenant;
    public RazorViewEngineProvider(ShellSettings shellSettings)
    {
        _tenant = shellSettings.Name;
    }

    public new IViewEngine CreateThemeViewEngine(CreateThemeViewEngineParams parameters)
    {
        var viewEngine = base.CreateThemeViewEngine(parameters);
        if (!string.IsNullOrWhiteSpace(_tenant))
        {
            var razorView = viewEngine as RazorViewEngine;
            if (razorView != null)
            {
                razorView.PartialViewLocationFormats = addTenant(razorView.PartialViewLocationFormats);
                razorView.AreaPartialViewLocationFormats = addTenant(razorView.AreaPartialViewLocationFormats);
            }
        }

        return viewEngine;
    }

    public new IViewEngine CreateModulesViewEngine(CreateModulesViewEngineParams parameters)
    {
        var viewEngine = base.CreateModulesViewEngine(parameters);
        if (!string.IsNullOrWhiteSpace(_tenant))
        {
            var razorView = viewEngine as RazorViewEngine;
            if (razorView != null)
            {
                razorView.ViewLocationFormats = addTenant(razorView.ViewLocationFormats);
                razorView.PartialViewLocationFormats = addTenant(razorView.PartialViewLocationFormats);
                razorView.AreaViewLocationFormats = addTenant(razorView.AreaViewLocationFormats);
                razorView.AreaPartialViewLocationFormats = addTenant(razorView.AreaPartialViewLocationFormats);
            }
        }

        return viewEngine;

    }

    private string[] addTenant(string[] views)
    {
        var tenantedView = new List<string>();
        foreach (var view in views)
        {
            if (view.EndsWith(".cshtml",StringComparison.OrdinalIgnoreCase))
                tenantedView.Add(string.Format ("{0}-tenant-{1}.cshtml", view.Substring(0,view.Length - 7) ,_tenant));
            tenantedView.Add(view);
        }
        return tenantedView.ToArray();
    }
}
于 2014-10-08T11:11:55.737 回答
1

答案当然是继承ShapeDisplayEvents并绑定到context.ShapeMetadata.OnDisplaying事件,因此:

public class MultiTenancyAlternatesFactory : ShapeDisplayEvents
{
    private readonly ShellSettings _shellSettings;

    public MultiTenancyAlternatesFactory(ShellSettings shellSettings)
    {
        _shellSettings = shellSettings;
    }

    public override void Displaying(ShapeDisplayingContext context)
    {
        context.ShapeMetadata.OnDisplaying(displayingContext =>
        {
            var tenant = _shellSettings.Name;

            // look for ContentItem property
            ContentItem contentItem = displayingContext.Shape.ContentItem;

            // if not, check for ContentPart 
            if (contentItem == null)
            {
                ContentPart contentPart = displayingContext.Shape.ContentPart;
                if (contentPart != null)
                {
                    contentItem = contentPart.ContentItem;
                }
            }

            var shapeName = displayingContext.ShapeMetadata.Type;

            if (contentItem != null)
            {
                var contentTypeName = contentItem.ContentType;

                displayingContext.ShapeMetadata.Alternates.Add(shapeName + "__" + contentTypeName + "__tenant__" + tenant);
            }

            displayingContext.ShapeMetadata.Alternates.Add(shapeName + "__tenant__" + tenant);

        });
    }
}
于 2013-09-24T13:42:40.773 回答