1
\$\begingroup\$

My ASP.NET application references a classlib that contains the business logic, where I need to have access to the IIdentity of the "current user".

In ASP.NET controller it is easy, outside it is not possible out of the box in a async model (I did not find any equivalent of Thread.CurrentPrincipal.Identity).

What do you think of that :

In the classlib :

public class SecurityContextHolder
{
    private static readonly AsyncLocal<IIdentity> asyncLocal = new();

    public static IIdentity? CurrentIdentity
    {
        get { return asyncLocal.Value; }
        set { asyncLocal.Value = value!; }
    }
    // Value of a `AsyncLocal<T>` is specific to a given ExecutionContext
}

In the webapi : a new middleware :

public class SecurityContextHolderMiddleware
{
    private readonly RequestDelegate _next;

    public SecurityContextHolderMiddleware(RequestDelegate next) => this._next = next;

    public async Task InvokeAsync(HttpContext context)
    {
        SecurityContextHolder.CurrentIdentity = context.User.Identity;
        await _next(context);
    }
}

registered after UseAuthentication in the Configure method :

app.UseRouting();

app.UseAuthentication();

app.UseAuthorization();

app.UseMiddleware<SecurityContextHolderMiddleware>();

Then, SecurityContextHolder.CurrentIdentity can be called anywhere and returns the identity of the caller (assuming authentification is properly configured of course).

Thanks for telling me what do you think.

\$\endgroup\$
2
  • \$\begingroup\$ Is this code already implemented and working? We only review working code on code review. If this code is currently in design you might want to ask this question on Software Engineering instead. How are you calling the Business Logic? Can you pass the user ID as a parameter instead? \$\endgroup\$
    – pacmaninbw
    Jun 10 at 13:46
  • \$\begingroup\$ Yes, it works. It allows, for example, to access the user identity in a constructor of an object created from request body by aspnet. If this object has a [Required] Username property, it can be assigned and then pass validation. Audit logic also need to have access to caller identity. Calls to the classlib are simple method calls, but I cannot add a IIdentity parameter to every method. \$\endgroup\$
    – Gengis
    Jun 10 at 18:21

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.