I've been inspecting the new bits of ASP.NET MVC 5
and trying to make sense of the new paradigm that me, as .NET
developer, is going to be working in. This new shift will probably be
known as the Open Web Inerface for .NET era or more succinctly the OWIN era. OWIN is a middleware implementation for .NET that
will allow developers, like me, to hook into a deeper pipeline to
perform tasks like logging, exception handling, authentication, and more
that my imagination can't contemplate just yet. This post isn't about OWIN and the possibilities, but it is about the new authentication found in ASP.NET MVC 5.
Registering the Middleware
I started by creating a new ASP.NET MVC 5 project using the existing templates that come with Visual Studio 2013 and picked the individual user accounts
option for authentication. This means my user information will be
stored locally in a data storage. The default data storage is SQL Server. Looking in the App_Start folder, I find Startup.Auth.cs. The file contents looks like this:
public partial class Startup
{
// For more information on configuring authentication, please visit http://go.microsoft.com/fwlink/?LinkId=301864
public void ConfigureAuth(IAppBuilder app)
{
// Enable the application to use a cookie to store information for the signed in user
app.UseCookieAuthentication(new CookieAuthenticationOptions
{
AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
LoginPath = new PathString("/Account/Login")
});
// Use a cookie to temporarily store information about a user logging in with a third party login provider
app.UseExternalSignInCookie(DefaultAuthenticationTypes.ExternalCookie);
// Uncomment the following lines to enable logging in with third party login providers
//app.UseMicrosoftAccountAuthentication(
// clientId: "",
// clientSecret: "");
//app.UseTwitterAuthentication(
// consumerKey: "",
// consumerSecret: "");
//app.UseFacebookAuthentication(
// appId: "",
// appSecret: "");
//app.UseGoogleAuthentication();
}
}
I also found this in the web.config of the application.
<system.web>
<authentication mode="None" />
<compilation debug="true" targetFramework="4.5" />
<httpRuntime targetFramework="4.5" />
</system.web>
<system.webServer>
<modules>
<remove name="FormsAuthenticationModule" />
</modules>
</system.webServer>
With these two files, I realize that the old forms authentication model has been replaced by the OWIN
pipeline. Diving deeper into the calls found in the startup app, I also
realize that each of the calls just registers a new middleware class
to handle that particular auth provider. This is the google
registration.
public static IAppBuilder UseGoogleAuthentication(this IAppBuilder app, GoogleAuthenticationOptions options)
{
if (app == null)
throw new ArgumentNullException("app");
if (options == null)
throw new ArgumentNullException("options");
app.Use((object) typeof (GoogleAuthenticationMiddleware), (object) app, (object) options);
return app;
}
nothing really fancy here, just instantiating the middle ware, then
registering it with the application. The next step is to use the
middleware.
AccountController
The AccountController is where ASP.NET MVC 5 gets confusing, because there is the noise introduced by the UserManager implementation. Ignore this, it is simply a Entity Framework implementation allowing you to save user information. I would most likely remove this, as I don't use Entity Framework myself.
The more interesting part of the AccountController is the IAuthenticationManager property.
private IAuthenticationManager AuthenticationManager
{
get
{
return HttpContext.GetOwinContext().Authentication;
}
}
The IAuthenticationManager is being pulled from the OWIN
implementation built on top of ASP.NET. When I start looking for uses
of this property, I find the next generation of the things I've grown
fond of with the FormsAuthentication class: SignIn and SignOut.
// Sign In
AuthenticationManager.SignIn(new AuthenticationProperties() { IsPersistent = isPersistent }, identity);
// Sign Out
AuthenticationManager.SignOut(DefaultAuthenticationTypes.ExternalCookie);
The interesting part, is now I can create cookies with the
distinction of whether they are internally generated, or generated by a
third party provider: Twitter, Facebook, or Google.
The final piece of this is the ChallengeResult class, which looks to be optional to implement.
private class ChallengeResult : HttpUnauthorizedResult
{
public ChallengeResult(string provider, string redirectUri) : this(provider, redirectUri, null)
{
}
public ChallengeResult(string provider, string redirectUri, string userId)
{
LoginProvider = provider;
RedirectUri = redirectUri;
UserId = userId;
}
public string LoginProvider { get; set; }
public string RedirectUri { get; set; }
public string UserId { get; set; }
public override void ExecuteResult(ControllerContext context)
{
var properties = new AuthenticationProperties() { RedirectUri = RedirectUri };
if (UserId != null)
{
properties.Dictionary[XsrfKey] = UserId;
}
context.HttpContext.GetOwinContext().Authentication.Challenge(properties, LoginProvider);
}
}
The only thing it does, is make a call to the IAuthenticationManager.Challenge to trigger the challenge built into the OWIN pipeline. This will redirect to a login page for the external auth providers.
Summary
All I need to get authentication working using OWIN is the following:
- The contents of App_Start/Startup.Auth.cs.
- The **IAuthenticationManager*.
- Optionally, ChallengeResult, which is a nice helper Result.
How they work together:
- The authentication providers are registered with the app in startup.
- Cookies are handled by OWIN and the middleware.
- Each external auth provider's login challenge can be triggered using the ChallengeResult.
- Cookies are managed using IAuthenticationManager.SignIn and IAuthenticationManager.SignOut.
- Auth is based on Claims.
So after dissecting the start template, I found out what is basically important and what is just "helpful"
stuff Microsoft gives me out of the box. There are definitely things
that are still foggy to me, but I think I have a good understanding now
of what it takes to do authentication in the OWIN era of ASP.NET MVC.
0 comments:
Post a Comment
thanks for your comment!