Page 12 - MSDN Magazine, September 2017
P. 12
Another interesting aspect of the previous example is that an explicit user name is not strictly required. Any claim, regardless of the declared type, can be used to name the user. The following code
snippet shows another equivalent way to have a new identity object:
var identity = new ClaimsIdentity(claims, CookieAuthenticationDefaults.AuthenticationScheme, "Nickname",
ClaimTypes.Role);
The new identity has “Cookies” as the authentication scheme and Nickname is the name of the claim in the provided list to be used to provide the name of the user. Role, instead, is the name of the claim in the same list determining the role. If not specified, the last two parameters default to ClaimTypes.Name and ClaimTypes.Role. Finally, you create the principal from the identity. It’s worth noting, though, that a principal may have multiple identities. If it sounds weird, think that different areas of the same application might need different information to authenticate the user in much the same way an ID is required to identify yourself at some hotel desks and an electronic key to get into the elevator. The ClaimsPrincipal class has both an Identities property (a collection) and an Identity prop- erty. The latter is only a reference to the first item in the collection.
External Authentication
ASP.NET Core supports external authentication via identity pro- viders from the ground up. Most of the time, all you do is install the appropriate NuGet package for the task. To rely on Twitter for authenticating users, you bring in the Microsoft.AspNetCore.Au-
thentication.Twitter package and install the related middleware:
app.UseTwitterAuthentication(new TwitterOptions()
When the external provider returns, a temporary cookie is created using the ExternalCookie scheme. Having set the redirect path appropriately, you have a chance to inspect the principal returned by Twitter and edit it further:
var props = new AuthenticationProperties RedirectUri = "/account/external"
};
To complete the workflow you also need to sign in in the cookies scheme and sign out of temporary scheme (ExternalCookie):
public async Task<IActionResult> External() var principal = await HttpContext
.Authentication
.AuthenticateAsync("ExternalCookie"); // Edit the principal
...
await HttpContext.Authentication.SignInAsync("Cookies", principal);
await HttpContext.Authentication.SignOutAsync("ExternalCookie "); }
ExternalCookie, as well as cookies, are just internal identifiers and can be renamed as long as they remain consistent through- out the application.
Wrapping Up
In ASP.NET Core many things seem to be radically different, but in the end most of the concepts you might know from ASP.NET remain unchanged. You still need to have an authentication cookie created, and you can still control the name of the cookie and the expiration date. External authentication is supported and login pages have the same structure as before. However, configuration and underlying working of the authentication infrastructure are different, while retaining their previous flexibility.
Everything stated in this article refers to ASP.NET Core 1.x. There are a few things that will work differently in ASP.NET Core 2.0. In particular, authentication middleware is now exposed as services and must be configured on ConfigureServices:
services.AddCookieAuthentication(options => {
Options.LoginPath = new PathString("/Account/Login"), options.AutomaticAuthenticate = true, options.AutomaticChallenge = true, options.AuthenticationScheme = "Cookies",
... });
In the Configure method of the Startup class of ASP.NET Core 2.0 applications, you just declare your intention to use authentication services without any further options:
app.UseAuthentication();
Also note that the SignInAsync method you use in your code to create the authentication cookie is also exposed from the HttpContext object directly, instead of passing through an intermediate Authentication property as shown in the last code snippet for ASP.NET Core 1.x. n
Dino Esposito is the author of “Microsoft .NET: Architecting Applications for the Enterprise” (Microsoft Press, 2014) and “Modern Web Applications with ASP.NET” (Microsoft Press, 2016). A technical evangelist for the .NET and Android platforms at JetBrains, and frequent speaker at industry events worldwide, Esposito shares his vision of software at software2cents@wordpress.com and on Twitter: @despos.
thanks to the following Microsoft technical expert for reviewing this article: Chris Ross
{
AuthenticationScheme = "Twitter", SignInScheme = "Cookies", ConsumerKey = "...", ConsumerSecret = "..."
});
The SignInScheme property is the identifier of the authentica- tion middleware that will be used to persist the resulting identity. In the example, an authentication cookie will be used. To see its
effects, you first add a controller method to call into Twitter:
public async Task TwitterAuth()
{
var props = new AuthenticationProperties {
RedirectUri = "/" };
await HttpContext.Authentication.ChallengeAsync("Twitter", props); }
Next, once Twitter has successfully authenticated the user, the
SignInScheme property instructs the application on what to do
next. A value of “Cookies” is acceptable if you want a cookie out of
the claims returned by the external provider (Twitter, in the exam-
ple). If you want to review and complete the information through,
say, an intermediate form, then you have to break the process in
two, introducing a temporary sign-in scheme. In addition to the
standard cookie middleware you have the following:
app.UseCookieAuthentication(new CookieAuthenticationOptions
{ AuthenticationScheme = "ExternalCookie", AutomaticAuthenticate = false
});
app.UseTwitterAuthentication(new TwitterOptions
{
AuthenticationScheme = "Twitter", SignInScheme = "ExternalCookie"
});
8 msdn magazine
Cutting Edge