Language selector and URL Rewriting

Posted by Community Admin on 04-Aug-2018 10:00

Language selector and URL Rewriting

All Replies

Posted by Community Admin on 28-Jul-2011 00:00

Hi all, I am running into a problem using the language selector when on pages that have URL rewriting implemented.  For example the browser URL says:

/en/destinations/country/gb/location/lon

which is being rewritten to /en/pages/location?country=gb&city=london

This is all fine but when I use the language selector to change the language to french the URL becomes

/fr/pages/location - which is the correct page but is not the correct URL and it has lost the querystring.  

What I need is the language selector control to post back to the proper URL

/fr/destinations/country/gb/location/lon

Before I start building my own custom language selector has anyone seen this problem before and worked around it.  For info I am running SF4.1 on IIS 6 using the URLRewritingNET code.

Thanks

Posted by Community Admin on 04-Aug-2011 00:00

Hi David,

Could you provide more details on your page hierarchy? Currently url parameters are ignored from the language selector.

Regards,
Pavel
the Telerik team

Do you want to have your say in the Sitefinity development roadmap? Do you want to know when a feature you requested is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items

Posted by Community Admin on 09-Aug-2011 00:00

My page hierarchy is quite simple.  I have a group page called 'pages' and then a page called 'location' - as indicated by the example I have given below.

I guess that I do not need it to support URL parameters, but to be able to post back to the original URL before it was rewritten.

Thanks

Posted by Community Admin on 10-Aug-2011 00:00

Hi David,

We have reproduced the problem and logged it in PITS. You can follow the status of the bug here.

However please note that the bug is that the Language Selector control disregards query string parameters. The thing with UrlRewriting is that the language selector cannot know if some other module is rewriting the request.

Kind regards,
Radoslav Georgiev
the Telerik team

Do you want to have your say in the Sitefinity development roadmap? Do you want to know when a feature you requested is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items

Posted by Community Admin on 10-Aug-2011 00:00

Thank you for your reply regarding the querystring.  Regarding the URL rewriting I believe a workaround is possible, you say that the language selector cannot know if a module is rewriting the request. I do not think this is the case, the built in URL rewriting in IIS 7 sends the original URL as the server variable "HTTP_X_ORIGINAL_URL" and URLRewritingNET adds the original URL to the HttpContext.Items collection with the key
"UrlRewritingNet.UrlRewriter.VirtualUrl"

It would require several configuration options to be shown to the administrator when adding the language selector control but in theory it could work.  Perhaps this could be looked into for a future version of SF (just for IIS 7) even though it may not be a widely used feature.

In the mean time can you point me to the location in the SF code that generates the URLs used in the language selector so that I can override and try to get it working with URLRewritingNET.  If I succeed I will post my code here for others to use.

Posted by Community Admin on 10-Aug-2011 00:00

Hello David,

You need to inherit the LanguageSelectorControl, overriding the followig method:

protected virtual void BindLanguageContainers(IEnumerable<CultureInfo> languages)
       
            if (this.SelectorType == LanguageSelectorType.DropDown)
           
                var dropDown = this.LanguagesDropDown;
                if (this.IsDesignMode() == false)
               
                    dropDown.Attributes["onChange"] = "document.location.href = this.value;";
               
                //dropDown.Choices.Clear();
                foreach (var lang in languages)
               
                    var langName = GetDisplayedLanguageName(lang);
                    var url = GetUrlForLanguage(lang);
                    url = RouteHelper.ResolveUrl(url, UrlResolveOptions.Absolute);

                    ListItem item = new ListItem(langName, url);
                    item.Selected = lang.Equals(CultureInfo.CurrentUICulture);
                    item.Attributes.Add("lang", lang.TwoLetterISOLanguageName);
                    dropDown.Items.Add(item);
               
           
            else
           
                this.LanguagesRepeater.ItemCreated += new RepeaterItemEventHandler(LanguagesRepeater_ItemCreated);
                this.LanguagesRepeater.DataSource = languages;
                this.LanguagesRepeater.DataBind();
           
       

You need to implement the event handler marked in yellow as follows:

void LanguagesRepeater_ItemCreated(object sender, RepeaterItemEventArgs e)
       
            if (e.Item.ItemType == ListItemType.Item || e.Item.ItemType == ListItemType.AlternatingItem)
           
                CultureInfo ci = (CultureInfo)e.Item.DataItem;

                //Get the name of the current language
                string languageName = GetDisplayedLanguageName(ci);

                //Get the URL of the language version for the current language
                var url = this.GetUrlForLanguage(ci);
                //add your custom code here

                if (this.SelectorType == LanguageSelectorType.DropDown)
               
                    HtmlGenericControl langOption = (HtmlGenericControl)e.Item.FindControl("langOption");
                    langOption.Attributes.Add("lang", ci.Name);
                    langOption.Attributes.Add("class", "sflangOption_" + ci.Name);

                    langOption.InnerHtml = languageName;
               
                else
               
                    //Add language-specific class to wrapper
                    HtmlGenericControl langHolder = (HtmlGenericControl)e.Item.FindControl("langHolder");

                    var classAttribute = langHolder.Attributes["class"];

                    var langSpecificClass = "sflang_" + ci.Name;
                    classAttribute = string.IsNullOrEmpty(classAttribute) ? langSpecificClass : classAttribute + " " + langSpecificClass;

                    //Add selected class, where necessary
                    if (ci.Equals(CultureInfo.CurrentUICulture))
                   
                        classAttribute += " " + "sflangSelected";
                   

                    langHolder.Attributes.Add("class", classAttribute);

                    //Add href to link
                    HtmlAnchor langLinkControl = (HtmlAnchor)e.Item.FindControl("langLink");
                    langLinkControl.HRef = url;
                    langLinkControl.Attributes.Add("lang", ci.TwoLetterISOLanguageName);

                    HtmlGenericControl langNameControl = (HtmlGenericControl)e.Item.FindControl("langName");
                    langNameControl.InnerHtml = languageName;
               
           
       

The code marked in yellow gets the url for each language link in the language selector you can overwrite that url before you set it as href to the langLinkControl.

Please let me know if you have any problems.

Kind regards,
Lilia Messechkova
the Telerik team

Do you want to have your say in the Sitefinity development roadmap? Do you want to know when a feature you requested is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items

This thread is closed