Skip to main content

Setup a multi-language website using ASP.NET MVC

Introduction

Since the first release of the .NET framework developers are given the chance to easily configure any kind of project – be it a Website, a Web Application, a Windows Forms or XPF/XAML client and such – in order to support multiple languages. This can be achieved using the well-known Resource Files (.resx) approach. We won’t explain them here (if you’re interested, read the official walkthrough), but we’ll remember a couple key concepts. A Resource Files is basically a key/value array of content resources (mostly images and text) for each supported language. All the developers have to do is to create a .resx file for the main language (let’s say english) and another one for each of these languages using the same name plus the ISO 639-1 two-letters language code of the language itself, i.e.:

  • Global.resx file to store text and images for english, assuming it’ll be our default & fallback language.
  • Global.it.resx file to store text and images for italian language
  • Global.de.resx file to store text and images for german language

and so on. Once we did that, we’ll only have to write our code using the key specified in these files instead of the actual content (if you don’t know how, read the walkthrough above): ASP.NET will look up the keys in our Resource Files, starting from the one with the Localization closest to the one set for the current thread and then going backwards until it founds something to show.

Kickass feature, indeed: let’s see how we can use it to build our very own multi-language MVC ASP.NET Web Application.

Resource Files in MVC

The first question would be: where do we put the .resx files? The answer is all but granted: our first choice would be adding the  App_GlobalResources ASP.NET Folder to our project, just like we always did since .NET Framework 1.1: where else?

App_GlobalResources

You could be surprised, but if you’re working with MVC this is not the right choice. If you want to know why, you can read the whole story in this great article by K. Scott Allen sul tema. To summarize it, let’s just say that the Framework will compile that folder in a separate assembly, thus making them unaccessible to our ControllersUnit Tests, etc.: we don’t want this, that’s why it’s better to just place them in a separate, dedicated standard folder which we’ll just call  /Resources/ .

Once we added there our .resx files there’s another thing we need to do: we need to change some default settings by opening each file’s Properties window:

Resx.Properties

First thing we need to do is to change the Custom Tool, which is the code-generator engine used by the Framework to build the Resource File strongly-typed class. The default tool, ResXFileCodeGenerator, would generate a private class, which is not what we want. That’s why we’ll replace it with the PublicResXFileCodeGenerator, which will be able to generate a public class with public methods & properties: just like what we need.

Second settings to change is the Custom Tool Namespace: default value, an empty string, means no namespace, which is far from ideal. That’s why we’ll replace it with something like Resources, so the custom tool will generate a code consistent with our folder structure: our resources will be located in the /Resources/  folder and will also have the Resources namespace: that’s good enough.

Notice that these small modifications will be required for each and every .resx we’ll add to our project: you cannot setup these values as default, but you can still duplicate your Resource Files so you’ll always have these settings set, since each .resx copy comes with the same properties as the source file.

How to serve the proper language to each Request

As we said before, .NET Framework automatically select the Resource Files closest to the localization of the actual thread, which is the one that will process the http request and serve the proper http response accordingly. The localization info are stored in the response thread’s CultureInfo object, which is usually set against the language specified by the request’s browser/client. Meaning that we’ll be able to serve the same contents in different languages – depending by the browser’s client language settings – upon the same URL.

Same URL, different content. Would that be a proper behaviour? We could be tempted to say yes – after all, allowing each user to read the exact same URL in their home/native language seems like a good thing. Problem is, from a SEO perspective it’s a complete failure. Everyone who knows something about the field knows that you need a different URL for each localized version of the same page. If you have doubts about that, we suggest you to carefully read this  brief Google guide about SEO featuring some useful best-practices, the most important one being the following: Keep the content for each language on separate URLs.

This basically means that we can’t just set the thread language taking into accont things like:

  • the user’s browser language
  • cookie values (if set)
  • user session values (if present)
  • any other Request-based field (HEADER, POST data, etc.) different from the URL

