Internationalisation d’une application ASP.NET MVC 3 Razor part 3 : Mécanisme de sélection de la langue dans l’IU

Dans les parties précédentes, nous avons introduit l’internationalisation sur la plateforme .NET et nous avons vu comment procéder à la localisation des vues, des messages d’erreur de validation et des attributs Display dans le modèle.

Cependant, jusqu’ici, lors de nos tests, vous pouvez vous rendre compte que notre application ne dispose d’aucun mécanisme permettant à un l’utilisateur à partir de l’interface de choisir une langue ou de basculer d’une langue à une autre à tout moment.

Cet aspect de l’internationalisation d’une application Web ASP.NET MVC 3 Razor fera l’objet de ce billet de blog.

Nous allons utiliser l’application que nous avons créée précédemment.

Dans notre cas, nous allons définir la langue qui est utilisée dans L’URL. Pour cela, nous allons commencer par définir la stratégie de routage qui sera utilisée dans notre application, en spécifiant la langue. L’URL que nous allons utilisera sous la forme suivante :

http://localhost/fr-fr/home/index pour le français
et
http://localhost/en-us/home/index pour l’anglais.

La route par défaut dans ASP.NET MVC 3 est définie sous la forme : http://localhost/controller/action/id. À partir de là, nous allons définir de nouveaux paramètres de route qui permettront de générer l’URL avec la langue. Pour cela, nous allons définir la route sous la forme suivante : http://localhost/lang/controller/action/id.

Pour atteindre ce résultat, il suffit de modifier le fichier Global.ascx.cs, et enregistrer une nouvelle route. Le code pour faire cela est le suivant :

public static void RegisterRoutes(RouteCollection routes)
{
routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
routes.IgnoreRoute("favicon.ico");

routes.MapRoute(
"LocalizedDefault", // Route name
"{lang}/{controller}/{action}/{id}", // URL with parameters
new { controller = "Home", action = "Index", id = UrlParameter.Optional } // Parameter defaults
);

routes.MapRoute(
"Default", // Route name
"{controller}/{action}/{id}", // URL with parameters
new { controller = "Home", action = "Index", id = UrlParameter.Optional } // Parameter defaults
);
}

Maintenant, vous devez ajouter un nouveau contrôleur (BaseController) qui héritera de System.Web.Mvc.Controller. Sa fonction principale sera de changer la langue du Thread d’exécution courant selon la valeur de la langue dans l’URL ou dans un cookie existant, et de sauvegarder le choix linguistique de l’utilisateur dans un cookie si ce n’est pas déjà fait. Si aucune langue n’est spécifiée dans l’URL, la langue du Thread d’exécution sera modifiée en utilisant par défaut la langue du navigateur de l’utilisateur.

Le code pour faire cela est le suivant :

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using System.Text;
using System.Threading;
using System.Globalization;

namespace MvcApplication1.Controllers
{
public class BaseController : Controller
{
//
// GET: /Base/

protected override void ExecuteCore()
{
if (RouteData.Values["lang"] != null &&
!string.IsNullOrWhiteSpace(RouteData.Values["lang"].ToString()))
{
// modification de la culture dans les données de la route
var lang = RouteData.Values["lang"].ToString();
Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture(lang);
}
else
{
// chargement de la culture depuis un cookie
var cookie = HttpContext.Request.Cookies["MvcApplication1.CurrentUICulture"];
var langHeader = string.Empty;
if (cookie != null)
{
// modification de la culture avec la valeur dans le cookie
langHeader = cookie.Value;
Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture(langHeader);
}
else
{
// utilisation de la langue par défaut du naviageteur si la culture n'est pas spécifiée
langHeader = HttpContext.Request.UserLanguages[0];
Thread.CurrentThread.CurrentUICulture = CultureInfo.CreateSpecificCulture(langHeader);
}
// modification de la culture dans les données de la route
RouteData.Values["lang"] = langHeader;
}

// sauvegarde de la culture dans un cookie
HttpCookie _cookie = new HttpCookie("MvcApplication1.CurrentUICulture", Thread.CurrentThread.CurrentUICulture.Name);
_cookie.Expires = DateTime.Now.AddYears(1);
HttpContext.Response.SetCookie(_cookie);

base.ExecuteCore();
}

}
}

Tous les contrôleurs de l’application doivent être modifiés pour hériter de ce contrôleur (Basecontrolleur).

