{
  "$type": "site.standard.document",
  "canonicalUrl": "https://johnnyreilly.com/posts/asp-net-authentication-hard-coding-claims",
  "description": "The DevelopmentModeAuthenticationHandler allows ASP.NET Core developers to hard code user authentication claims during development, easing testing.",
  "path": "/posts/asp-net-authentication-hard-coding-claims",
  "publishedAt": "2019-08-02T00:00:00.000Z",
  "site": "at://did:plc:yy3apqjlms24kso7ahn7lbmb/site.standard.publication/3mova7c4nho2b",
  "tags": [
    "asp.net",
    "auth"
  ],
  "textContent": "This post demonstrates how you can hard code user authentication claims in ASP.NET Core; a useful technique to facilate testing during development.\n\n\n\nI was recently part of a hackathon team that put together an API in just 30 hours. We came second. (Not bitter, not bitter...)\n\nWe were moving pretty quickly during the hackathon and, when we came to the end of it, we had a working API which we were able to demo. The good news is that the API is going to graduate to be a product! We're going to ship this. Before we can do that though, there's a little tidy up to do.\n\nThe first thing I remembered / realised when I picked up the codebase again, was the shortcuts we'd made on the developer experience. We'd put the API together using ASP.Net Core. We're handling authentication using JWTs which is nicely supported. When we're deployed, an external facing proxy calls our application with the appropriate JWT and everything works as you'd hope.\n\nThe question is, what's it like to develop against this on your laptop? Getting a JWT for when I'm debugging locally is too much friction. I want to be able to work on the problem at hand, going away to get a JWT each time is a timesuck. So what to do? Well, during the hackathon, we just commented out [Authorize] attributes and hardcoded user ids in our controllers. This works, but it's a messy developer experience; it's easy to forget to uncomment things you've commented and break things. There must be a better way.\n\nThe solution I landed on was this: in development mode (which we only use whilst debugging) we hardcode an authenticated user. The way our authentication works is that we have a claim on our principal called something like \"our-user-id\", the value of which is our authenticated user id. So in the ConfigureServices method of our Startup.cs we have a conditional authentication registration like this:\n\nAs you can see, we're using a special DevelopmentModeAuthenticationHandler authentication scheme in development mode, instead of JWT. As we register that, we declare the user id that we want to use. Whenever the app runs using the DevelopmentModeAuthenticationHandler auth, all requests will arrive using a principal with an \"our-user-id\" claim with a value of \"this-is-a-user-id\" (or whatever you've set it to.)\n\nThe DevelopmentModeAuthenticationHandler looks like this:\n\nNow, developing locally is frictionless! We don't comment out [Authorize] attributes, we don't hard code user ids in controllers.",
  "title": "ASP.NET Core authentication: hard-coding a claim in development"
}