【发布时间】:2015-08-25 20:30:16
【问题描述】:
我正在使用 Language Fallback 提供程序。这似乎对存储在 System > Dictionary 中的项目没有任何影响。
我希望它回退到 Language 项的“Fallback”属性中指定的语言。
更糟糕的情况,我想回退到英语。
我从字典中获取文本的方法可以调用它。
Globalization.Translate.TextByLanguage(key, ????);
我被困住了:
- 如何找到当前指定语言的“Fallback”属性值
- 如何将它传递给 TextByLanguage。它似乎需要一个 Language 属性,但 Language 似乎没有 任何构造函数。
历史:按照@Jammykam 的建议,我查看了 Verndale 示例,但我的运气为零。它似乎从来没有开过火。
我在我的解决方案中添加了以下类:
using Sitecore.Diagnostics;
using Sitecore.Globalization;
using Sitecore.Pipelines.GetTranslation;
using Sitecore.SharedSource.PartialLanguageFallback.Extensions;
using System;
using System.Collections.Generic;
namespace Sitecore.Web.Pipelines
{
public class DictionaryFallback : TryGetFromFallbackDomains
{
public static bool EnableFallback
{
get
{
return Sitecore.Context.Site != null &&
Sitecore.Context.Site.SiteInfo.Properties["enableFallback"] != null &&
Sitecore.Context.Site.SiteInfo.Properties["enableFallback"].Equals("true", StringComparison.InvariantCultureIgnoreCase);
}
}
/// <summary>
/// Runs the processor.
///
/// </summary>
/// <param name="args">The arguments.
/// </param>
public void Process(GetTranslationArgs args)
{
Assert.ArgumentNotNull((object)args, "args");
List<string> processedDomains = new List<string>();
if (args.HasResult || Context.Site == null || string.IsNullOrEmpty(Context.Site.DictionaryDomain))
return;
this.Args = args;
this.Database = args.Options.Database ?? args.ContentDatabase;
DictionaryDomain domain;
if (!DictionaryDomain.TryParse(Context.Site.DictionaryDomain, this.Database, out domain) || domain == null) {
Log.Info("Error Parsing Dictionary: " + domain.FullyQualifiedName, this);
return;
}
string result;
if (this.TryGetTranslation(domain, processedDomains, out result) && result != null)
{
Log.Info("Normal Translation: " + domain.FullyQualifiedName + ": " + result, this);
args.Result = result;
}
else if (EnableFallback)
{
if (this.TryTranslateTextByFallbackLanguage(args, domain, out result) && result != null)
{
Log.Info("Fallback Translation: " + domain.FullyQualifiedName + ": " + result, this);
args.Result = result;
}
}
}
protected virtual bool TryTranslateTextByFallbackLanguage(GetTranslationArgs args, DictionaryDomain domain, out string result)
{
result = null;
List<string> processedDomains = new List<string>();
// check if the the language passed in with the args has fallback assigned
// if so, then get that fallback language
// must try to get the translation based on that language
var languageFallsBack = args.Language.HasFallbackAssigned(args.ContentDatabase);
if (languageFallsBack)
{
Language fallbackLanguage = args.Language.GetFallbackLanguage(args.ContentDatabase);
// the following cannot be called from here, because it is an internal method to the Sitecore.Kernel library
//Translate.TryTranslateTextByLanguage(args.Key, domain, fallbackLanguage, out result, args.Parameters);
// therefore, we set Args.Language to the fallbacklanguage
// this.Args is the Args object in TryGetFromFallbackDomains processor
// then we call this.TryGetTranslation, which is a method in the TryGetFromFallbackDomains processor,
// which IS in the Sitecore.Kernel library and therefore can make the call to TryTranslateTextByLanguage
this.Args.Language = fallbackLanguage;
if (this.TryGetTranslation(domain, processedDomains, out result) && result != null)
{
return true;
}
else
{
// if no results if found, try to see if this fallback language falls back itself to another language
// and then if so, try the translation with that
// pass into the recursive call this.Args (instead of args), since the language has been updated in this.Args
if (result == null)
{
var isSuccess = TryTranslateTextByFallbackLanguage(this.Args, domain, out result);
return isSuccess;
}
else
return false;
}
}
else
{
return false;
}
}
}
}
我在补丁文件中添加了以下代码:
<pipelines>
<getTranslation>
<processor patch:after="*[@type='Sitecore.Pipelines.GetTranslation.TryGetFromCoreDatabase, Sitecore.Kernel']" type="Sitecore.Web.Pipelines.DictionaryFallback, Sitecore.Web" />
</getTranslation>
</pipelines>
我可以使用 showconfig.aspx 看到它:
<getTranslation>
<processor type="Sitecore.Pipelines.GetTranslation.ResolveContentDatabase, Sitecore.Kernel"/>
<processor type="Sitecore.Pipelines.GetTranslation.TryGetFromDomain, Sitecore.Kernel"/>
<processor type="Sitecore.Pipelines.GetTranslation.TryGetFromFallbackDomains, Sitecore.Kernel"/>
<processor type="Sitecore.Pipelines.GetTranslation.TryGetFromSiteDomain, Sitecore.Kernel"/>
<processor type="Sitecore.Pipelines.GetTranslation.TryGetFromContextDatabase, Sitecore.Kernel"/>
<processor type="Sitecore.Pipelines.GetTranslation.TryGetFromCoreDatabase, Sitecore.Kernel"/>
<processor type="Sitecore.Web.Pipelines.DictionaryFallback, Sitecore.Web" patch:source="SitecoreSettings.config"/>
</getTranslation>
您会在我的课堂上看到我投入了一些日志记录,但我从未看到记录的项目。具有所选语言版本的项目正确呈现。但如果他们没有版本,它会显示密钥而不是后退。
这是通过 showconfig.aspx 显示的部分(我的真实域在此处更改为 example.com):
<sites><site name="shell" virtualFolder="/sitecore/shell" physicalFolder="/sitecore/shell" rootPath="/sitecore/content" startItem="/home" language="en" database="core" domain="sitecore" loginPage="/sitecore/login" content="master" contentStartItem="/Home" enableWorkflow="true" enableAnalytics="false" analyticsDefinitions="content" xmlControlPage="/sitecore/shell/default.aspx" browserTitle="Sitecore" htmlCacheSize="10MB" registryCacheSize="15MB" viewStateCacheSize="1MB" xslCacheSize="25MB" disableBrowserCaching="true" itemwebapi.mode="StandardSecurity" itemwebapi.access="ReadWrite" itemwebapi.allowanonymousaccess="false" /><site name="login" virtualFolder="/sitecore/login" physicalFolder="/sitecore/login" enableAnalytics="false" database="core" domain="sitecore" disableXmlControls="true" /><site name="admin" virtualFolder="/sitecore/admin" physicalFolder="/sitecore/admin" enableAnalytics="false" enableWorkflow="true" domain="sitecore" loginPage="/sitecore/admin/login.aspx" /><site name="service" virtualFolder="/sitecore/service" physicalFolder="/sitecore/service" /><site name="modules_shell" virtualFolder="/sitecore modules/shell" physicalFolder="/sitecore modules/shell" rootPath="/sitecore/content" startItem="/home" language="en" database="core" domain="sitecore" content="master" enableAnalytics="false" enableWorkflow="true" /><site name="modules_website" virtualFolder="/sitecore modules/web" physicalFolder="/sitecore modules/web" rootPath="/sitecore/content" startItem="/home" language="en" database="web" domain="extranet" allowDebug="true" cacheHtml="true" /><!-- ITEM WEB API SETTINGS FOR A SITE
Supported attributes (first is default):
itemwebapi.mode: [Off|StandardSecurity|AdvancedSecurity]
If set to Off, Item Web API is turned off.
If set to StandardSecurity, Item Web API is turned on. Default Sitecore security model is used.
If set to AdvancedSecurity, Item Web API is turned on. Default Sitecore security model is extended with a requirement to explicitely set the 'remote:fieldread' access right for content fields.
itemwebapi.access: [ReadOnly|ReadWrite]
If set to ReadOnly, then only READ operation is allowed.
If set to ReadWrite, then CREATE, READ, UPDATE, and DELETE operations are allowed.
itemwebapi.allowanonymousaccess: [false|true].
Defines if access is allowed for non-authenticated user.
--><!--<site name="mysite" patch:before="site[@name='website']"
virtualFolder="/"
physicalFolder="/"
rootPath="/sitecore/content"
startItem="/home"
database="web"
domain="extranet"
allowDebug="true"
cacheHtml="true"
htmlCacheSize="50MB"
enablePreview="true"
enableWebEdit="true"
enableDebugger="true"
disableClientData="false"/>--><site name="english" virtualFolder="/" physicalFolder="/" rootPath="/sitecore/content" startItem="/home" hostName="stage.example.com|127.0.0.1|localhost" language="en" database="web" domain="extranet" allowDebug="true" cacheHtml="true" htmlCacheSize="1GB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" enableFallback="true" patch:source="SiteDefinition.config" /><site name="chinese" virtualFolder="/" physicalFolder="/" rootPath="/sitecore/content" startItem="/home" hostName="chinesestage.example.com" language="zh-CN" database="web" domain="extranet" allowDebug="true" cacheHtml="true" htmlCacheSize="500MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" enableFallback="true" patch:source="SiteDefinition.config" /><site name="german" virtualFolder="/" physicalFolder="/" rootPath="/sitecore/content" startItem="/home" hostName="germanstage.example.com" language="de-DE" database="web" domain="extranet" allowDebug="true" cacheHtml="true" htmlCacheSize="500MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" enableFallback="true" patch:source="SiteDefinition.config" /><site name="spanish" virtualFolder="/" physicalFolder="/" rootPath="/sitecore/content" startItem="/home" hostName="spanishstage.example.com" language="es-ES" database="web" domain="extranet" allowDebug="true" cacheHtml="true" htmlCacheSize="500MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" enableFallback="true" patch:source="SiteDefinition.config" /><site name="french" virtualFolder="/" physicalFolder="/" rootPath="/sitecore/content" startItem="/home" hostName="frenchstage.example.com" language="fr-FR" database="web" domain="extranet" allowDebug="true" cacheHtml="true" htmlCacheSize="500MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" enableFallback="true" patch:source="SiteDefinition.config" /><site name="italian" virtualFolder="/" physicalFolder="/" rootPath="/sitecore/content" startItem="/home" hostName="italianstage.example.com" language="it-IT" database="web" domain="extranet" allowDebug="true" cacheHtml="true" htmlCacheSize="500MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" enableFallback="true" patch:source="SiteDefinition.config" /><site name="japanese" virtualFolder="/" physicalFolder="/" rootPath="/sitecore/content" startItem="/home" hostName="japanesestage.example.com" language="ja-JP" database="web" domain="extranet" allowDebug="true" cacheHtml="true" htmlCacheSize="500MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" enableFallback="true" patch:source="SiteDefinition.config" /><site name="portuguese" virtualFolder="/" physicalFolder="/" rootPath="/sitecore/content" startItem="/home" hostName="portuguesestage.example.com" language="pt-BR" database="web" domain="extranet" allowDebug="true" cacheHtml="true" htmlCacheSize="500MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" enableFallback="true" patch:source="SiteDefinition.config" /><site name="russian" virtualFolder="/" physicalFolder="/" rootPath="/sitecore/content" startItem="/home" hostName="russianstage.example.com" language="ru-RU" database="web" domain="extranet" allowDebug="true" cacheHtml="true" htmlCacheSize="500MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" enableFallback="true" patch:source="SiteDefinition.config" /><site name="website" virtualFolder="/" physicalFolder="/" rootPath="/sitecore/content" startItem="/home" database="web" domain="extranet" allowDebug="true" cacheHtml="true" registryCacheSize="0" viewStateCacheSize="0" xslCacheSize="25MB" filteredItemsCacheSize="10MB" enablePreview="true" enableWebEdit="true" enableDebugger="true" disableClientData="false" cacheRenderingParameters="true" renderingParametersCacheSize="10MB" itemwebapi.mode="Off" itemwebapi.access="ReadOnly" itemwebapi.allowanonymousaccess="false" htmlCacheSize="1GB" /><site name="scheduler" enableAnalytics="false" domain="sitecore" /><site name="system" enableAnalytics="false" domain="sitecore" /><site name="publisher" domain="sitecore" enableAnalytics="false" enableWorkflow="true" /></sites>
关闭更新:我使用了下面接受的答案并对其进行了修改以适合我:https://gist.github.com/eat-sleep-code/0ea3f1bd2be19bbf9fc6
【问题讨论】:
-
您是否在配置中的
节点上设置了“enableFallback=true”? -
@jammykam 是的。我添加了上面 showconfig.aspx 的输出部分。
-
这一切对我来说都是正确的。尝试将您的处理器向上/首先移动并检查它是否运行正确。
-
我添加了更多的日志记录行。看来 Context.Site.DictionaryDomain 是一个空字符串?这会导致进程退出。我该如何解决?
-
@jammykam 您发送的 Gist 有一个未定义的变量,称为“数据库”,我尝试使用 this.Database 代替它,但它对此并不满意。我试过什么都不用,但还是不开心。
标签: sitecore sitecore-mvc sitecore8