public class HomeController : BaseController

Après avoir enregistré la route localisée, nous devons procéder à l’écriture d’une fonction permettant de générer l’URL localisée en fonction du choix de la langue de l’utilisateur.
Pour cela, nous allons ajouter un HTML Helper dans notre projet. Les Helpers HTML sont des méthodes d’extensions pour les classes HtmlHelper. Ces méthodes sont accessibles dans une vue à partir de la méthode HTML.

Le code pour notre Helper HTML est le suivant :

public static class SwitchLanguageHelper
{
public class Language
{
public string Url { get; set; }
public string ActionName { get; set; }
public string ControllerName { get; set; }
public RouteValueDictionary RouteValues { get; set; }
public bool IsSelected { get; set; }

public MvcHtmlString HtmlSafeUrl
{
get
{
return MvcHtmlString.Create(Url);
}
}
}

public static Language LanguageUrl(this HtmlHelper helper, string cultureName,
string languageRouteName = "lang", bool strictSelected = false)
{

cultureName = cultureName.ToLower();
// récuperation des valeurs de ka route depuis le view context
var routeValues = new RouteValueDictionary(helper.ViewContext.RouteData.Values);

//copie de la chaine de requête dans les valeurs de route pour générer le nouveau lien
var queryString = helper.ViewContext.HttpContext.Request.QueryString;
foreach (string key in queryString)
{
if (queryString[key] != null && !string.IsNullOrWhiteSpace(key))
{
if (routeValues.ContainsKey(key))
{
routeValues[key] = queryString[key];
}
else
{
routeValues.Add(key, queryString[key]);
}
}
}
var actionName = routeValues["action"].ToString();
var controllerName = routeValues["controller"].ToString();
//modification de la langue dans les valeurs de route
routeValues[languageRouteName] = cultureName;
//génération de l'url avec la langue
var urlHelper = new UrlHelper(helper.ViewContext.RequestContext, helper.RouteCollection);
var url = urlHelper.RouteUrl("LocalizedDefault", routeValues);
// vérification si la culture courante correspond à celle passée en paramètre
var current_lang_name = Thread.CurrentThread.CurrentUICulture.Name.ToLower();
var isSelected = strictSelected ?
current_lang_name == cultureName :
current_lang_name.StartsWith(cultureName);
return new Language()
{
Url = url,
ActionName = actionName,
ControllerName = controllerName,
RouteValues = routeValues,
IsSelected = isSelected
};
}


public static MvcHtmlString LanguageSelectorLink(this HtmlHelper helper,
string cultureName, string selectedText, string unselectedText,
IDictionary htmlAttributes, string languageRouteName = "lang", bool strictSelected = false)
{
var language = helper.LanguageUrl(cultureName, languageRouteName, strictSelected);
var link = helper.RouteLink(language.IsSelected ? selectedText : unselectedText,
"LocalizedDefault", language.RouteValues);
return link;
}


}

Enfin, dans le dossier View/Shared, nous allons ajouter une vue partielle (_SelectLanguage.cshtml) pour la sélection de la langue par l’utilisateur.
Le code pour cette page est le suivant :

@using MvcApplication1.MyHelper

@Html.LanguageSelectorLink("en-US", "[English]", "English", null)
@Html.LanguageSelectorLink("fr-FR", "[Français]", "Français", null)

La vue partielle doit être appelée dans le Layout de votre projet :

<div id="logindisplay">
@Html.Partial("_LogOnPartial")
@Html.Partial("_SelectLanguage
</div>

Nous pouvons maintenant exécuter l’application pour voir le résultat produit comme l’illustrent les captures suivantes :

Et voilà, nous venons de finir avec la dernière étape d’internationalisation de notre application. J’espère que ce tutoriel vous sera d’une grande utilité pour créer des applications ASP.NET MVC 3 multilingues ;).

Une réflexion au sujet de « Internationalisation d’une application ASP.NET MVC 3 Razor part 3 : Mécanisme de sélection de la langue dans l’IU »

  1. Bonjour,
    Tout d’abord, je vous remercie pour ce tuto. Cependant, j’ai une version plus récente c’est asp.net MVC4 et je n’arrive pas à réaliser la dernière étape avec les layout j’ai essayé de les mettre dans ma page d’accueil mais cela ne marche pas. J’aimerai savoir quel modification je dois apporter au layout et ou les intégrer?
    Merci d’avance

Laisser un commentaire