But we need to build a proper URL-based localization mechanism, where each language answers to its very own set of URL patterns, such as:

  • http://www.example.com/page (for default language contents – english in our example)
  • http://www.example.com/it/page (for all italian contents)
  • http://www.example.com/de/page (for all german contents)

… And so on. Once we do that, we’re free to use some or all the above info to route the requests we receive to the most suited language – i.e. sending the english browsers to the english contents and stuff like that. This basically means that we will use the URL to set the thread localization, and any other info – browser language, cookie values and such – to choose the user’s default route.

Let’s see how we can build our Web Application to make sure it will behave in such way.

Set-up a Multi-Language Route

First thing we have to do is to setup an ASP.NET Route to handle these kind of requests and store the localization-related info. If our web-application implements the standard ASP.NET MVC route-pattern, such as {controller}/{action}/{id}, you can use the following example:

You’ll need to put this route in the  /App_Start/RouteConfig.cs file just before the last one, which is the pre-defined route{controller}/{action}/{id}. If you’re Web Application used a different routing approach, you’ll need to adopt a similar, yet suitable strategy according to that.

The main goal of this “localized” Route is to isolate and store a   lang  variable corresponding to the requested language. This information, if present, will be used to set the localization of the current Thread so it will use the corresponding Resource Files.

Using a LocalizationAttribute to handle Multi-Language Requests

Now that we have a Localization Route to catch our multi-language URL calls and store our language info in a handy variable, we need to find a way to programmatically handle it. To fullfill this task we can create a LocalizationAttribute by creating a new LocalizationAttribute.cs class: the attribute will be executed upon each Action and it will set the current Thread‘s Culture and the UICulture with the value stored into the lang variable by the route.

This class can be put everywhere in our Web Application, such as a /Classes/  or  /AppCode/ folder. Once we add it to our project we also need to make sure it will be executed upon each request/Actions: we can do that by registering it as a Global Filter by using the RegisterGlobalFilters method in the  /App_Start/FilterConfig.cs  class:

The marked line shows the line we need to add to the default implementation to make our LocalizationAttribute kick in upon each and every response. We can – and actually should – also choose a default Localization – “en” in our sample, corresponding to the English language: that will ensure that we’ll serve the default language for any URL not containing Localization info, i.e. any time the lang variable will be set to null because the request will be handled by a route other than our LocalizationRoute.

Using a LocalizedControllerActivator instead of a LocalizationAttribute

IMPORTANT: A couple commenters made me recently realize that setting the culture in the OnActionExecuting method might be too late in some cases, due to how MVC lifecycle actually works. A common example of this is when the model metadata is being created by ASP.NET MVC right after a POST request, which is something that gets processed before any ActionFilter – including ours! When this happens, a lot of stuff (such as the DataAnnotations values) is handled using the default culture.

Luckily enough, we can easily overcome this by creating a LocalizedControllerActivator instead of the LocalizationAttribute in the following way:

And implement it in the following way (Global.asax.cs or Startup.cs, depending if you’re using the OWIN startup pattern or not):

This is the most reliable implementation to handle this issue, regardless if we’re working with DataAnnotations or not.

Source: StackOverflow (many thanks to s.ermakovitch for sharing this and to Rob LeGood for pointing it out).

Translating MVC Routes

There’s still a major issue we need to address yet: we need a good plan to translate/localize the URLs generated by the Razor helpers such as Html.ActionLink , Url.Action  and so on. There are two ways we can choose to do that:

  • Implementing a custom HtmlHelper  that will accept an additional   CultureInfo  object (using CultureInfo.CurrentUICulture  if/when null) and use it to prepend a /prefix/  built against the CultureInfo.TwoLetterISOLanguageName  property value.
    EDIT: by popular demand, we recently added a sample implementation of this technique by using two extension methods to enhance the Html.ActionLink and Url.Action so they can accept a CultureInfo object (or just use the one provided by the application’s CurrentCulture).
  • Using the great RouteLocalization project by Dresel, available at this link, that can be used to do that and also a lot more interesting stuff such as “fully-translated” routes. You can also grab it via NuGet with the following names:
    • RouteLocalizaiton.Mvc  (for MVC)
    • RouteLocalization.WebApi  (for WebApi)

