OWIN Authentication Middleware Architecture
In Katana (Microsoft’s OWIN framework and host implementation) there is an abstraction for creating middleware that does authentication. Microsoft has defined base class called AuthenticationMiddleware and AuthenticationHandler (among other helper classes) and these work to process requests to establish the identity of the user. Microsoft has also defined several derived classes that implement various authentication schemes, such as Basic authentication, cookie-based (comparable to forms authentication in ASP.NET), and external authentication mechanisms (like google, facebook, microsoft accounts, etc.).
The processing model for authentication middleware is as such. In the application’s startup configuration authentication middleware would be registered (much like any other middleware). The AuthenticationMiddleware base class provides the implementation of Invoke (the required middleware “interface”), and the derived implementation overrides CreateHandler to return a new instance of an AuthenticationHandler. The authentication handler is created per-request and it then overrides various base class methods depending on the nature of the authentication being performed. The four main methods (with their purpose) are:
AuthenticateCoreAsync: This is used to look for incoming tokens on the request and convert them into an AuthenticationTicket (which is a container for the caller’s identity). This returns null if there is no token or the token is invalid. This is invoked during pre-processing in the OWIN pipeline if the authentication middleware is considered “active”. When marked as “passive” then it’s invoked only when it’s needed (typically by the application layer).
InvokeAsync: This is invoked during pre-processing in the OWIN pipeline. The purpose of this method is to determine if the incoming request is an authentication callback of some sort (like an OAuth callback, for example). If this is a callback request, the implementation should process the request, log the user in (via some other middleware like the cookie based middleware), issue a redirect, and then return true indicating that no other middleware should be invoked (thus short-circuiting the middleware pipeline). If the request is not a callback, then simply return false and the rest of the pipeline is executed.
ApplyResponseGrantAsync: This is invoked during post-processing in the OWIN pipeline. It is used to modify the response if needed to either issue a token or clear a token. This will only be appropriate if earlier in the OWIN pipeline the client had provided credentials in some way or requested to sign-out.
ApplyResponseChallengeAsync: This is invoked during post-processing in the OWIN pipeline. The purpose is to issue a challenge back to the caller if the application has issued a 401 (unauthorized). For some authentication protocols this means a “WWW-Authenticate” response header, but for other protocols this means issuing a 302 redirect.
Not all of these methods make sense for all types of authentication. This is the breakdown for the built-in authentication middleware:
The pattern I see here is that there are two styles: local token processing and external authentication. It feels a bit cumbersome to have both of these styles mixed into a single base class with such mixed semantics. Oh well.
If you need to build your own authentication middleware then it can be confusing which methods you need to implement (from the AuthenticationHandler base class). Hopefully this breakdown helps inform any custom implementation you need to build (such as Basic, WS-Federation, SAML2-P, OpenID Connect or any others that aren’t provided by Katana).