d00d
d00d

Reputation: 763

Dynamically set the culture by user preference does not work

I followed this tutorial to provide users of my blazor server-side app with a selector where they can switch between two languages de and fr. I followed the tutorial step-by-step and when I click the culture selector, I am being redirected but the CurrentCulture is not changed but remains the standard Culture of my system (which is de).

These are my components:

CultureSelector as is from the link above.

Added to the Navmenu.razor:

<div class="bottom-row px-4">
    <CultureSelector />
</div>

So what I have is a Request.razor file and resource files for German and French language:

enter image description here

Snippet from Request.razor:

@using Microsoft.Extensions.Configuration
@using System.Globalization
@inject IStringLocalizer<Request> Localizer

<div class="col-md-1" style="border: 1px solid;">
    @Localizer["Name"]
</div>

The language selector is located in my sidebar and I have the CurrentCulture printed in the Request.razor:

<p>
    <b>CurrentCulture</b>: @CultureInfo.CurrentCulture
</p>

which looks like that:

enter image description here

I have the CultureController as is from the tutorial (only changed the cultures to de-De and fr-FR)

I also added the code from the tutorial to the Startup.Configure section:

var supportedCultures = new[] { "de-DE", "fr-FR" };
var localizationOptions = new RequestLocalizationOptions()
    .SetDefaultCulture(supportedCultures[0])
    .AddSupportedCultures(supportedCultures)
    .AddSupportedUICultures(supportedCultures);

app.UseRequestLocalization(localizationOptions);

I also update the _Host.cshtml file according to the tutorial:

enter image description here

So far so good. When I change the language to French, the controller action is triggered with the correct parameters:

enter image description here

But as soon as the page reload is done, CurrentCulture is set to de-DE and the German language is used for my view instead of French.

Not sure if its related but when I have a look at the GET request after I switched the language to French, there's a Set-Cookie attribute that sets the de-DE culture after the reload is initiated.

enter image description here

Is there anything that I'm missing right now?

Upvotes: 3

Views: 1826

Answers (2)

d00d
d00d

Reputation: 763

Oh my goodness, I just watched a YT video of a guy doing the same thing and he put emphasize on that it can be important to put the code right between app.UseStaticFiles() and app.UseRouting(). I had it placed after the app.UseEndpoints() call. When I moved it accordingly, the culture switch suddenly worked.

public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{                 
            app.UseStaticFiles();

            var supportedCultures = new[] { "de-DE", "fr-FR" };
            var localizationOptions = new RequestLocalizationOptions()
                .SetDefaultCulture(supportedCultures[0])
                .AddSupportedCultures(supportedCultures)
                .AddSupportedUICultures(supportedCultures);

            app.UseRequestLocalization(localizationOptions);
                
            app.UseRouting();

            app.UseEndpoints(endpoints =>
            {
                endpoints.MapControllers();
                endpoints.MapBlazorHub();
                endpoints.MapFallbackToPage("/_Host");
            });

        }
    }

Upvotes: 2

Nicola Biada
Nicola Biada

Reputation: 2800

You need to add the IsEssential option to your cookie, like:

this.HttpContext.Response.Cookies.Append(
            CookieRequestCultureProvider.DefaultCookieName,
            CookieRequestCultureProvider.MakeCookieValue(
                new RequestCulture(
                    CultureInfo.CurrentCulture,
                    CultureInfo.CurrentUICulture)),
            new CookieOptions
            {
                IsEssential = true,
                Expires = DateTimeOffset.UtcNow.AddYears(1),
                SameSite = SameSiteMode.Lax
            });

Upvotes: 1

Related Questions