Why Translation Command in Content Editor Does Not Work in Sitecore Experience Commerce 9.0 Update 1


This article explains what causes the translation in Content Editor to be not working correctly in Sitecore Experience Commerce (SXC) 9.0 Update-1 installed on Sitecore XP 9 Update 1 (rev. 171219).

The scenario is when you run two instances of Sitecore XP 9.0.1, one with SXC 9 installed and another one without SXC 9 (I will call it “default” SXP 9 as this refers to the fresh instance without SXC 9 installed), clicking on the Translation Command will give the following results.

This is how it looks in default SXP 9.



Whereas, this is how it looks in SXC 9 (in the ribbon, VERSIONS > Translate command button is clicked but the translation is not shown).


The reason can be explained as follows:

Let’s first look at the difference of showconfig (<yourSitecore>/sitecore/admin/showconfig.aspx) between those two instances. There are 2 additional processors under <renderContentEditor> as highlighted in blue rectangle below.

 

The part where the translation is handled differently is when the method RenderInput(Editor.Field) from [Sitecore.Shell.Applications.ContentEditor.Pipelines.RenderContentEditor.RenderSkinedContentEditor.Renderer] is executed (please use ILSpy or any reverse engineering tool if you want to check the content of the assembly (Sitecore.Client.dll in this case)).

 

The EditorFormatter acts as TranslatorFormatter in default SXP 9 and it uses CommerceEditorFormatter in SXC 9 (the CommerceEditorFormatter is set as the EditorFormatter by the first processor in <renderContentEditor> pipeline, SetCommerceEditorFormatter).

Let’s look at the call stack between those two classes inherited from EditorFormatter to understand how they do the translation (you can choose to use .NET reflector for debugging or any other debugging tools, such as DotPeek from JetBrain).


This is how TranslationFormatter does the translation.



As we can see the “main” and the “translated” are the content item of current selected language (German in my case) and the one I wish to translate to (English), respectively.

This is how CommerceEditorFormatter does the translation.


The translation is only done for the main language, but there is no logic from CommerceEditorFormatter that does the second translation for the language I wish to translate to.

The above behavior is caused by the line
this.args.EditorFormatter.RenderField(this.args.Parent, field, fieldType, readOnly);
inside the method private void RenderInput(Editor.Field field) from RenderSkinedContentEditor.Renderer
which is handled differently by TranslatorFormatter and CommerceEditorFormatter.

As shown in the call stack of TranslatorFormatter, it shows the content item’s field(s) in current selected language when the line 131 in the method RenderField is reached, and it shows the content item’s field(s) of the language to be translated when the line 163 is reached (depending on the debugger used, you may get different line number).


It is clear if we look at the call stack from CommerceEditorFormatter that the root cause of the issue is in the missing logic in the method RenderField to work on showing the second content item’s field(s) to be translated. The method RenderField in CommerceEditorFormatter just calls back the base class’ method but it doesn’t actually does the translation for the language to be translated.


Apart from the missing logic in CommerceEditorFormatter, the processor SetCommerceEditorFormatter has an issue too. It sets one type of EditorFormatter only (as shown in the picture below).




This means the result will always be translating (if we fix the logic in CommerceEditorFormatter) or always not translating regardless whether the “Translate” button is clicked or not. 

The default implementation (without involving CommerceEditorFormatter) is the following: TranslatorFormatter is set as the EditorFormatter when we click on “Translate” button whereas EditorFormatter is set when we un-click the “Translate” button. This process is done before the pipeline <renderContentEditor> is executed. We should make the same logic in the processor SetCommerceEditorFormatter so it will return not only CommerceEditorFormatter everytime but also EditorFormatter when the “Translate” button is un-clicked.

Basically, there are two things that we need to fix. First is the logic of CommerceEditorFormatter to have the ability to translate and second is the way the EditorFormatter is selected.
Here is how I fix it:


1.       Create a new class that has the same content with CommerceEditorFormatter, but this inherits from TranslatorFormatter. I was suggested by a Sitecore Commerce expert from Support team as I told him that the logic works for TranslatorFormatter, he also told me that CommerceEditorFormatter’s purpose is just to make the fields in an item based on Commerce template READONLY (therefore it has the same content as CommerceEditorFormatter).
2.       Create a new processor class that acts like a SetCommerceEditorFormatter that will check when the “Translate” button is clicked or not. This is the source code of this processor:

I found there are two ways to detect when a “Translate” button is clicked, other than the one I used above, I could also use:
if(args.EditorFormatter.GetType().FullName == "Sitecore.Shell.Applications.ContentEditor.TranslatorFormatter")
because this value is assigned in Sitecore.Shell.Applications.ContentManager.ContentEditorForm.RenderEditor(Item item, Item root, System.Web.UI.Control editorsContainer, bool showEditor) even before the pipeline <renderContentEditor> is executed.

3.       The config patch to replace current SetCommerceEditorFormatter processor (You can put this for example in \App_Config\Include\zzz). It will look like:

If you want the official fix, the bug number for the above problem is 40718.

Comments

Post a Comment

Popular posts from this blog

Added Contact Is Not Shown in List Manager in a Scaled Sitecore XP 9

Windows could not start the Sitecore Xconnect Search Indexer - {xConnectInstance}-IndexWorker service on Local Computer. Error 1064: An exception occurred in the service when handling the control request.

EXM Throws NonCriticalException "Failed to download string content" with Nested Exception of "403 Forbidden" in Azure Web App