0

I have the following custom middleware that sets the current culture info.

At the end, I want to redirect to another page, but my code isn't working.

In use, it seems like the execution stop's after invoking my middleware.

It currently uses context.Response.Redirect(redir);.

Middleware, SetCulture.cs:

public class SetCulture
{
    private readonly RequestDelegate _next;

    public SetCulture(RequestDelegate next)
    {
        _next = next;
    }

    public async Task Invoke(HttpContext context, IAssetsConfigAccessor config)
    {
        string name = string.Empty;

        if (context.Request.Query.Count > 0 && context.Request.Query.ContainsKey("culture"))
        {
            context.Session.SetString("Culture", context.Request.Query["culture"]);
            name = context.Request.Query["culture"];
        }
        else if (context.Session.Keys.Contains("Culture"))
        {
            name = context.Session.GetString("Culture");
        }
        else if (context.Request.Cookies.ContainsKey("Culture"))
        {
            name = context.Request.Cookies["Culture"];
        }
        else
        {
            ISite site = await config.GetSiteAsync();

            if (site.Cultures.Count() > 0)
            {
                ISiteCulture siteCult = site.Cultures.SingleOrDefault(c => c.IsDefault);

                if (!siteCult.Null())
                {
                    name = siteCult.Culture.Name;
                }
                else
                {
                    name = Thread.CurrentThread.CurrentCulture.Name;
                }

                context.Session.SetString(AssetsStatics.CacheCurrentCultureName, name);
            }
            else
            {
                ICulture tmp = await config.GetCultureAsync(false);
                name = tmp.Name;
            }
        }

        CultureInfo cult = new CultureInfo(name);
        CultureInfo.CurrentCulture = cult;
        CultureInfo.CurrentUICulture = cult;

        string redir = context.Request.Query.ContainsKey("returnUrl") ? context.Request.Query["returnUrl"] : "/";

        context.Response.Redirect(redir);

        await _next.Invoke(context);
    }
}

How I configure it in Program.cs:

app
    .UseWhen(cntx => cntx.Request.Path.StartsWithSegments("/Assets/SetCulture")
                     && cntx.Request.Query.ContainsKey("Culture"), 
             bld => { bld.UseMiddleware<SetCulture>(); });
8
  • 1
    Aren't you getting a "Too many redirects" error? Your redirect is not inside any IF statement, so it will redirect 100% of the requests that go through the middleware, including the redirects you make. The redirect statement must be conditioned or it will be neverending. Commented Jun 25, 2024 at 1:37
  • @JoséRamírez ok I didn't know I had to since I configure it using UseWhen, with the following code: .UseWhen(cntx => cntx.Request.Path.StartsWithSegments("/Assets/SetCulture") && cntx.Request.Query.ContainsKey("Culture"), bld =>. So it will only be invoked when a specific url is requested. when I debug it only hits breakpoint inside middleware if I type in the right url Commented Jun 25, 2024 at 2:30
  • 1
    Ok, UseWhen is acceptable too. Now I see another problem: Setting CultureInfo.CurrentCulture + 1 doesn't work as you intend. You're setting the culture of the thread that is about to redirect the user. This is not setting the culture of the "future request product of the redirect". Commented Jun 25, 2024 at 2:52
  • 1
    Normally, culture-setting middleware set the culture and don't redirect because redirecting makes the current thread not the thread that will do the actual work. Normally you set the culture based on an HTTP header or a cookie but don't redirect. Redirecting makes setting the culture a wasted effort. Commented Jun 25, 2024 at 2:54
  • 1
    Ah ok. I see. Don't call _next(). Just return; after redirecting. The .Redirect() method sets a redirect result object that the output formatter translates to an HTTP redirect response. If you call _next(), other middleware might return other responses that invalidate your redirect. Commented Jun 25, 2024 at 3:11

0

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.