I'm creating a simple, multilingual website using ASP.NET 4.6, C#, OWIN pipeline on IIS (Microsoft.Owin.Host.SystemWeb
), lots of asynchronous method calls and standard, global resource files (*.resx
in App_GlobalResources
). The website uses MVC5, WebAPI2 and Autofac as dependency resolver.
I can't correctly change the locale/culture of generated pages, because asynchronous methods use multiple threads per request and I can't find a way to set Thread.Current[UI]Culture
for every thread associated with given request as those properties aren't synchronized. I would also like to stay with clean code without "async/await culture configuration" messing with useful code.
Startup.cs
public void Configuration(IAppBuilder app)
{
...
app.UseAutofacMiddleware(container);
app.UseAutofacMvc();
app.UseAutofacWebApi(httpConfiguration);
app.UseWebApi(httpConfiguration);
...
app.Use(async (ctx, next) =>
{
/* in production, detect based on current URL and/or cookie */
var culture = new CultureInfo("pl_PL");
CultureInfo.CurrentCulture = CultureInfo.CurrentUICulture = culture;
await next.Invoke();
});
}
SampleController.cs
public async Task<ActionResult> SayHello()
{
// returns pl_PL message
var msgA = Resources.Messages.HelloWorld;
await someService.doSthAsync();
// returns system default (en_US) message
var msgB = Resources.Messages.HelloWorld;
return Content(msgA + " - " + msgB);
}
[AspNet]SynchronizationContext
as suggested in this SO answer? If that is the case how should I do that?What about using the Owing Globalization Library, it seems like it was created just for this purpose.
You can still use your resx to localize your resources, and it has great customization capabilities:
public void Configuration(IAppBuilder app)
{
...
app.UseGlobalization(new OwinGlobalizationOptions("en-US",true)
.DisablePaths("Content", "bundles")
.Add("fr-FR", true).AddCustomSeeker(new CultureFromPreferences()));
}
I have tested the use of async/await and the culture is preserved:
public async Task<ActionResult> About()
{
var msgA = Resources.Resources.About;
await Task.Delay(1000);
var msgB = Resources.Resources.About;
ViewBag.Message = msgA + " - " + msgB;
return View();
}
Note: I'm not the author of the library, I happen to have used it before.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With