If you just need to prepend the culture code to your URLs you might just stick to the former option and save some valuable time: if you don’t know how to get the relevant stuff done, just ask for help in this post comments and we’ll be more than happy to provide a working code sample. If you want more flexibility, such as being able to do /en/Products  for English and /it/Prodotti  for Italian, you should really give the latter one a try. Here’s a great guide about how to use/implement it:

Conclusions

We don’t need to do anything else, except creating the relevant .resx files for any language we want to support. As soon as we do that, we’ll be able to test the results of our work by calling the following pages of our Web Application:

  • http://www.example.com/page , seeing our contents in the default language (which is english in our example).
  • http://www.example.com/it/page , seeing our contents in italian language (with a fallback to the default language if not present).
  • http://www.example.com/de/page , seeing our contents in german language (with a fallback to the default language if not present).

… and so on.

 

RELATED POSTS

Ryan

IT Project Manager, Web Interface Architect and Lead Developer for many high-traffic web sites & services hosted in Italy and Europe. Since 2010 it's also a lead designer for many App and games for Android, iOS and Windows Phone mobile devices for a number of italian companies.

  • Alex

    If your default language is English, I am curious why you have both http://www.example.com/page and http://www.example.com/en/page ? Why not simply default to ‘en’ language i.e. http://www.example.com/en/page ? Are there SEO reasons or MVC best practices for having both URLs? It would seem that this setup would lead to duplicate content and hurt SEO.

    • Ryadel

      Hi Alex,

      thanks for your reply. Actually my default language is Italian, that’s why you found the /en/ reference in the above post. I understand that it could be counterintuitive in an english-written post, so I changed it a little following your advice: now I clearly stated that the default language is english, and I also changed the example URLs accordingly. As a side note, I can absolutely confirm that there aren’t SEO reasons or MVC best practices for having the same language content served by different URLs, as it would definitely hurt SEO: that was the point of the whole post and I hope that now everything is clear enough.

      Thank you for helping me writing a better post.

      • Alex

        Thank you for the post!

        After the update, see the conclusion section, http://www.example.com/it/page is referenced as English.

        Thanks again.

        • Ryadel

          Fixed! Thanks again

  • Pingback: Change IIS default language on a working Windows Server()

  • Pingback: ASP.NET - Insert HTML code in Resource Files (.resx)()

  • Koko

    Is the default language changeable from controllers ?

    • Yes, you can insert something like that in an action method:

      Thread.CurrentThread.CurrentCulture = new System.Globalization.CultureInfo(yourLanguageString);
      Thread.CurrentThread.CurrentUICulture = Thread.CurrentThread.CurrentCulture;

  • Sven Bock

    Can you tell me how to achieve translated URL’s in this approach?

    • Hello, thanks for the comment and sorry for the delay. Please see my answer to hayim S regarding this.

  • Amol Oak

    Great article! Was precise and to the point.

  • hayimS

    Hi Ryan,
    Great and practical post for the multi-lingual issue.
    I have a question: I implemented your suggestion and it mostly works great.
    my problem is that for some links created by razor (Html.ActionLink, Url.Action)
    the href is without the language prefix. For example ,when I am in mysite/es, I
    get the Spanish copy I put it the resx file, but some links on the page are still : mysite/somepage
    and not mysite/es/somepage. I hope it makes sense,
    any thought would be appreciated.

  • Pingback: Multi Language ASP.net MVC | Porão do AJ()

  • E.B

    Hey Rayan, Congrats on this great post.
    Just when Creating the new route, need to add a constraint to the default route generated by visual studio, so the id param would be accepted as an integer (or some other modifications), otherwise
    the route “{controller}/{action}/{id}” will be selected instead of “{lang}/{controller}/{action}” with an id optional.

    • Hi to you and hanks for the support! 🙂

      Regarding your suggestion, I am fairly sure that if you add my route before the default one, just like I said in the post, mine will always trigger first, as it will be processed first.

  • Perry

    this is great but for some reason, on one of my project that I copied from RBAC (http://www.codeproject.com/Articles/875547/Custom-Roles-Based-Access-Control-RBAC-in-ASP-NET), the default routing was not working. I had to modify it this way:
    defaults: new { lang = “en”, controller = “Home”, action = “Index”, id = UrlParameter.Optional }

    • That’s not recommended tho, since you won’t be able to properly handle browser redirection for the default URLs by forcing that route attribute (see my above answer to Jostein Torseter for details).

      If you see the above LocalizationAttribute implementation (first line of the OnActionExecuting method) you can clearly see that, if the lang routeValue is not present, the default one is used instead (which should be “en” in your scenario). I would put a breakpoint on that line and take a look on what happens there.

  • Jostein Torseter

    Ok, so I have tried to set this up according to the instructions (great post btw, thanks!), but I am having a logical issue. I have set up my view with a test string, and on //localhost/Home/Test it shows my default language (norwegian). Also, if i navigate to //localhost/en/Home/Test i get the english version. Fine so far. But how will the browser know where to direct me in the first place? The site address never contains the “en”, and it does not redirect me automatically based on the language of my browser. I might be missing something obvious here, but how do I make sure a user with a browser set to english will end up on the /en/ pages?

    • This method doesn’t automatically “redirect” the browser to its default language, but you can easily do that by issuing a conditional redirect inside the LocalizationAttribute’s OnActionExecuting method, assuming these two conditions are true:

      1) there is no explicit filterContext.RouteData.Values["lang"] set, meaning that the browser is poking the “default” url without a language being specified: if that’s not the case, you should probably respect that since it most likely is an explicit choice issued by the client.

      2) the Thread.CurrentThread.CurrentUICulture (which you can use to fetch the browser’s default language from server-side in .NET) is different from the default one (which is _DefaultLanguage in my sample).

      If these two conditions are both true, you can most likely put together something like the following:

      [/crayon]

      … or something like that.

      Let me know if that’s enough or if you need a full working code sample.

  • Rob LeGood

    Hey Ryan,

    Great article, but I’m running into an issue myself. I’m unable to get this working with DataAnnotations. I’m setting the annotation properly, ie..

    [Required(ErrorMessageResourceType = typeof(Resources.SharedRegistration), ErrorMessageResourceName = “ERROR_EMAIL_REQ”)]

    ..but I’m always getting my default language back from this. It’s acting like these values are set before the filter changes the culture.

    Any thoughts on what I’m doing wrong? Thanks!!

    (Edit: Note that I’m not using RouteLocalization)

  • Fanouris

    Hello Ryan,

    I followed your tutorial and it works great so far.
    I have but one question. I have 3-4 language menus in the _Header file of my application.
    Is there a way (and how) to create a Html or Url.Action to change the language of the site, but redirect the user to the same page he was when he clicked the languageChange button?

    In which controller should i put this method? I tried putting it in the HomeController, but i could’t redirect the user to the previous page he was and changing the ‘lang’ parameter

  • Pingback: Html.ActionLink Extension Method for multi-language Routes in NET MVC()

  • Pingback: Url.Action Extension Method for multi-language Routes in NET MVC()

  • Alex

    Hello Ryan.
    That’s really good! Thanks a lot for sharing this information.

    But still, i have one questionissue.
    I am unable to use attribute routing. Just always getting 404 error.
    Currently URLs are generated in form “/en/Home/About”, “/en/Home/Contact”, etc.
    How it could be achieved to get URLs like “/en/About”, “en/Contact”, etc?

    I’ve played with RoutePrefix, Route for each ActionResult, etc (routes.MapMvcAttributeRoutes(); was in RouteConfig) but result was the same all the time – 404.

    Also i’ve slightly amended your described solution to following, to get automatic redirection to required language:

    public IController Create(RequestContext requestContext, Type controllerType)
    {
    string language = “en”;
    List supportedLanguages = new List() {“en”,”de”,”es” };
    if(requestContext.RouteData.Values[“lang”] == null)
    {
    if(supportedLanguages.Contains(CultureInfo.CurrentCulture.TwoLetterISOLanguageName))
    {
    language = CultureInfo.CurrentCulture.TwoLetterISOLanguageName;
    string redirectString = requestContext.HttpContext.Request.RawUrl == “/”? “/” + language : “/” + language + requestContext.HttpContext.Request.RawUrl;
    requestContext.HttpContext.Response.Redirect(redirectString,false);
    }
    }
    else
    {
    language = requestContext.RouteData.Values[“lang”].ToString();
    }

    //Get the culture info of the language code
    CultureInfo culture = CultureInfo.GetCultureInfo(language);
    Thread.CurrentThread.CurrentCulture = culture;
    Thread.CurrentThread.CurrentUICulture = culture;

    return DependencyResolver.Current.GetService(controllerType) as IController;

    Thank you in advance for suggestions.

    • Alex

      Hi again.
      Looks like I’ve found root cause and it’s solution.

      First of all, when Route attribute was applied to Action, when i was clicking on the link (which was correct, like “/en/About”), my requestContext.RouteData.Values was without “lang” key, and instead there was “MS_DirectRouteMatches” key with another RouteData object in it’s value, which containing “lang” key and it’s correct value. As result, “requestContext.RouteData.Values[“lang”] == null” was returning “True” and i was redirected to /en/en/About (language was in URL 2 times).
      After searching for “MS_DirectRouteMatches”, an answer was found:

      http://stackoverflow.com/questions/25727558/asp-net-mvc5-route-annotation-ms-directroutematches

      So final function now is following, and works correctly (while it, maybe, not very elegant 🙂 ):

      public IController Create(RequestContext requestContext, Type controllerType)
      {
      string language = “en”;
      List supportedLanguages = new List() {“en”,”de”,”es” };
      string requestLanguage = requestContext.RouteData.Values[“lang”] as string;
      if(requestLanguage == null)
      {
      if (requestContext.RouteData.Values.ContainsKey(“MS_DirectRouteMatches”))
      {
      RouteData routeData = ((IEnumerable)requestContext.RouteData.Values[“MS_DirectRouteMatches”]).First();
      requestLanguage = routeData.Values[“lang”] as string;
      }
      }
      if (requestLanguage == null)
      {
      if(supportedLanguages.Contains(CultureInfo.CurrentCulture.TwoLetterISOLanguageName))
      {
      language = CultureInfo.CurrentCulture.TwoLetterISOLanguageName;
      string redirectString = requestContext.HttpContext.Request.RawUrl == “/”? “/” + language : “/” + language + requestContext.HttpContext.Request.RawUrl;
      requestContext.HttpContext.Response.Redirect(redirectString,false);
      }
      }
      else
      {
      language = requestLanguage;
      }

      //Get the culture info of the language code
      CultureInfo culture = CultureInfo.GetCultureInfo(language);
      Thread.CurrentThread.CurrentCulture = culture;
      Thread.CurrentThread.CurrentUICulture = culture;

      return DependencyResolver.Current.GetService(controllerType) as IController;
      }

      Now i can use routing attribute as following:
      [Route(“{lang}/About”)]
      public ActionResult About()

      But at the same time i have another minor issue with ActionResult Index()
      I was trying to decorate as following (commenting and uncommenting it in different combinations):
      [Route(“/”)]
      [Route(“{lang}”)]
      [Route(“{lang}/Index”)]
      public ActionResult Index()

      But in this case i am getting Index URL generated without currently selected language, just “/”, and if i am clicking it, selected language then reset to CultureInfo language, or, getting 404 error.
      Without any decoration for this Action – i am getting correct URL, for example “/en”, or other currently selected language, and no 404’s. Any ideas how to solve it?

    • Hello Alex,

      To achieve such result I would do the following (assuming your About and Contact ActionMethods are in HomeController.cs):

      routes.MapRoute(
      name: “DefaultLocalized”,
      url: “{lang}/{action}/{id}”,
      constraints: new { lang = @”(w{2})|(w{2}-w{2})” }, // en or en-US
      defaults: new { controller = “Home”, action = “Index”, id = UrlParameter.Optional }
      );

      However, since you’re using AttributeRouting, you won’t need that.

      Regarding the auto-redirection to browser-default language, your approach seems quite overkill to me: I would do something like the following instead (adding the “lang” to route value if it isn’t set).

      public class LanguageCodeAttribute: ActionFilterAttribute
      {
      private string[] _AcceptedLangCodes = new[] { “en”, “it” };
      public string[] AcceptedLangCodes { get { return _AcceptedLangCodes; } set { _AcceptedLangCodes = value; } }

      private string _DefaultLangCode = “it”;
      public string DefaultLangCode { get { return _DefaultLangCode; } set { _DefaultLangCode = value; } }

      private string _RouteDataKey = “lang”;
      public string RouteDataKey { get { return _RouteDataKey; } set { _RouteDataKey = value; } }

      // This checks the current langauge code. if there’s one missing, it defaults it.
      public override void OnActionExecuting(ActionExecutingContext filterContext)
      {
      // Determine the language.
      if (filterContext.RouteData.Values[RouteDataKey] == null || !AcceptedLangCodes.Contains(filterContext.RouteData.Values[RouteDataKey]))
      {
      // Add or overwrite the language code value.
      if (filterContext.RouteData.Values.ContainsKey(RouteDataKey)) filterContext.RouteData.Values[RouteDataKey] = DefaultLangCode;
      else filterContext.RouteData.Values.Add(RouteDataKey, DefaultLangCode);
      }

      base.OnActionExecuting(filterContext);
      }
      }

      I’m using the ActionFilterAttribute approach here but you can do the same with the IControllerActivator approach you’re using instead. Anyway, in the above sample I’m forcing the DefaultLangCode here if there’s none, but you could go with CultureInfo.CurrentCulture.TwoLetterISOLanguageName instead to achieve what you want.

      Last but not least, in case you need a centralized way to generate CultureInfo-aware ActionLinks or URLs, I would suggest you reading my other 2 recent posts about Html.ActionLink and Url.Action, adding an overload to skip the Controller part in the url generation.

      • Alex

        Emm, something wrong with you site, Ryan…

        • Changed DNS tonight 🙂 It will take some hours. If you’re in a hurry, add the following to your /system32/drivers/etc/hosts file:

          5.189.148.122 http://www.ryadel.com

      • Alex

        Hi Ryan.
        Regarding firs part of my question everything is clear – i am using AttributeRouting.

        But regarding second part (see my comment from September 16, 11:54 PM) – why my approach look so bad for you? What is the difference between adding language in front of URL and then doing redirection, and your approach with RouteData values?

        • There’s nothing bad in your approach: never said that 🙂 I just thought it was quite overkill, as you are basically doing the same thing twice: since I’ve already put up an engine that uses routeData I would just stick to that instead, until I can for all language-related issues… but it was just my thought.

  • Nicolai

    Are you using both LocalizedControllerActivator and the LocalizationAttribute class?
    Cause when im trying to only use the LocalizedControllerActivator class I get an error saying :

    “The given filter instance must implement one or more of the following filter interfaces: System.Web.Mvc.IAuthorizationFilter, System.Web.Mvc.IActionFilter, System.Web.Mvc.IResultFilter, System.Web.Mvc.IExceptionFilter, System.Web.Mvc.Filters.IAuthenticationFilter.”

  • Sanjeev

    Ryadel, your tutorial is really good and helpful. However i would really appreciate if you could add a test project which would be really handy.
    Thanks.

  • Nhi Sửu

    Hi Ryadel,
    Thanks for your article, i would like to make a website multiple language and route like you site (http://www.ryadel.com/en/setup-a-multi-language-website-using-asp-net-mvc/). i saw the way you do that it seem easy. Please guide me step by step in asp.net mvc 5. Thank you a lot.

    • Nhi Sửu

      when i did like your article, after that how to i want to get language in url? if i do like HttpContext.Current.Request[“lang”]; it always null. Pleases help me

      • You won’t find it in the request, because it’s not a GET or POST parameter: it’s a route value.

        You can get the current language by using Thread.CurrentThread.CurrentCulture, since this is where we set it once retrieved by the URL.

        Or, if you have a requestContext available, you can pull it off by calling requestContext.RouteData.Values[“lang”].

  • Os1r1s Major

    Hi there, I’d like to know how to change the URL when the user clicks on the language button to change it. As of now I send the “returnUrl” from the view but my default url for example will be something like root/, no locale specified as a default one has been specified in the routing setup.

    Now I need to be able to insert the desired locale into the url prior to redirecting the user to the other language version…. Would someone have an idea of how to accomplish it?

    Thanks in advance!

  • Diogo Almeida

    It was giving me an ‘object reference not set’ because requestContext.RouteData.Values[“lang”] is null when there is no labguage set in the URL.

    changed it to:
    string lang = (requestContext.RouteData.Values[“lang”] != null) ? requestContext.RouteData.Values[“lang”].ToString() : _DefaultLanguage;

    • Hello, that’s quite strange because null values are handled by my code (using the ?? coalesce operator)… Can you tell me the line you needed to change?

  • Matheus Lemos

    Hello Ryadel! Great post, thank you very much! I managed to make it working using /en/test and /pt-br/test for example but I have one question still… Is there a way to “keep” the current language so all the pages that I access after changing the language will be opened with the selected language? With a Dropdown for lang selection, for example. Know what I mean?

    • Hey Matheus, you can definitely setup a cookie in the browser client and then retrieve that value using Get-Cookie (if it does exist) to valorize the DefaultLanguage within the LocalizationAttribute OR within the LocalizedControllerActivator, depending of the path you’ve chosen to follow: it would be very simple to implement.

      Regarding the Set-Cookie part, I think that a good place to do that would be whenever the language fetched from the route value is different from DefaultLanguage. Please let me know if that’s enough to help you!

    • Matheus Lemos

      Well, I think I finally found it. For those who are looking for it too, here it is:
      http://stackoverflow.com/questions/928053/asp-net-mvc-switch-language-how-to-implement

      • Yeah: you will notice that it does that by setting a client-side cookie in the same exact way I just wrote in the answer below 🙂

  • Pitri

    I implemented your method and in general it works fine. I used the LocalizedControllerActivator version.

    My problem is that my actionlinks do not work properly. I can switch the language but then it adds just another {lang}.

    Example:
    Root-Url: http://contoso.com/
    Action-Link – First click: http://contoso.com/en/Home
    Action-Link 2 – Second click: http://contoso.com/en/en/Home

    My Action-Link Code:
    @Html.ActionLink(“EN”, “Index”, “Home”, null, new { @class = “linkImgGB”, @alt = “English Version”}, CultureInfo.GetCultureInfo(“en”))

    How can I fix this problem? Any idea?
    Thanks in advance!

Close
Read previous post:
WordPress: re-enable Publicize for already published posts via Jetpack Publicize

If you use Wordpress and you do not know the Jetpack plugin we can't help but recommend you to fill...

Close