diff --git a/src/Umbraco.Core/Security/AuthenticationExtensions.cs b/src/Umbraco.Core/Security/AuthenticationExtensions.cs index 9df84cc2b1..bd0891cd1a 100644 --- a/src/Umbraco.Core/Security/AuthenticationExtensions.cs +++ b/src/Umbraco.Core/Security/AuthenticationExtensions.cs @@ -1,8 +1,10 @@ using System; using System.Collections; +using System.Collections.Concurrent; using System.Collections.Generic; using System.Collections.Specialized; using System.ComponentModel; +using System.Globalization; using System.Linq; using System.Net.Http; using System.Net.Http.Headers; @@ -458,5 +460,23 @@ namespace Umbraco.Core.Security return ticket; } + + /// + /// Ensures that the thread culture is set based on the back office user's culture + /// + /// + internal static void EnsureCulture(this IIdentity identity) + { + if (identity is UmbracoBackOfficeIdentity umbIdentity && umbIdentity.IsAuthenticated) + { + Thread.CurrentThread.CurrentUICulture = + Thread.CurrentThread.CurrentCulture = + UserCultures.GetOrAdd(umbIdentity.Culture, s => new CultureInfo(s)); + } + } + /// + /// Used so that we aren't creating a new CultureInfo object for every single request + /// + private static readonly ConcurrentDictionary UserCultures = new ConcurrentDictionary(); } -} \ No newline at end of file +} diff --git a/src/Umbraco.Core/Security/BackOfficeCookieAuthenticationProvider.cs b/src/Umbraco.Core/Security/BackOfficeCookieAuthenticationProvider.cs index 3ff1266c6b..1a3b9f54ee 100644 --- a/src/Umbraco.Core/Security/BackOfficeCookieAuthenticationProvider.cs +++ b/src/Umbraco.Core/Security/BackOfficeCookieAuthenticationProvider.cs @@ -102,7 +102,8 @@ namespace Umbraco.Core.Security /// public override async Task ValidateIdentity(CookieValidateIdentityContext context) { - EnsureCulture(context); + //ensure the thread culture is set + context?.Identity?.EnsureCulture(); await EnsureValidSessionId(context); @@ -120,21 +121,5 @@ namespace Umbraco.Core.Security if (_appCtx.IsConfigured && _appCtx.IsUpgrading == false) await SessionIdValidator.ValidateSessionAsync(TimeSpan.FromMinutes(1), context); } - - private void EnsureCulture(CookieValidateIdentityContext context) - { - var umbIdentity = context.Identity as UmbracoBackOfficeIdentity; - if (umbIdentity != null && umbIdentity.IsAuthenticated) - { - Thread.CurrentThread.CurrentCulture = - Thread.CurrentThread.CurrentUICulture = - UserCultures.GetOrAdd(umbIdentity.Culture, s => new CultureInfo(s)); - } - } - - /// - /// Used so that we aren't creating a new CultureInfo object for every single request - /// - private static readonly ConcurrentDictionary UserCultures = new ConcurrentDictionary(); } -} \ No newline at end of file +} diff --git a/src/Umbraco.Web/UmbracoModule.cs b/src/Umbraco.Web/UmbracoModule.cs index 99043143a7..29d0de968d 100644 --- a/src/Umbraco.Web/UmbracoModule.cs +++ b/src/Umbraco.Web/UmbracoModule.cs @@ -509,6 +509,13 @@ namespace Umbraco.Web } }; + app.PostAuthenticateRequest += (sender, e) => + { + var httpContext = ((HttpApplication)sender).Context; + //ensure the thread culture is set + httpContext.User?.Identity?.EnsureCulture(); + }; + app.PostResolveRequestCache += (sender, e) => { var httpContext = ((HttpApplication)sender).Context;