Cómo cambiar la cultura manualmente en ASP.NET MVC?

Buenas a todos! Después de varios meses vuelvo al ruedo en el blog, así que vamos a arrancar nuevamente.

El disparador de este post es el comentario de Carlos en Internacionalizar entradas de usuario en ASP.NET MVC:

Quería preguntarte, si es recomendable o no y como se haría para que un usuario pudiera cambiar el idioma de la web pues pulsando en una banderita o escogiendo un idioma de alguna manera sin tener que ver con la configuración del navegador.

La verdad es que es una excelente pregunta, así que vamos a responderla creando este post.

El post original donde comenzamos con este concepto de internacionalización en ASP.NET MVC lo planteamos cómo algo para poder tomar automáticamente la cultura del navegador del usuario. Esto es una excelente alternativa, ya que estamos interpretando la cultura que tiene el usuario brindándole el contenido acorde a esa definición sin que deba hacer nada adicional. Pero también hay que ser conscientes de que el usuario puede estar con una configuración heredada en el navegador por el cual accede que no sea la suya, y por lo tanto quiera cambiarla. Ante esto debemos poder darle la posibilidad de ese cambio, y que esa configuración se mantenga para dicho usuario. Así que veamos como hacerlo!

Lo primero que haremos será tomar como base todo lo hecho en el post de internacionalización inicial de esta serie. Sobre todo lo que es la configuración en el archivo web.config para habilitar que se tome la cultura del cliente:

Configuración de cultura en Web.Config
Configuración de cultura en Web.Config

Lo primero que debemos hacer es saber cómo establecer la cultura de forma manual para un usuario. Para ello lo que podemos hacer es trabajar con el hilo de ejecución del usuario actual, lugar donde está la cultura actual. Así que sería el lugar donde podemos editar su valor.

Lo primero que vamos a hacer es una prueba piloto, para validar que nuestro enfoque sea válido. Para ello agregaremos en una acción de controlador el establecimiento de la cultura en el hilo de ejecución de forma manual a uno distinto al que tengamos en nuestro navegador (en mi caso tengo español así que lo cambiamos a inglés):

CulturaManual - PruebaCultura
Establecemos una cultura distinta de forma manual

Como se puede ver, aplicamos directamente en el Thread actual una nueva cultura con la nomenclatura estándar utilizada normalmente. Ahora vamos a probar acceder desde nuestro navegador a dos acciones, Index y About. En la primera debería verse el menú en español con la cultura actual y en la segunda se debería ver en inglés (es lo único que tenemos adaptado con archivos de recursos según la cultura):

CulturaManual - AccesoInicialEspanol
Acceso inicial en español
CulturaManual - AccesoInicialIngles
Acceso a la acción con cultura establecida de forma fija

Efectivamente el resultado es el esperado, así que con esto ya sabemos que nuestro enfoque es válido, por lo que ahora nos queda definir cómo gestionarlo. Y con esto apunto a cómo mantener el estado de ese cambio de cultura para el usuario, ya que ASP.NET MVC por defecto no maneja estado, haciendo que cada request HTTP sea independiente al otro. Siguiendo el ejemplo anterior, si luego de la acción About vuelvo a Index volveré a ver todo en español, ya que el cambio hecho en la cultura solo sirvió para ese hilo y por ende ese request particular.

Para ello propongo utilizar una cookie para pasar el valor entre los sucesivos request que haga un usuario particular hacia nuestro sitio. Esto basándome en que es un mecanismo integrado y por lo tanto simple de usar. El enfoque está pensado para sitios web’s convencionales donde cada usuario que lo visita es un anónimo, si pasamos a un esquema donde el usuario accede con una cuenta particular allí tal vez deberíamos cambiar algunas cosas.

Para esta propuesta lo primero que vamos a hacer es definir el mecanismo para establecer la cultura a petición del usuario. Algo simple que vamos a hacer para este ejemplo es una acción en el controlador Home, la cual recibirá como parámetro el valor de cultura que queramos establecer:

CulturaManual - AccionCookie
Establecimiento de la cultura en una cookie

Cómo se puede ver, tan solo estamos guardando una cookie con el texto de la cultura y la clave correspondiente para que podamos usar para luego identificar esa cookie en un momento futuro. Aquí establecí la expiración de la cookie en un día, seguramente en un ejemplo real vamos a establecerla en un valor mucho mayor, probablemente un año.

Para acceder a esta acción, simplemente agregamos en el header de nuestro sitio los accesos para cada una de las culturas en cuestión. Nuevamente en un caso de implementación real haríamos algo más estético, pero les pido que en lo posible no sean todas las banderas directamente que mucho no me gusta 😛

CulturaManual - AccesosCambioDeCultura
Links para el establecimiento de la cultura en cookie

Y ya está casi todo hecho, salvo usar la cookie. Dónde lo hacemos, para que en todos los accesos a nuestra aplicación podamos estar seguros de que la cultura se establece de forma correcta en caso de que sea necesario? Una alternativa puede ser el Global.asax, implementando el método Application_BeginRequest. También podemos hacerlo de otra forma, como un filtro de acción usado en un BaseController. Pero el concepto que vamos a aplicar es el mismo:

CulturaManual - RecuperarCookie
Recuperamos la cookie y si existe establecemos la cultura

Y con esto ya tendríamos todo listo. Si probamos acceder a nuestro sitio inicialmente tendremos activada la cultura automática tomada del navegador, pero cuando la cambiemos a través del acceso creado para ello se creará la cookie y tendremos la nueva cultura establecida para todos los request que realice el usuario sobre nuestro sitio:

CulturaManual - ResultadoFinal
Resultado luego de haber establecido la cultura y navegado por el sitio

En esta última imagen, lo que hice fue acceder por defecto en español, cambiar a inglés la cultura, ir a la acción Contact y validar que efectivamente se mantiene la elección del usuario luego de navegar por distintas páginas.

Y con esto ya tenemos establecida la cultura del navegador automática dependiendo del usuario, pero con la posibilidad de que el mismo decida cambiarla. Como mencionaba en uno de los puntos dependiendo de cómo sea nuestro sitio habrá que realizar variantes. Una es si tenemos usuarios logueados a través de una cuenta, donde la información de cultura será parte del perfil del mismo. Otra variante puede ser si queremos que la elección de la cultura forme parte de la URL de acceso, algo que desde el enfoque de SEO es una buena práctica.

Gracias por leer!

Anuncios

3 comentarios en “Cómo cambiar la cultura manualmente en ASP.NET MVC?

  1. Hola Diego,

    Muchas gracias por este brillante post, ya lo he probado y todo genial!!! Como el resto de entradas respecto a Asp.NET MVC vuelve a ser una explicación fantástica.

    Gracias de nuevo y seguiremos atentos al blog para seguir aprendiendo!

    Me gusta

    • Hola Carlos, por nada. Me alegro que te haya servido.
      Cualquier tema que tengas dudas o algo que te parezca que valga la pena me lo haces saber, y veo si puedo armar una entrada con ello. Siempre me terminan dando alguna buena idea!

      Saludos!

      Me gusta

Responder

Introduce tus datos o haz clic en un icono para iniciar sesión:

Logo de WordPress.com

Estás comentando usando tu cuenta de WordPress.com. Cerrar sesión / Cambiar )

Imagen de Twitter

Estás comentando usando tu cuenta de Twitter. Cerrar sesión / Cambiar )

Foto de Facebook

Estás comentando usando tu cuenta de Facebook. Cerrar sesión / Cambiar )

Google+ photo

Estás comentando usando tu cuenta de Google+. Cerrar sesión / Cambiar )

Conectando a %s