React to AuthN changes

This commit is contained in:
Hao Kung 2015-03-02 16:39:01 -08:00
parent 747f4137c6
commit 3aaa628365
27 changed files with 534 additions and 462 deletions

View File

@ -2,10 +2,11 @@
using System.Security.Claims;
using System.Security.Principal;
using System.Threading.Tasks;
using Microsoft.AspNet.Authentication;
using Microsoft.AspNet.Identity;
using Microsoft.AspNet.Mvc;
using Microsoft.AspNet.Mvc.Rendering;
using Microsoft.AspNet.Security;
using Microsoft.AspNet.Authorization;
namespace IdentitySample.Models
{
@ -29,7 +30,7 @@ namespace IdentitySample.Models
public IActionResult Login(string returnUrl = null)
{
ViewBag.ReturnUrl = returnUrl;
ViewBag.LoginProviders = SignInManager.GetExternalAuthenticationTypes().ToList();
ViewBag.LoginProviders = SignInManager.GetExternalAuthenticationSchemes().ToList();
return View();
}
@ -164,7 +165,7 @@ namespace IdentitySample.Models
ViewBag.ReturnUrl = returnUrl;
ViewBag.LoginProvider = info.LoginProvider;
// REVIEW: handle case where email not in claims?
var email = info.ExternalIdentity.FindFirstValue(ClaimTypes.Email);
var email = info.ExternalPrincipal.FindFirstValue(ClaimTypes.Email);
return View("ExternalLoginConfirmation", new ExternalLoginConfirmationViewModel { Email = email });
}
}
@ -176,7 +177,7 @@ namespace IdentitySample.Models
[ValidateAntiForgeryToken]
public async Task<IActionResult> ExternalLoginConfirmation(ExternalLoginConfirmationViewModel model, string returnUrl = null)
{
if (User.Identity.IsAuthenticated)
if (User.IsSignedIn())
{
return RedirectToAction("Index", "Manage");
}
@ -414,7 +415,7 @@ namespace IdentitySample.Models
private async Task<ApplicationUser> GetCurrentUserAsync()
{
return await UserManager.FindByIdAsync(Context.User.Identity.GetUserId());
return await UserManager.FindByIdAsync(Context.User.GetUserId());
}
private IActionResult RedirectToLocal(string returnUrl)

View File

@ -2,9 +2,9 @@
using System.Security.Principal;
using System.Threading.Tasks;
using IdentitySample.Models;
using Microsoft.AspNet.Authorization;
using Microsoft.AspNet.Identity;
using Microsoft.AspNet.Mvc;
using Microsoft.AspNet.Security;
namespace IdentitySample
{
@ -300,7 +300,7 @@ namespace IdentitySample
return View("Error");
}
var userLogins = await UserManager.GetLoginsAsync(user);
var otherLogins = SignInManager.GetExternalAuthenticationTypes().Where(auth => userLogins.All(ul => auth.AuthenticationType != ul.LoginProvider)).ToList();
var otherLogins = SignInManager.GetExternalAuthenticationSchemes().Where(auth => userLogins.All(ul => auth.AuthenticationScheme != ul.LoginProvider)).ToList();
ViewBag.ShowRemoveButton = user.PasswordHash != null || userLogins.Count > 1;
return View(new ManageLoginsViewModel
{
@ -317,7 +317,7 @@ namespace IdentitySample
{
// Request a redirect to the external login provider to link a login for the current user
var redirectUrl = Url.Action("LinkLoginCallback", "Manage");
var properties = SignInManager.ConfigureExternalAuthenticationProperties(provider, redirectUrl, User.Identity.GetUserId());
var properties = SignInManager.ConfigureExternalAuthenticationProperties(provider, redirectUrl, User.GetUserId());
return new ChallengeResult(provider, properties);
}
@ -331,7 +331,7 @@ namespace IdentitySample
{
return View("Error");
}
var info = await SignInManager.GetExternalLoginInfoAsync(User.Identity.GetUserId());
var info = await SignInManager.GetExternalLoginInfoAsync(User.GetUserId());
if (info == null)
{
return RedirectToAction("ManageLogins", new { Message = ManageMessageId.Error });
@ -353,7 +353,7 @@ namespace IdentitySample
private async Task<bool> HasPhoneNumber()
{
var user = await UserManager.FindByIdAsync(User.Identity.GetUserId());
var user = await UserManager.FindByIdAsync(User.GetUserId());
if (user != null)
{
return user.PhoneNumber != null;
@ -375,7 +375,7 @@ namespace IdentitySample
private async Task<ApplicationUser> GetCurrentUserAsync()
{
return await UserManager.FindByIdAsync(Context.User.Identity.GetUserId());
return await UserManager.FindByIdAsync(Context.User.GetUserId());
}
private IActionResult RedirectToLocal(string returnUrl)

View File

@ -3,7 +3,7 @@
"DefaultAdminPassword": "YouShouldChangeThisPassword1!",
"Data": {
"IdentityConnection": {
"Connectionstring": "Server=(localdb)\\mssqllocaldb;Database=IdentityMvc-1-7-15;Trusted_Connection=True;MultipleActiveResultSets=true"
"Connectionstring": "Server=(localdb)\\mssqllocaldb;Database=IdentityMvc-2-20-15-3;Trusted_Connection=True;MultipleActiveResultSets=true"
}
},
"Identity": {

View File

@ -1,8 +1,8 @@
using Microsoft.AspNet.Http.Security;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using Microsoft.AspNet.Http.Authentication;
using Microsoft.AspNet.Identity;
using Microsoft.AspNet.Mvc.Rendering;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
namespace IdentitySample.Models
{

View File

@ -74,7 +74,7 @@
<div id="socialLoginList">
<p>
@foreach (AuthenticationDescription p in ViewBag.LoginProviders) {
<button type="submit" class="btn btn-default" id="@p.AuthenticationType" name="provider" value="@p.AuthenticationType" title="Log in using your @p.Caption account">@p.AuthenticationType</button>
<button type="submit" class="btn btn-default" id="@p.AuthenticationScheme" name="provider" value="@p.AuthenticationScheme" title="Log in using your @p.Caption account">@p.AuthenticationScheme</button>
}
</p>
</div>

View File

@ -52,7 +52,7 @@
<p>
@foreach (AuthenticationDescription p in Model.OtherLogins)
{
<button type="submit" class="btn btn-default" id="@p.AuthenticationType" name="provider" value="@p.AuthenticationType" title="Log in using your @p.Caption account">@p.AuthenticationType</button>
<button type="submit" class="btn btn-default" id="@p.AuthenticationScheme" name="provider" value="@p.AuthenticationScheme" title="Log in using your @p.Caption account">@p.AuthenticationScheme</button>
}
</p>
</div>

View File

@ -1,6 +1,6 @@
@using System.Security.Principal
@if (User.Identity.IsAuthenticated)
@if (User.IsSignedIn())
{
using (Html.BeginForm("LogOff", "Account", FormMethod.Post, new { id = "logoutForm", @class = "navbar-right" }))
{
@ -8,7 +8,7 @@
<ul class="nav navbar-nav navbar-right">
<li>
@Html.ActionLink("Hello " + User.Identity.GetUserName() + "!", "Index", "Manage", routeValues: null, htmlAttributes: new { title = "Manage" })
@Html.ActionLink("Hello " + User.GetUserName() + "!", "Index", "Manage", routeValues: null, htmlAttributes: new { title = "Manage" })
</li>
<li><a href="javascript:document.getElementById('logoutForm').submit()">Log off</a></li>
</ul>

View File

@ -11,10 +11,11 @@
"Microsoft.AspNet.Diagnostics": "1.0.0-*",
"Microsoft.AspNet.Identity": "3.0.0-*",
"Microsoft.AspNet.Identity.EntityFramework": "3.0.0-*",
"Microsoft.AspNet.Security.Cookies": "1.0.0-*",
"Microsoft.AspNet.Security.Facebook": "1.0.0-*",
"Microsoft.AspNet.Security.Google": "1.0.0-*",
"Microsoft.AspNet.Security.Twitter": "1.0.0-*",
"Microsoft.AspNet.Authentication.Cookies": "1.0.0-*",
"Microsoft.AspNet.Authentication.Facebook": "1.0.0-*",
"Microsoft.AspNet.Authentication.Google": "1.0.0-*",
"Microsoft.AspNet.Authentication.Twitter": "1.0.0-*",
"Microsoft.AspNet.Authorization": "1.0.0-*",
"Microsoft.AspNet.StaticFiles": "1.0.0-*",
"EntityFramework.SqlServer": "7.0.0-*",
"Microsoft.Framework.ConfigurationModel.Json": "1.0.0-*",

View File

@ -23,10 +23,10 @@ namespace Microsoft.AspNet.Builder
{
throw new ArgumentNullException("app");
}
app.UseCookieAuthentication(null, IdentityOptions.ExternalCookieAuthenticationType);
app.UseCookieAuthentication(null, IdentityOptions.TwoFactorRememberMeCookieAuthenticationType);
app.UseCookieAuthentication(null, IdentityOptions.TwoFactorUserIdCookieAuthenticationType);
app.UseCookieAuthentication(null, IdentityOptions.ApplicationCookieAuthenticationType);
app.UseCookieAuthentication(null, IdentityOptions.ExternalCookieAuthenticationScheme);
app.UseCookieAuthentication(null, IdentityOptions.TwoFactorRememberMeCookieAuthenticationScheme);
app.UseCookieAuthentication(null, IdentityOptions.TwoFactorUserIdCookieAuthenticationScheme);
app.UseCookieAuthentication(null, IdentityOptions.ApplicationCookieAuthenticationScheme);
return app;
}
}

View File

@ -1,61 +0,0 @@
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Security.Claims;
namespace System.Security.Principal
{
/// <summary>
/// Claims related extensions for <see cref="IIdentity"/>.
/// </summary>
public static class ClaimsIdentityExtensions
{
/// <summary>
/// Returns the Name claim value if present otherwise returns null.
/// </summary>
/// <param name="identity">The <see cref="IIdentity"/> instance this method extends.</param>
/// <returns>The Name claim value, or null if the claim is not present.</returns>
/// <remarks>The name claim is identified by <see cref="ClaimsIdentity.DefaultNameClaimType"/>.</remarks>
public static string GetUserName(this IIdentity identity)
{
if (identity == null)
{
throw new ArgumentNullException("identity");
}
var ci = identity as ClaimsIdentity;
return ci != null ? ci.FindFirstValue(ClaimsIdentity.DefaultNameClaimType) : null;
}
/// <summary>
/// Returns the User ID claim value if present otherwise returns null.
/// </summary>
/// <param name="identity">The <see cref="IIdentity"/> instance this method extends.</param>
/// <returns>The User ID claim value, or null if the claim is not present.</returns>
/// <remarks>The name claim is identified by <see cref="ClaimTypes.NameIdentifier"/>.</remarks>
public static string GetUserId(this IIdentity identity)
{
if (identity == null)
{
throw new ArgumentNullException("identity");
}
var ci = identity as ClaimsIdentity;
return ci != null ? ci.FindFirstValue(ClaimTypes.NameIdentifier) : null;
}
/// <summary>
/// Returns the value for the first claim of the specified type otherwise null the claim is not present.
/// </summary>
/// <param name="identity">The <see cref="IIdentity"/> instance this method extends.</param>
/// <param name="claimType">The claim type whose first value should be returned.</param>
/// <returns>The value of the first instance of the specifed claim type, or null if the claim is not present.</returns>
public static string FindFirstValue(this ClaimsIdentity identity, string claimType)
{
if (identity == null)
{
throw new ArgumentNullException("identity");
}
var claim = identity.FindFirst(claimType);
return claim != null ? claim.Value : null;
}
}
}

View File

@ -7,12 +7,12 @@ namespace Microsoft.AspNet.Identity
{
public class ExternalLoginInfo : UserLoginInfo
{
public ExternalLoginInfo(ClaimsIdentity externalIdentity, string loginProvider, string providerKey,
public ExternalLoginInfo(ClaimsPrincipal externalPrincipal, string loginProvider, string providerKey,
string displayName) : base(loginProvider, providerKey, displayName)
{
ExternalIdentity = externalIdentity;
ExternalPrincipal = externalPrincipal;
}
public ClaimsIdentity ExternalIdentity { get; set; }
public ClaimsPrincipal ExternalPrincipal { get; set; }
}
}

View File

@ -1,14 +1,13 @@
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Security.Claims;
using System.Threading.Tasks;
using Microsoft.AspNet.Security.Cookies;
using Microsoft.AspNet.Authentication.Cookies;
namespace Microsoft.AspNet.Identity
{
public interface ISecurityStampValidator
{
Task ValidateAsync(CookieValidateIdentityContext context, ClaimsIdentity identity);
Task ValidateAsync(CookieValidatePrincipalContext context);
}
}

View File

@ -2,24 +2,23 @@
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Security.Claims;
using System.Threading;
using System.Threading.Tasks;
namespace Microsoft.AspNet.Identity
{
/// <summary>
/// Interface for creating a ClaimsIdentity from an user
/// Interface for creating a ClaimsPrincipal from an user
/// </summary>
/// <typeparam name="TUser"></typeparam>
public interface IClaimsIdentityFactory<TUser>
public interface IUserClaimsPrincipalFactory<TUser>
where TUser : class
{
/// <summary>
/// Create a ClaimsIdentity from an user
/// Create a ClaimsPrincipal from an user
/// </summary>
/// <param name="user"></param>
/// <param name="authenticationType"></param>
/// <returns></returns>
Task<ClaimsIdentity> CreateAsync(TUser user);
Task<ClaimsPrincipal> CreateAsync(TUser user);
}
}

View File

@ -1,9 +1,6 @@
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using Microsoft.AspNet.Http;
using Microsoft.AspNet.Security;
using Microsoft.AspNet.Security.Cookies;
using System;
namespace Microsoft.AspNet.Identity
@ -31,9 +28,15 @@ namespace Microsoft.AspNet.Identity
public string ChangeEmailTokenProvider { get; set; } = Resources.DefaultTokenProvider;
public static string ApplicationCookieAuthenticationType { get; set; } = typeof(IdentityOptions).Namespace + ".Application";
public static string ExternalCookieAuthenticationType { get; set; } = typeof(IdentityOptions).Namespace + ".External";
public static string TwoFactorUserIdCookieAuthenticationType { get; set; } = typeof(IdentityOptions).Namespace + ".TwoFactorUserId";
public static string TwoFactorRememberMeCookieAuthenticationType { get; set; } = typeof(IdentityOptions).Namespace + ".TwoFactorRemeberMe";
public static string ApplicationCookieAuthenticationScheme { get; set; } = typeof(IdentityOptions).Namespace + ".Application";
public static string ExternalCookieAuthenticationScheme { get; set; } = typeof(IdentityOptions).Namespace + ".External";
public static string TwoFactorUserIdCookieAuthenticationScheme { get; set; } = typeof(IdentityOptions).Namespace + ".TwoFactorUserId";
public static string TwoFactorRememberMeCookieAuthenticationScheme { get; set; } = typeof(IdentityOptions).Namespace + ".TwoFactorRemeberMe";
public static string ApplicationCookieAuthenticationType { get; set; } = typeof(IdentityOptions).Namespace + ".Application.AuthType";
public static string ExternalCookieAuthenticationType { get; set; } = typeof(IdentityOptions).Namespace + ".External.AuthType";
public static string TwoFactorUserIdCookieAuthenticationType { get; set; } = typeof(IdentityOptions).Namespace + ".TwoFactorUserId.AuthType";
public static string TwoFactorRememberMeCookieAuthenticationType { get; set; } = typeof(IdentityOptions).Namespace + ".TwoFactorRemeberMe.AuthType";
}
}

View File

@ -5,8 +5,8 @@ using System;
using Microsoft.AspNet.Hosting;
using Microsoft.AspNet.Http;
using Microsoft.AspNet.Identity;
using Microsoft.AspNet.Security;
using Microsoft.AspNet.Security.Cookies;
using Microsoft.AspNet.Authentication;
using Microsoft.AspNet.Authentication.Cookies;
using Microsoft.Framework.ConfigurationModel;
namespace Microsoft.Framework.DependencyInjection
@ -65,7 +65,7 @@ namespace Microsoft.Framework.DependencyInjection
// No interface for the error describer so we can add errors without rev'ing the interface
services.TryAdd(describe.Transient<IdentityErrorDescriber, IdentityErrorDescriber>());
services.TryAdd(describe.Scoped<ISecurityStampValidator, SecurityStampValidator<TUser>>());
services.TryAdd(describe.Scoped<IClaimsIdentityFactory<TUser>, ClaimsIdentityFactory<TUser, TRole>>());
services.TryAdd(describe.Scoped<IUserClaimsPrincipalFactory<TUser>, UserClaimsPrincipalFactory<TUser, TRole>>());
services.TryAdd(describe.Scoped<UserManager<TUser>, UserManager<TUser>>());
services.TryAdd(describe.Scoped<SignInManager<TUser>, SignInManager<TUser>>());
services.TryAdd(describe.Scoped<RoleManager<TRole>, RoleManager<TRole>>());
@ -76,39 +76,39 @@ namespace Microsoft.Framework.DependencyInjection
}
services.Configure<ExternalAuthenticationOptions>(options =>
{
options.SignInAsAuthenticationType = IdentityOptions.ExternalCookieAuthenticationType;
options.SignInScheme = IdentityOptions.ExternalCookieAuthenticationScheme;
});
// Configure all of the cookie middlewares
services.Configure<CookieAuthenticationOptions>(options =>
{
options.AuthenticationType = IdentityOptions.ApplicationCookieAuthenticationType;
options.AuthenticationScheme = IdentityOptions.ApplicationCookieAuthenticationScheme;
options.LoginPath = new PathString("/Account/Login");
options.Notifications = new CookieAuthenticationNotifications
{
OnValidateIdentity = SecurityStampValidator.ValidateIdentityAsync
OnValidatePrincipal = SecurityStampValidator.ValidatePrincipalAsync
};
}, IdentityOptions.ApplicationCookieAuthenticationType);
}, IdentityOptions.ApplicationCookieAuthenticationScheme);
services.Configure<CookieAuthenticationOptions>(options =>
{
options.AuthenticationType = IdentityOptions.ExternalCookieAuthenticationType;
options.AuthenticationMode = AuthenticationMode.Passive;
options.CookieName = IdentityOptions.ExternalCookieAuthenticationType;
options.AuthenticationScheme = IdentityOptions.ExternalCookieAuthenticationScheme;
options.AutomaticAuthentication = false;
options.CookieName = IdentityOptions.ExternalCookieAuthenticationScheme;
options.ExpireTimeSpan = TimeSpan.FromMinutes(5);
}, IdentityOptions.ExternalCookieAuthenticationType);
}, IdentityOptions.ExternalCookieAuthenticationScheme);
services.Configure<CookieAuthenticationOptions>(options =>
{
options.AuthenticationType = IdentityOptions.TwoFactorRememberMeCookieAuthenticationType;
options.AuthenticationMode = AuthenticationMode.Passive;
options.CookieName = IdentityOptions.TwoFactorRememberMeCookieAuthenticationType;
}, IdentityOptions.TwoFactorRememberMeCookieAuthenticationType);
options.AuthenticationScheme = IdentityOptions.TwoFactorRememberMeCookieAuthenticationScheme;
options.AutomaticAuthentication = false;
options.CookieName = IdentityOptions.TwoFactorRememberMeCookieAuthenticationScheme;
}, IdentityOptions.TwoFactorRememberMeCookieAuthenticationScheme);
services.Configure<CookieAuthenticationOptions>(options =>
{
options.AuthenticationType = IdentityOptions.TwoFactorUserIdCookieAuthenticationType;
options.AuthenticationMode = AuthenticationMode.Passive;
options.CookieName = IdentityOptions.TwoFactorUserIdCookieAuthenticationType;
options.AuthenticationScheme = IdentityOptions.TwoFactorUserIdCookieAuthenticationScheme;
options.AutomaticAuthentication = false;
options.CookieName = IdentityOptions.TwoFactorUserIdCookieAuthenticationScheme;
options.ExpireTimeSpan = TimeSpan.FromMinutes(5);
}, IdentityOptions.TwoFactorUserIdCookieAuthenticationType);
}, IdentityOptions.TwoFactorUserIdCookieAuthenticationScheme);
return new IdentityBuilder(typeof(TUser), typeof(TRole), services);
}

View File

@ -0,0 +1,80 @@
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Linq;
using System.Security.Claims;
using Microsoft.AspNet.Identity;
namespace System.Security.Principal
{
/// <summary>
/// Claims related extensions for <see cref="IPrincipal"/>.
/// </summary>
public static class PrincipalExtensions
{
/// <summary>
/// Returns the Name claim value if present otherwise returns null.
/// </summary>
/// <param name="principal">The <see cref="IPrincipal"/> instance this method extends.</param>
/// <returns>The Name claim value, or null if the claim is not present.</returns>
/// <remarks>The name claim is identified by <see cref="ClaimsIdentity.DefaultNameClaimType"/>.</remarks>
public static string GetUserName(this IPrincipal principal)
{
if (principal == null)
{
throw new ArgumentNullException(nameof(principal));
}
var cp = principal as ClaimsPrincipal;
return cp != null ? cp.FindFirstValue(ClaimsIdentity.DefaultNameClaimType) : null;
}
/// <summary>
/// Returns the User ID claim value if present otherwise returns null.
/// </summary>
/// <param name="principal">The <see cref="IPrincipal"/> instance this method extends.</param>
/// <returns>The User ID claim value, or null if the claim is not present.</returns>
/// <remarks>The name claim is identified by <see cref="ClaimTypes.NameIdentifier"/>.</remarks>
public static string GetUserId(this IPrincipal principal)
{
if (principal == null)
{
throw new ArgumentNullException(nameof(principal));
}
var ci = principal as ClaimsPrincipal;
return ci != null ? ci.FindFirstValue(ClaimTypes.NameIdentifier) : null;
}
/// <summary>
/// Returns true if the principal has an identity with the application cookie identity
/// </summary>
/// <param name="principal">The <see cref="IPrincipal"/> instance this method extends.</param>
/// <returns>True if the user is logged in with identity.</returns>
public static bool IsSignedIn(this IPrincipal principal)
{
if (principal == null)
{
throw new ArgumentNullException(nameof(principal));
}
var p = principal as ClaimsPrincipal;
return p?.Identities != null &&
p.Identities.Any(i => i.AuthenticationType == IdentityOptions.ApplicationCookieAuthenticationType);
}
/// <summary>
/// Returns the value for the first claim of the specified type otherwise null the claim is not present.
/// </summary>
/// <param name="identity">The <see cref="IIdentity"/> instance this method extends.</param>
/// <param name="claimType">The claim type whose first value should be returned.</param>
/// <returns>The value of the first instance of the specifed claim type, or null if the claim is not present.</returns>
public static string FindFirstValue(this ClaimsPrincipal principal, string claimType)
{
if (principal == null)
{
throw new ArgumentNullException(nameof(principal));
}
var claim = principal.FindFirst(claimType);
return claim != null ? claim.Value : null;
}
}
}

View File

@ -2,11 +2,9 @@
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Security.Claims;
using System.Security.Principal;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.AspNet.Security.Cookies;
using Microsoft.AspNet.Authentication.Cookies;
using Microsoft.Framework.DependencyInjection;
using Microsoft.Framework.OptionsModel;
@ -19,11 +17,11 @@ namespace Microsoft.AspNet.Identity
/// ClaimsIdentity
/// </summary>
/// <returns></returns>
public virtual async Task ValidateAsync(CookieValidateIdentityContext context, ClaimsIdentity identity)
public virtual async Task ValidateAsync(CookieValidatePrincipalContext context)
{
var manager = context.HttpContext.RequestServices.GetRequiredService<SignInManager<TUser>>();
var userId = identity.GetUserId();
var user = await manager.ValidateSecurityStampAsync(identity, userId);
var userId = context.Principal.GetUserId();
var user = await manager.ValidateSecurityStampAsync(context.Principal, userId);
if (user != null)
{
var isPersistent = false;
@ -35,7 +33,7 @@ namespace Microsoft.AspNet.Identity
}
else
{
context.RejectIdentity();
context.RejectPrincipal();
manager.SignOut();
}
}
@ -47,7 +45,7 @@ namespace Microsoft.AspNet.Identity
/// </summary>
public static class SecurityStampValidator
{
public static Task ValidateIdentityAsync(CookieValidateIdentityContext context)
public static Task ValidatePrincipalAsync(CookieValidatePrincipalContext context)
{
var currentUtc = DateTimeOffset.UtcNow;
if (context.Options != null && context.Options.SystemClock != null)
@ -72,7 +70,7 @@ namespace Microsoft.AspNet.Identity
if (validate)
{
var validator = context.HttpContext.RequestServices.GetRequiredService<ISecurityStampValidator>();
return validator.ValidateAsync(context, context.Identity);
return validator.ValidateAsync(context);
}
return Task.FromResult(0);
}

View File

@ -9,7 +9,7 @@ using System.Security.Principal;
using System.Threading.Tasks;
using Microsoft.AspNet.Hosting;
using Microsoft.AspNet.Http;
using Microsoft.AspNet.Http.Security;
using Microsoft.AspNet.Http.Authentication;
using Microsoft.Framework.Logging;
using Microsoft.Framework.OptionsModel;
@ -23,7 +23,7 @@ namespace Microsoft.AspNet.Identity
{
public SignInManager(UserManager<TUser> userManager,
IHttpContextAccessor contextAccessor,
IClaimsIdentityFactory<TUser> claimsFactory,
IUserClaimsPrincipalFactory<TUser> claimsFactory,
IOptions<IdentityOptions> optionsAccessor = null,
ILogger<SignInManager<TUser>> logger = null)
{
@ -50,12 +50,12 @@ namespace Microsoft.AspNet.Identity
public UserManager<TUser> UserManager { get; private set; }
public HttpContext Context { get; private set; }
public IClaimsIdentityFactory<TUser> ClaimsFactory { get; private set; }
public IUserClaimsPrincipalFactory<TUser> ClaimsFactory { get; private set; }
public IdentityOptions Options { get; private set; }
public ILogger<SignInManager<TUser>> Logger { get; set; }
// Should this be a func?
public virtual async Task<ClaimsIdentity> CreateUserIdentityAsync(TUser user)
public virtual async Task<ClaimsPrincipal> CreateUserPrincipalAsync(TUser user)
{
return await ClaimsFactory.CreateAsync(user);
}
@ -75,19 +75,22 @@ namespace Microsoft.AspNet.Identity
public virtual async Task SignInAsync(TUser user, bool isPersistent, string authenticationMethod = null)
{
var userIdentity = await CreateUserIdentityAsync(user);
var userPrincipal = await CreateUserPrincipalAsync(user);
// Review: should we guard against CreateUserPrincipal returning null?
if (authenticationMethod != null)
{
userIdentity.AddClaim(new Claim(ClaimTypes.AuthenticationMethod, authenticationMethod));
userPrincipal.Identities.First().AddClaim(new Claim(ClaimTypes.AuthenticationMethod, authenticationMethod));
}
Context.Response.SignIn(new AuthenticationProperties() { IsPersistent = isPersistent }, userIdentity);
Context.Response.SignIn(IdentityOptions.ApplicationCookieAuthenticationScheme,
userPrincipal,
new AuthenticationProperties() { IsPersistent = isPersistent });
}
public virtual void SignOut()
{
Context.Response.SignOut(IdentityOptions.ApplicationCookieAuthenticationType);
Context.Response.SignOut(IdentityOptions.ExternalCookieAuthenticationType);
Context.Response.SignOut(IdentityOptions.TwoFactorUserIdCookieAuthenticationType);
Context.Response.SignOut(IdentityOptions.ApplicationCookieAuthenticationScheme);
Context.Response.SignOut(IdentityOptions.ExternalCookieAuthenticationScheme);
Context.Response.SignOut(IdentityOptions.TwoFactorUserIdCookieAuthenticationScheme);
}
private async Task<bool> IsLockedOut(TUser user)
@ -124,13 +127,13 @@ namespace Microsoft.AspNet.Identity
/// <param name="identity"></param>
/// <param name="userId"></param>
/// <returns></returns>
public virtual async Task<TUser> ValidateSecurityStampAsync(ClaimsIdentity identity, string userId)
public virtual async Task<TUser> ValidateSecurityStampAsync(ClaimsPrincipal principal, string userId)
{
var user = await UserManager.FindByIdAsync(userId);
if (user != null && UserManager.SupportsUserSecurityStamp)
{
var securityStamp =
identity.FindFirstValue(Options.ClaimsIdentity.SecurityStampClaimType);
principal.FindFirstValue(Options.ClaimsIdentity.SecurityStampClaimType);
if (securityStamp == await UserManager.GetSecurityStampAsync(user))
{
return user;
@ -221,8 +224,8 @@ namespace Microsoft.AspNet.Identity
{
var userId = await UserManager.GetUserIdAsync(user);
var result =
await Context.AuthenticateAsync(IdentityOptions.TwoFactorRememberMeCookieAuthenticationType);
return (result != null && result.Identity != null && result.Identity.Name == userId);
await Context.AuthenticateAsync(IdentityOptions.TwoFactorRememberMeCookieAuthenticationScheme);
return (result?.Principal != null && result.Principal.FindFirstValue(ClaimTypes.Name) == userId);
}
public virtual async Task RememberTwoFactorClientAsync(TUser user)
@ -230,12 +233,14 @@ namespace Microsoft.AspNet.Identity
var userId = await UserManager.GetUserIdAsync(user);
var rememberBrowserIdentity = new ClaimsIdentity(IdentityOptions.TwoFactorRememberMeCookieAuthenticationType);
rememberBrowserIdentity.AddClaim(new Claim(ClaimTypes.Name, userId));
Context.Response.SignIn(new AuthenticationProperties { IsPersistent = true }, rememberBrowserIdentity);
Context.Response.SignIn(IdentityOptions.TwoFactorRememberMeCookieAuthenticationScheme,
new ClaimsPrincipal(rememberBrowserIdentity),
new AuthenticationProperties { IsPersistent = true });
}
public virtual Task ForgetTwoFactorClientAsync()
{
Context.Response.SignOut(IdentityOptions.TwoFactorRememberMeCookieAuthenticationType);
Context.Response.SignOut(IdentityOptions.TwoFactorRememberMeCookieAuthenticationScheme);
return Task.FromResult(0);
}
@ -264,7 +269,7 @@ namespace Microsoft.AspNet.Identity
// Cleanup external cookie
if (twoFactorInfo.LoginProvider != null)
{
Context.Response.SignOut(IdentityOptions.ExternalCookieAuthenticationType);
Context.Response.SignOut(IdentityOptions.ExternalCookieAuthenticationScheme);
}
await SignInAsync(user, isPersistent, twoFactorInfo.LoginProvider);
if (rememberClient)
@ -314,15 +319,15 @@ namespace Microsoft.AspNet.Identity
private const string LoginProviderKey = "LoginProvider";
private const string XsrfKey = "XsrfId";
public virtual IEnumerable<AuthenticationDescription> GetExternalAuthenticationTypes()
public virtual IEnumerable<AuthenticationDescription> GetExternalAuthenticationSchemes()
{
return Context.GetAuthenticationTypes().Where(d => !string.IsNullOrEmpty(d.Caption));
return Context.GetAuthenticationSchemes().Where(d => !string.IsNullOrEmpty(d.Caption));
}
public virtual async Task<ExternalLoginInfo> GetExternalLoginInfoAsync(string expectedXsrf = null)
{
var auth = await Context.AuthenticateAsync(IdentityOptions.ExternalCookieAuthenticationType);
if (auth == null || auth.Identity == null || auth.Properties.Dictionary == null || !auth.Properties.Dictionary.ContainsKey(LoginProviderKey))
var auth = await Context.AuthenticateAsync(IdentityOptions.ExternalCookieAuthenticationScheme);
if (auth == null || auth.Principal == null || auth.Properties.Dictionary == null || !auth.Properties.Dictionary.ContainsKey(LoginProviderKey))
{
return null;
}
@ -340,13 +345,13 @@ namespace Microsoft.AspNet.Identity
}
}
var providerKey = auth.Identity.FindFirstValue(ClaimTypes.NameIdentifier);
var providerKey = auth.Principal.FindFirstValue(ClaimTypes.NameIdentifier);
var provider = auth.Properties.Dictionary[LoginProviderKey] as string;
if (providerKey == null || provider == null)
{
return null;
}
return new ExternalLoginInfo(auth.Identity, provider, providerKey, auth.Description.Caption);
return new ExternalLoginInfo(auth.Principal, provider, providerKey, auth.Description.Caption);
}
public virtual AuthenticationProperties ConfigureExternalAuthenticationProperties(string provider, string redirectUrl, string userId = null)
@ -370,14 +375,14 @@ namespace Microsoft.AspNet.Identity
{
// Store the userId for use after two factor check
var userId = await UserManager.GetUserIdAsync(user);
Context.Response.SignIn(StoreTwoFactorInfo(userId, loginProvider));
Context.Response.SignIn(IdentityOptions.TwoFactorUserIdCookieAuthenticationScheme, StoreTwoFactorInfo(userId, loginProvider));
return SignInResult.TwoFactorRequired;
}
}
// Cleanup external cookie
if (loginProvider != null)
{
Context.Response.SignOut(IdentityOptions.ExternalCookieAuthenticationType);
Context.Response.SignOut(IdentityOptions.ExternalCookieAuthenticationScheme);
}
await SignInAsync(user, isPersistent, loginProvider);
return SignInResult.Success;
@ -385,13 +390,13 @@ namespace Microsoft.AspNet.Identity
private async Task<TwoFactorAuthenticationInfo> RetrieveTwoFactorInfoAsync()
{
var result = await Context.AuthenticateAsync(IdentityOptions.TwoFactorUserIdCookieAuthenticationType);
if (result != null && result.Identity != null)
var result = await Context.AuthenticateAsync(IdentityOptions.TwoFactorUserIdCookieAuthenticationScheme);
if (result?.Principal != null)
{
return new TwoFactorAuthenticationInfo
{
UserId = result.Identity.Name,
LoginProvider = result.Identity.FindFirstValue(ClaimTypes.AuthenticationMethod)
UserId = result.Principal.FindFirstValue(ClaimTypes.Name),
LoginProvider = result.Principal.FindFirstValue(ClaimTypes.AuthenticationMethod)
};
}
return null;
@ -426,7 +431,7 @@ namespace Microsoft.AspNet.Identity
return status;
}
internal static ClaimsIdentity StoreTwoFactorInfo(string userId, string loginProvider)
internal static ClaimsPrincipal StoreTwoFactorInfo(string userId, string loginProvider)
{
var identity = new ClaimsIdentity(IdentityOptions.TwoFactorUserIdCookieAuthenticationType);
identity.AddClaim(new Claim(ClaimTypes.Name, userId));
@ -434,7 +439,7 @@ namespace Microsoft.AspNet.Identity
{
identity.AddClaim(new Claim(ClaimTypes.AuthenticationMethod, loginProvider));
}
return identity;
return new ClaimsPrincipal(identity);
}
internal class TwoFactorAuthenticationInfo

View File

@ -11,11 +11,11 @@ using Microsoft.Framework.OptionsModel;
namespace Microsoft.AspNet.Identity
{
/// <summary>
/// Provides methods to create a claims identity for a given user.
/// Provides methods to create a claims principal for a given user.
/// </summary>
/// <typeparam name="TUser">The type used to represent a user.</typeparam>
/// <typeparam name="TRole">The type used to represent a role.</typeparam>
public class ClaimsIdentityFactory<TUser, TRole> : IClaimsIdentityFactory<TUser>
public class UserClaimsPrincipalFactory<TUser, TRole> : IUserClaimsPrincipalFactory<TUser>
where TUser : class
where TRole : class
{
@ -25,7 +25,7 @@ namespace Microsoft.AspNet.Identity
/// <param name="userManager">The <see cref="UserManager{TUser}"/> to retrieve user information from.</param>
/// <param name="roleManager">The <see cref="RoleManager{TRole}"/> to retrieve a user's roles from.</param>
/// <param name="optionsAccessor">The configured <see cref="IdentityOptions"/>.</param>
public ClaimsIdentityFactory(
public UserClaimsPrincipalFactory(
UserManager<TUser> userManager,
RoleManager<TRole> roleManager,
IOptions<IdentityOptions> optionsAccessor)
@ -72,12 +72,11 @@ namespace Microsoft.AspNet.Identity
public IdentityOptions Options { get; private set; }
/// <summary>
/// Creates a populated <see cref="ClaimsIdentity"/> for the specified <paramref name="user"/>.
/// Creates a populated <see cref="ClaimsPrincipal"/> for the specified <paramref name="user"/>.
/// </summary>
/// <param name="user">The user instance to create claims on.</param>
/// <param name="cancellationToken">A <see cref="CancellationToken"/> to observe while waiting for the tasks to complete.</param>
/// <returns>A <see cref="Task{TResult}"/> that represents the started task.</returns>
public virtual async Task<ClaimsIdentity> CreateAsync(TUser user)
public virtual async Task<ClaimsPrincipal> CreateAsync(TUser user)
{
if (user == null)
{
@ -85,10 +84,11 @@ namespace Microsoft.AspNet.Identity
}
var userId = await UserManager.GetUserIdAsync(user);
var userName = await UserManager.GetUserNameAsync(user);
var id = new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationType, Options.ClaimsIdentity.UserNameClaimType,
var id = new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationType,
Options.ClaimsIdentity.UserNameClaimType,
Options.ClaimsIdentity.RoleClaimType);
id.AddClaim(new Claim(Options.ClaimsIdentity.UserIdClaimType, userId));
id.AddClaim(new Claim(Options.ClaimsIdentity.UserNameClaimType, userName, ClaimValueTypes.String));
id.AddClaim(new Claim(Options.ClaimsIdentity.UserNameClaimType, userName));
if (UserManager.SupportsUserSecurityStamp)
{
id.AddClaim(new Claim(Options.ClaimsIdentity.SecurityStampClaimType,
@ -99,7 +99,7 @@ namespace Microsoft.AspNet.Identity
var roles = await UserManager.GetRolesAsync(user);
foreach (var roleName in roles)
{
id.AddClaim(new Claim(Options.ClaimsIdentity.RoleClaimType, roleName, ClaimValueTypes.String));
id.AddClaim(new Claim(Options.ClaimsIdentity.RoleClaimType, roleName));
if (RoleManager.SupportsRoleClaims)
{
var role = await RoleManager.FindByNameAsync(roleName);
@ -114,7 +114,7 @@ namespace Microsoft.AspNet.Identity
{
id.AddClaims(await UserManager.GetClaimsAsync(user));
}
return id;
return new ClaimsPrincipal(id);
}
}
}

View File

@ -1,14 +1,14 @@
{
"version": "3.0.0-*",
"dependencies": {
"Microsoft.AspNet.Authentication" : "1.0.0-*",
"Microsoft.AspNet.Authentication.Cookies": "1.0.0-*",
"Microsoft.AspNet.Cryptography.KeyDerivation": "1.0.0-*",
"Microsoft.AspNet.Http" : "1.0.0-*",
"Microsoft.AspNet.Security" : "1.0.0-*",
"Microsoft.AspNet.Security.Cookies": "1.0.0-*",
"Microsoft.Framework.ConfigurationModel": "1.0.0-*",
"Microsoft.Framework.DependencyInjection" : "1.0.0-*",
"Microsoft.Framework.OptionsModel": "1.0.0-*",
"Microsoft.Framework.Logging": "1.0.0-*"
"Microsoft.Framework.Logging": "1.0.0-*",
"Microsoft.Framework.OptionsModel": "1.0.0-*"
},
"frameworks": {
"aspnet50": {},

View File

@ -6,7 +6,7 @@ using System.Threading.Tasks;
using Microsoft.AspNet.Builder;
using Microsoft.AspNet.Hosting;
using Microsoft.AspNet.Http;
using Microsoft.AspNet.Http.Security;
using Microsoft.AspNet.Http.Authentication;
using Microsoft.AspNet.Identity.Test;
using Microsoft.Framework.DependencyInjection;
using Microsoft.Framework.Runtime.Infrastructure;
@ -30,7 +30,9 @@ namespace Microsoft.AspNet.Identity.InMemory.Test
var context = new Mock<HttpContext>();
var response = new Mock<HttpResponse>();
context.Setup(c => c.Response).Returns(response.Object).Verifiable();
response.Setup(r => r.SignIn(It.Is<AuthenticationProperties>(v => v.IsPersistent == isPersistent), It.IsAny<ClaimsIdentity>())).Verifiable();
response.Setup(r => r.SignIn(IdentityOptions.ApplicationCookieAuthenticationScheme,
It.IsAny<ClaimsPrincipal>(),
It.Is<AuthenticationProperties>(v => v.IsPersistent == isPersistent))).Verifiable();
var contextAccessor = new Mock<IHttpContextAccessor>();
contextAccessor.Setup(a => a.HttpContext).Returns(context.Object);
app.UseServices(services =>

View File

@ -4,8 +4,8 @@
"Microsoft.AspNet.Http" : "1.0.0-*",
"Microsoft.AspNet.Identity" : "3.0.0-*",
"Microsoft.AspNet.RequestContainer" : "1.0.0-*",
"Microsoft.AspNet.Security" : "1.0.0-*",
"Microsoft.AspNet.Security.Cookies" : "1.0.0-*",
"Microsoft.AspNet.Authentication" : "1.0.0-*",
"Microsoft.AspNet.Authentication.Cookies" : "1.0.0-*",
"Microsoft.AspNet.Testing" : "1.0.0-*",
"Microsoft.Framework.ConfigurationModel": "1.0.0-*",
"Microsoft.Framework.DependencyInjection" : "1.0.0-*",

View File

@ -1,77 +0,0 @@
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Security.Claims;
using System.Security.Principal;
using Xunit;
namespace Microsoft.AspNet.Identity.Test
{
public class ClaimsIdentityExtensionsTest
{
public const string ExternalAuthenticationType = "TestExternalAuth";
[Fact]
public void IdentityNullCheckTest()
{
IIdentity identity = null;
Assert.Throws<ArgumentNullException>("identity", () => identity.GetUserId());
Assert.Throws<ArgumentNullException>("identity", () => identity.GetUserName());
ClaimsIdentity claimsIdentity = null;
Assert.Throws<ArgumentNullException>("identity", () => claimsIdentity.FindFirstValue(null));
}
[Fact]
public void IdentityNullIfNotClaimsIdentityTest()
{
IIdentity identity = new TestIdentity();
Assert.Null(identity.GetUserId());
Assert.Null(identity.GetUserName());
}
[Fact]
public void UserNameAndIdTest()
{
var id = CreateTestExternalIdentity();
Assert.Equal("NameIdentifier", id.GetUserId());
Assert.Equal("Name", id.GetUserName());
}
[Fact]
public void IdentityExtensionsFindFirstValueNullIfUnknownTest()
{
var id = CreateTestExternalIdentity();
Assert.Null(id.FindFirstValue("bogus"));
}
private static ClaimsIdentity CreateTestExternalIdentity()
{
return new ClaimsIdentity(
new[]
{
new Claim(ClaimTypes.NameIdentifier, "NameIdentifier", null, ExternalAuthenticationType),
new Claim(ClaimTypes.Name, "Name")
},
ExternalAuthenticationType);
}
private class TestIdentity : IIdentity
{
public string AuthenticationType
{
get { throw new NotImplementedException(); }
}
public bool IsAuthenticated
{
get { throw new NotImplementedException(); }
}
public string Name
{
get { throw new NotImplementedException(); }
}
}
}
}

View File

@ -0,0 +1,120 @@
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Security.Claims;
using System.Security.Principal;
using Xunit;
namespace Microsoft.AspNet.Identity.Test
{
public class ClaimsIdentityExtensionsTest
{
public const string ExternalAuthenticationScheme = "TestExternalAuth";
[Fact]
public void IdentityNullCheckTest()
{
IPrincipal p = null;
Assert.Throws<ArgumentNullException>("principal", () => p.GetUserId());
Assert.Throws<ArgumentNullException>("principal", () => p.GetUserName());
ClaimsPrincipal cp = null;
Assert.Throws<ArgumentNullException>("principal", () => cp.FindFirstValue(null));
}
[Fact]
public void IdentityNullIfNotClaimsIdentityTest()
{
IPrincipal identity = new TestPrincipal();
Assert.Null(identity.GetUserId());
Assert.Null(identity.GetUserName());
}
[Fact]
public void UserNameAndIdTest()
{
var p = CreateTestExternalIdentity();
Assert.Equal("NameIdentifier", p.GetUserId());
Assert.Equal("Name", p.GetUserName());
}
[Fact]
public void IdentityExtensionsFindFirstValueNullIfUnknownTest()
{
var id = CreateTestExternalIdentity();
Assert.Null(id.FindFirstValue("bogus"));
}
[Fact]
public void IsSignedInWithDefaultAppAuthenticationType()
{
var id = CreateAppIdentity();
Assert.True(id.IsSignedIn());
}
[Fact]
public void IsSignedInFalseWithWrongAppAuthenticationType()
{
var id = CreateAppIdentity("bogus");
Assert.False(id.IsSignedIn());
}
private static ClaimsPrincipal CreateAppIdentity(string authType = null)
{
authType = authType ?? IdentityOptions.ApplicationCookieAuthenticationType;
return new ClaimsPrincipal(new ClaimsIdentity(
new[]
{
new Claim(ClaimTypes.NameIdentifier, "NameIdentifier"),
new Claim(ClaimTypes.Name, "Name")
},
authType));
}
private static ClaimsPrincipal CreateTestExternalIdentity()
{
return new ClaimsPrincipal(new ClaimsIdentity(
new[]
{
new Claim(ClaimTypes.NameIdentifier, "NameIdentifier", null, ExternalAuthenticationScheme),
new Claim(ClaimTypes.Name, "Name")
},
ExternalAuthenticationScheme));
}
private class TestPrincipal : IPrincipal
{
public IIdentity Identity
{
get
{
throw new NotImplementedException();
}
}
public bool IsInRole(string role)
{
throw new NotImplementedException();
}
}
private class TestIdentity : IIdentity
{
public string AuthenticationType
{
get { throw new NotImplementedException(); }
}
public bool IsAuthenticated
{
get { throw new NotImplementedException(); }
}
public string Name
{
get { throw new NotImplementedException(); }
}
}
}
}

View File

@ -3,13 +3,12 @@
using System;
using System.Security.Claims;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.AspNet.Authentication;
using Microsoft.AspNet.Authentication.Cookies;
using Microsoft.AspNet.Hosting;
using Microsoft.AspNet.Http;
using Microsoft.AspNet.Http.Security;
using Microsoft.AspNet.Security;
using Microsoft.AspNet.Security.Cookies;
using Microsoft.AspNet.Http.Authentication;
using Microsoft.Framework.DependencyInjection;
using Microsoft.Framework.DependencyInjection.Fallback;
using Microsoft.Framework.OptionsModel;
@ -21,25 +20,25 @@ namespace Microsoft.AspNet.Identity.Test
public class SecurityStampTest
{
[Fact]
public async Task OnValidateIdentityThrowsWithEmptyServiceCollection()
public async Task OnValidatePrincipalThrowsWithEmptyServiceCollection()
{
var httpContext = new Mock<HttpContext>();
httpContext.Setup(c => c.RequestServices).Returns(new ServiceCollection().BuildServiceProvider());
var id = new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationType);
var ticket = new AuthenticationTicket(id, new AuthenticationProperties { IssuedUtc = DateTimeOffset.UtcNow });
var context = new CookieValidateIdentityContext(httpContext.Object, ticket, new CookieAuthenticationOptions());
var ex = await Assert.ThrowsAsync<InvalidOperationException>(() => SecurityStampValidator.ValidateIdentityAsync(context));
var id = new ClaimsPrincipal(new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationScheme));
var ticket = new AuthenticationTicket(id, new AuthenticationProperties { IssuedUtc = DateTimeOffset.UtcNow }, IdentityOptions.ApplicationCookieAuthenticationScheme);
var context = new CookieValidatePrincipalContext(httpContext.Object, ticket, new CookieAuthenticationOptions());
var ex = await Assert.ThrowsAsync<InvalidOperationException>(() => SecurityStampValidator.ValidatePrincipalAsync(context));
Assert.True(ex.Message.Contains("No service for type 'Microsoft.Framework.OptionsModel.IOptions"));
}
[Theory]
[InlineData(true)]
[InlineData(false)]
public async Task OnValidateIdentityTestSuccess(bool isPersistent)
public async Task OnValidatePrincipalTestSuccess(bool isPersistent)
{
var user = new IdentityUser("test");
var userManager = MockHelpers.MockUserManager<IdentityUser>();
var claimsManager = new Mock<IClaimsIdentityFactory<IdentityUser>>();
var claimsManager = new Mock<IUserClaimsPrincipalFactory<IdentityUser>>();
var identityOptions = new IdentityOptions { SecurityStampValidationInterval = TimeSpan.Zero };
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
@ -48,24 +47,26 @@ namespace Microsoft.AspNet.Identity.Test
contextAccessor.Setup(a => a.HttpContext).Returns(httpContext.Object);
var signInManager = new Mock<SignInManager<IdentityUser>>(userManager.Object,
contextAccessor.Object, claimsManager.Object, options.Object, null);
signInManager.Setup(s => s.ValidateSecurityStampAsync(It.IsAny<ClaimsIdentity>(), user.Id)).ReturnsAsync(user).Verifiable();
signInManager.Setup(s => s.ValidateSecurityStampAsync(It.IsAny<ClaimsPrincipal>(), user.Id)).ReturnsAsync(user).Verifiable();
signInManager.Setup(s => s.SignInAsync(user, isPersistent, null)).Returns(Task.FromResult(0)).Verifiable();
var services = new ServiceCollection();
services.AddInstance(options.Object);
services.AddInstance(signInManager.Object);
services.AddInstance<ISecurityStampValidator>(new SecurityStampValidator<IdentityUser>());
httpContext.Setup(c => c.RequestServices).Returns(services.BuildServiceProvider());
var id = new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationType);
var id = new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationScheme);
id.AddClaim(new Claim(ClaimTypes.NameIdentifier, user.Id));
var ticket = new AuthenticationTicket(id, new AuthenticationProperties { IssuedUtc = DateTimeOffset.UtcNow, IsPersistent = isPersistent });
var context = new CookieValidateIdentityContext(httpContext.Object, ticket, new CookieAuthenticationOptions());
var ticket = new AuthenticationTicket(new ClaimsPrincipal(id),
new AuthenticationProperties { IssuedUtc = DateTimeOffset.UtcNow, IsPersistent = isPersistent },
IdentityOptions.ApplicationCookieAuthenticationScheme);
var context = new CookieValidatePrincipalContext(httpContext.Object, ticket, new CookieAuthenticationOptions());
Assert.NotNull(context.Properties);
Assert.NotNull(context.Options);
Assert.NotNull(context.Identity);
Assert.NotNull(context.Principal);
await
SecurityStampValidator.ValidateIdentityAsync(context);
Assert.NotNull(context.Identity);
SecurityStampValidator.ValidatePrincipalAsync(context);
Assert.NotNull(context.Principal);
signInManager.VerifyAll();
}
@ -74,7 +75,7 @@ namespace Microsoft.AspNet.Identity.Test
{
var user = new IdentityUser("test");
var userManager = MockHelpers.MockUserManager<IdentityUser>();
var claimsManager = new Mock<IClaimsIdentityFactory<IdentityUser>>();
var claimsManager = new Mock<IUserClaimsPrincipalFactory<IdentityUser>>();
var identityOptions = new IdentityOptions { SecurityStampValidationInterval = TimeSpan.Zero };
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
@ -83,23 +84,24 @@ namespace Microsoft.AspNet.Identity.Test
contextAccessor.Setup(a => a.HttpContext).Returns(httpContext.Object);
var signInManager = new Mock<SignInManager<IdentityUser>>(userManager.Object,
contextAccessor.Object, claimsManager.Object, options.Object, null);
signInManager.Setup(s => s.ValidateSecurityStampAsync(It.IsAny<ClaimsIdentity>(), user.Id)).ReturnsAsync(null).Verifiable();
signInManager.Setup(s => s.ValidateSecurityStampAsync(It.IsAny<ClaimsPrincipal>(), user.Id)).ReturnsAsync(null).Verifiable();
var services = new ServiceCollection();
services.AddInstance(options.Object);
services.AddInstance(signInManager.Object);
services.AddInstance<ISecurityStampValidator>(new SecurityStampValidator<IdentityUser>());
httpContext.Setup(c => c.RequestServices).Returns(services.BuildServiceProvider());
var id = new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationType);
var id = new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationScheme);
id.AddClaim(new Claim(ClaimTypes.NameIdentifier, user.Id));
var ticket = new AuthenticationTicket(id, new AuthenticationProperties { IssuedUtc = DateTimeOffset.UtcNow });
var context = new CookieValidateIdentityContext(httpContext.Object, ticket, new CookieAuthenticationOptions());
var ticket = new AuthenticationTicket(new ClaimsPrincipal(id),
new AuthenticationProperties { IssuedUtc = DateTimeOffset.UtcNow },
IdentityOptions.ApplicationCookieAuthenticationScheme);
var context = new CookieValidatePrincipalContext(httpContext.Object, ticket, new CookieAuthenticationOptions());
Assert.NotNull(context.Properties);
Assert.NotNull(context.Options);
Assert.NotNull(context.Identity);
await
SecurityStampValidator.ValidateIdentityAsync(context);
Assert.Null(context.Identity);
Assert.NotNull(context.Principal);
await SecurityStampValidator.ValidatePrincipalAsync(context);
Assert.Null(context.Principal);
signInManager.VerifyAll();
}
@ -109,7 +111,7 @@ namespace Microsoft.AspNet.Identity.Test
var user = new IdentityUser("test");
var httpContext = new Mock<HttpContext>();
var userManager = MockHelpers.MockUserManager<IdentityUser>();
var claimsManager = new Mock<IClaimsIdentityFactory<IdentityUser>>();
var claimsManager = new Mock<IUserClaimsPrincipalFactory<IdentityUser>>();
var identityOptions = new IdentityOptions { SecurityStampValidationInterval = TimeSpan.Zero };
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
@ -117,23 +119,24 @@ namespace Microsoft.AspNet.Identity.Test
contextAccessor.Setup(a => a.HttpContext).Returns(httpContext.Object);
var signInManager = new Mock<SignInManager<IdentityUser>>(userManager.Object,
contextAccessor.Object, claimsManager.Object, options.Object, null);
signInManager.Setup(s => s.ValidateSecurityStampAsync(It.IsAny<ClaimsIdentity>(), user.Id)).ReturnsAsync(null).Verifiable();
signInManager.Setup(s => s.ValidateSecurityStampAsync(It.IsAny<ClaimsPrincipal>(), user.Id)).ReturnsAsync(null).Verifiable();
var services = new ServiceCollection();
services.AddInstance(options.Object);
services.AddInstance(signInManager.Object);
services.AddInstance<ISecurityStampValidator>(new SecurityStampValidator<IdentityUser>());
httpContext.Setup(c => c.RequestServices).Returns(services.BuildServiceProvider());
var id = new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationType);
var id = new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationScheme);
id.AddClaim(new Claim(ClaimTypes.NameIdentifier, user.Id));
var ticket = new AuthenticationTicket(id, new AuthenticationProperties());
var context = new CookieValidateIdentityContext(httpContext.Object, ticket, new CookieAuthenticationOptions());
var ticket = new AuthenticationTicket(new ClaimsPrincipal(id),
new AuthenticationProperties(),
IdentityOptions.ApplicationCookieAuthenticationScheme);
var context = new CookieValidatePrincipalContext(httpContext.Object, ticket, new CookieAuthenticationOptions());
Assert.NotNull(context.Properties);
Assert.NotNull(context.Options);
Assert.NotNull(context.Identity);
await
SecurityStampValidator.ValidateIdentityAsync(context);
Assert.Null(context.Identity);
Assert.NotNull(context.Principal);
await SecurityStampValidator.ValidatePrincipalAsync(context);
Assert.Null(context.Principal);
signInManager.VerifyAll();
}
@ -143,7 +146,7 @@ namespace Microsoft.AspNet.Identity.Test
var user = new IdentityUser("test");
var httpContext = new Mock<HttpContext>();
var userManager = MockHelpers.MockUserManager<IdentityUser>();
var claimsManager = new Mock<IClaimsIdentityFactory<IdentityUser>>();
var claimsManager = new Mock<IUserClaimsPrincipalFactory<IdentityUser>>();
var identityOptions = new IdentityOptions { SecurityStampValidationInterval = TimeSpan.FromDays(1) };
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
@ -151,24 +154,25 @@ namespace Microsoft.AspNet.Identity.Test
contextAccessor.Setup(a => a.HttpContext).Returns(httpContext.Object);
var signInManager = new Mock<SignInManager<IdentityUser>>(userManager.Object,
contextAccessor.Object, claimsManager.Object, options.Object, null);
signInManager.Setup(s => s.ValidateSecurityStampAsync(It.IsAny<ClaimsIdentity>(), user.Id)).Throws(new Exception("Shouldn't be called"));
signInManager.Setup(s => s.ValidateSecurityStampAsync(It.IsAny<ClaimsPrincipal>(), user.Id)).Throws(new Exception("Shouldn't be called"));
signInManager.Setup(s => s.SignInAsync(user, false, null)).Throws(new Exception("Shouldn't be called"));
var services = new ServiceCollection();
services.AddInstance(options.Object);
services.AddInstance(signInManager.Object);
services.AddInstance<ISecurityStampValidator>(new SecurityStampValidator<IdentityUser>());
httpContext.Setup(c => c.RequestServices).Returns(services.BuildServiceProvider());
var id = new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationType);
var id = new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationScheme);
id.AddClaim(new Claim(ClaimTypes.NameIdentifier, user.Id));
var ticket = new AuthenticationTicket(id, new AuthenticationProperties { IssuedUtc = DateTimeOffset.UtcNow });
var context = new CookieValidateIdentityContext(httpContext.Object, ticket, new CookieAuthenticationOptions());
var ticket = new AuthenticationTicket(new ClaimsPrincipal(id),
new AuthenticationProperties { IssuedUtc = DateTimeOffset.UtcNow },
IdentityOptions.ApplicationCookieAuthenticationScheme);
var context = new CookieValidatePrincipalContext(httpContext.Object, ticket, new CookieAuthenticationOptions());
Assert.NotNull(context.Properties);
Assert.NotNull(context.Options);
Assert.NotNull(context.Identity);
await
SecurityStampValidator.ValidateIdentityAsync(context);
Assert.NotNull(context.Identity);
Assert.NotNull(context.Principal);
await SecurityStampValidator.ValidatePrincipalAsync(context);
Assert.NotNull(context.Principal);
}
}
}

View File

@ -3,15 +3,14 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Security.Claims;
using System.Security.Principal;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.AspNet.Hosting;
using Microsoft.AspNet.Http;
using Microsoft.AspNet.Http.Security;
using Microsoft.Framework.DependencyInjection;
using Microsoft.AspNet.Http.Authentication;
using Microsoft.Framework.OptionsModel;
using Moq;
using Xunit;
@ -28,7 +27,7 @@ namespace Microsoft.AspNet.Identity.Test
// var app = new ApplicationBuilder(new ServiceCollection().BuildServiceProvider());
// app.UseCookieAuthentication(new CookieAuthenticationOptions
// {
// AuthenticationType = ClaimsIdentityOptions.DefaultAuthenticationType
// AuthenticationScheme = ClaimsIdentityOptions.DefaultAuthenticationScheme
// });
// TODO: how to functionally test context?
@ -63,7 +62,7 @@ namespace Microsoft.AspNet.Identity.Test
// // Assert
// Assert.Equal(SignInStatus.Success, result);
// contextAccessor.VerifyAll();
// contextAccessor.Verify();
//}
[Fact]
@ -81,16 +80,16 @@ namespace Microsoft.AspNet.Identity.Test
//TODO: Mock fails in K (this works fine in net45)
//[Fact]
//public async Task EnsureClaimsIdentityFactoryCreateIdentityCalled()
//public async Task EnsureClaimsPrincipalFactoryCreateIdentityCalled()
//{
// // Setup
// var user = new TestUser { UserName = "Foo" };
// var userManager = MockHelpers.TestUserManager<TestUser>();
// var identityFactory = new Mock<IClaimsIdentityFactory<TestUser>>();
// var identityFactory = new Mock<IUserClaimsPrincipalFactory<TestUser>>();
// const string authType = "Test";
// var testIdentity = new ClaimsIdentity(authType);
// identityFactory.Setup(s => s.CreateAsync(userManager, user, authType)).ReturnsAsync(testIdentity).Verifiable();
// userManager.ClaimsIdentityFactory = identityFactory.Object;
// userManager.UserClaimsPrincipalFactory = identityFactory.Object;
// var context = new Mock<HttpContext>();
// var response = new Mock<HttpResponse>();
// context.Setup(c => c.Response).Returns(response.Object).Verifiable();
@ -103,10 +102,10 @@ namespace Microsoft.AspNet.Identity.Test
// helper.SignIn(user, false);
// // Assert
// identityFactory.VerifyAll();
// context.VerifyAll();
// contextAccessor.VerifyAll();
// response.VerifyAll();
// identityFactory.Verify();
// context.Verify();
// contextAccessor.Verify();
// response.Verify();
//}
[Fact]
@ -114,11 +113,9 @@ namespace Microsoft.AspNet.Identity.Test
{
// Setup
var user = new TestUser { UserName = "Foo" };
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
manager.Setup(m => m.SupportsUserLockout).Returns(true).Verifiable();
manager.Setup(m => m.IsLockedOutAsync(user)).ReturnsAsync(true).Verifiable();
manager.Setup(m => m.FindByNameAsync(user.UserName)).ReturnsAsync(user).Verifiable();
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id.ToString()).Verifiable();
var context = new Mock<HttpContext>();
var contextAccessor = new Mock<IHttpContextAccessor>();
@ -127,10 +124,10 @@ namespace Microsoft.AspNet.Identity.Test
var identityOptions = new IdentityOptions();
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new Mock<ClaimsIdentityFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var claimsFactory = new UserClaimsPrincipalFactory<TestUser, TestRole>(manager.Object, roleManager.Object, options.Object);
var logStore = new StringBuilder();
var logger = MockHelpers.MockILogger<SignInManager<TestUser>>(logStore);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory.Object, options.Object, logger.Object);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory, options.Object, logger.Object);
string expected = string.Format("{0} for user: {1} : Result : {2}", "PasswordSignInAsync", user.Id, "Lockedout");
// Act
@ -140,7 +137,17 @@ namespace Microsoft.AspNet.Identity.Test
Assert.False(result.Succeeded);
Assert.True(result.IsLockedOut);
Assert.NotEqual(-1, logStore.ToString().IndexOf(expected));
manager.VerifyAll();
manager.Verify();
}
private static Mock<UserManager<TestUser>> SetupUserManager(TestUser user)
{
var manager = MockHelpers.MockUserManager<TestUser>();
manager.Setup(m => m.FindByNameAsync(user.UserName)).ReturnsAsync(user);
manager.Setup(m => m.FindByIdAsync(user.Id)).ReturnsAsync(user);
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id.ToString());
manager.Setup(m => m.GetUserNameAsync(user)).ReturnsAsync(user.UserName);
return manager;
}
[Theory]
@ -150,29 +157,25 @@ namespace Microsoft.AspNet.Identity.Test
{
// Setup
var user = new TestUser { UserName = "Foo" };
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
manager.Setup(m => m.SupportsUserLockout).Returns(true).Verifiable();
manager.Setup(m => m.IsLockedOutAsync(user)).ReturnsAsync(false).Verifiable();
manager.Setup(m => m.FindByNameAsync(user.UserName)).ReturnsAsync(user).Verifiable();
manager.Setup(m => m.CheckPasswordAsync(user, "password")).ReturnsAsync(true).Verifiable();
manager.Setup(m => m.ResetAccessFailedCountAsync(user)).ReturnsAsync(IdentityResult.Success).Verifiable();
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id.ToString()).Verifiable();
var context = new Mock<HttpContext>();
var response = new Mock<HttpResponse>();
context.Setup(c => c.Response).Returns(response.Object).Verifiable();
response.Setup(r => r.SignIn(It.Is<AuthenticationProperties>(v => v.IsPersistent == isPersistent), It.IsAny<ClaimsIdentity>())).Verifiable();
SetupSignIn(response, user.Id, isPersistent);
var contextAccessor = new Mock<IHttpContextAccessor>();
contextAccessor.Setup(a => a.HttpContext).Returns(context.Object);
var roleManager = MockHelpers.MockRoleManager<TestRole>();
var identityOptions = new IdentityOptions();
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new Mock<ClaimsIdentityFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
claimsFactory.Setup(m => m.CreateAsync(user)).ReturnsAsync(new ClaimsIdentity("Microsoft.AspNet.Identity")).Verifiable();
var claimsFactory = new UserClaimsPrincipalFactory<TestUser, TestRole>(manager.Object, roleManager.Object, options.Object);
var logStore = new StringBuilder();
var logger = MockHelpers.MockILogger<SignInManager<TestUser>>(logStore);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory.Object, options.Object, logger.Object);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory, options.Object, logger.Object);
string expected = string.Format("{0} for user: {1} : Result : {2}", "PasswordSignInAsync", user.Id, "Succeeded");
// Act
@ -181,11 +184,10 @@ namespace Microsoft.AspNet.Identity.Test
// Assert
Assert.True(result.Succeeded);
Assert.NotEqual(-1, logStore.ToString().IndexOf(expected));
manager.VerifyAll();
context.VerifyAll();
response.VerifyAll();
contextAccessor.VerifyAll();
claimsFactory.VerifyAll();
manager.Verify();
context.Verify();
response.Verify();
contextAccessor.Verify();
}
[Fact]
@ -193,17 +195,15 @@ namespace Microsoft.AspNet.Identity.Test
{
// Setup
var user = new TestUser { UserName = "Foo" };
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
manager.Setup(m => m.SupportsUserLockout).Returns(true).Verifiable();
manager.Setup(m => m.IsLockedOutAsync(user)).ReturnsAsync(false).Verifiable();
manager.Setup(m => m.FindByNameAsync(user.UserName)).ReturnsAsync(user).Verifiable();
manager.Setup(m => m.CheckPasswordAsync(user, "password")).ReturnsAsync(true).Verifiable();
manager.Setup(m => m.ResetAccessFailedCountAsync(user)).ReturnsAsync(IdentityResult.Success).Verifiable();
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id.ToString()).Verifiable();
var context = new Mock<HttpContext>();
var response = new Mock<HttpResponse>();
response.Setup(r => r.SignIn(It.IsAny<AuthenticationProperties>(), It.IsAny<ClaimsIdentity>())).Verifiable();
SetupSignIn(response);
context.Setup(c => c.Response).Returns(response.Object).Verifiable();
var contextAccessor = new Mock<IHttpContextAccessor>();
contextAccessor.Setup(a => a.HttpContext).Returns(context.Object);
@ -211,18 +211,18 @@ namespace Microsoft.AspNet.Identity.Test
var identityOptions = new IdentityOptions();
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new Mock<ClaimsIdentityFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory.Object, options.Object);
var claimsFactory = new UserClaimsPrincipalFactory<TestUser, TestRole>(manager.Object, roleManager.Object, options.Object);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory, options.Object);
// Act
var result = await helper.PasswordSignInAsync(user.UserName, "password", false, false);
// Assert
Assert.True(result.Succeeded);
manager.VerifyAll();
context.VerifyAll();
response.VerifyAll();
contextAccessor.VerifyAll();
manager.Verify();
context.Verify();
response.Verify();
contextAccessor.Verify();
}
[Theory]
@ -232,7 +232,7 @@ namespace Microsoft.AspNet.Identity.Test
{
// Setup
var user = new TestUser { UserName = "Foo" };
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
manager.Setup(m => m.SupportsUserLockout).Returns(supportsLockout).Verifiable();
if (supportsLockout)
{
@ -243,8 +243,6 @@ namespace Microsoft.AspNet.Identity.Test
manager.Setup(m => m.GetValidTwoFactorProvidersAsync(user)).Returns(Task.FromResult(providers)).Verifiable();
manager.Setup(m => m.SupportsUserTwoFactor).Returns(true).Verifiable();
manager.Setup(m => m.GetTwoFactorEnabledAsync(user)).ReturnsAsync(true).Verifiable();
manager.Setup(m => m.FindByNameAsync(user.UserName)).ReturnsAsync(user).Verifiable();
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id).Verifiable();
manager.Setup(m => m.CheckPasswordAsync(user, "password")).ReturnsAsync(true).Verifiable();
if (supportsLockout)
{
@ -252,7 +250,9 @@ namespace Microsoft.AspNet.Identity.Test
}
var context = new Mock<HttpContext>();
var response = new Mock<HttpResponse>();
response.Setup(r => r.SignIn(It.Is<ClaimsIdentity>(id => id.Name == user.Id))).Verifiable();
response.Setup(r => r.SignIn(IdentityOptions.TwoFactorUserIdCookieAuthenticationScheme,
It.Is<ClaimsPrincipal>(id => id.FindFirstValue(ClaimTypes.Name) == user.Id),
It.IsAny<AuthenticationProperties>())).Verifiable();
context.Setup(c => c.Response).Returns(response.Object).Verifiable();
var contextAccessor = new Mock<IHttpContextAccessor>();
contextAccessor.Setup(a => a.HttpContext).Returns(context.Object);
@ -262,7 +262,11 @@ namespace Microsoft.AspNet.Identity.Test
options.Setup(a => a.Options).Returns(identityOptions);
var logStore = new StringBuilder();
var logger = MockHelpers.MockILogger<SignInManager<TestUser>>(logStore);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, new ClaimsIdentityFactory<TestUser, TestRole>(manager.Object, roleManager.Object, options.Object), options.Object, logger.Object);
var helper = new SignInManager<TestUser>(manager.Object,
contextAccessor.Object,
new UserClaimsPrincipalFactory<TestUser, TestRole>(manager.Object, roleManager.Object, options.Object),
options.Object,
logger.Object);
string expected = string.Format("{0} for user: {1} : Result : {2}", "PasswordSignInAsync", user.Id, "RequiresTwoFactor");
// Act
@ -272,10 +276,10 @@ namespace Microsoft.AspNet.Identity.Test
Assert.False(result.Succeeded);
Assert.True(result.RequiresTwoFactor);
Assert.NotEqual(-1, logStore.ToString().IndexOf(expected));
manager.VerifyAll();
context.VerifyAll();
response.VerifyAll();
contextAccessor.VerifyAll();
manager.Verify();
context.Verify();
response.Verify();
contextAccessor.Verify();
}
[Theory]
@ -289,33 +293,29 @@ namespace Microsoft.AspNet.Identity.Test
var user = new TestUser { UserName = "Foo" };
const string loginProvider = "login";
const string providerKey = "fookey";
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
manager.Setup(m => m.SupportsUserLockout).Returns(supportsLockout).Verifiable();
if (supportsLockout)
{
manager.Setup(m => m.IsLockedOutAsync(user)).ReturnsAsync(false).Verifiable();
}
manager.Setup(m => m.FindByLoginAsync(loginProvider, providerKey)).ReturnsAsync(user).Verifiable();
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id.ToString()).Verifiable();
var context = new Mock<HttpContext>();
var response = new Mock<HttpResponse>();
context.Setup(c => c.Response).Returns(response.Object).Verifiable();
response.Setup(r => r.SignIn(
It.Is<AuthenticationProperties>(v => v.IsPersistent == isPersistent),
It.Is<ClaimsIdentity>(i => i.FindFirstValue(ClaimTypes.AuthenticationMethod) == loginProvider))).Verifiable();
SetupSignIn(response, user.Id, isPersistent, loginProvider);
var contextAccessor = new Mock<IHttpContextAccessor>();
contextAccessor.Setup(a => a.HttpContext).Returns(context.Object);
var roleManager = MockHelpers.MockRoleManager<TestRole>();
var identityOptions = new IdentityOptions();
response.Setup(r => r.SignOut(IdentityOptions.ExternalCookieAuthenticationType)).Verifiable();
response.Setup(r => r.SignOut(IdentityOptions.ExternalCookieAuthenticationScheme)).Verifiable();
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new Mock<ClaimsIdentityFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
claimsFactory.Setup(m => m.CreateAsync(user)).ReturnsAsync(new ClaimsIdentity("Microsoft.AspNet.Identity")).Verifiable();
var claimsFactory = new UserClaimsPrincipalFactory<TestUser, TestRole>(manager.Object, roleManager.Object, options.Object);
var logStore = new StringBuilder();
var logger = MockHelpers.MockILogger<SignInManager<TestUser>>(logStore);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory.Object, options.Object, logger.Object);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory, options.Object, logger.Object);
string expected = string.Format("{0} for user: {1} : Result : {2}", "ExternalLoginSignInAsync", user.Id.ToString(), "Succeeded");
// Act
@ -324,11 +324,10 @@ namespace Microsoft.AspNet.Identity.Test
// Assert
Assert.True(result.Succeeded);
Assert.NotEqual(-1, logStore.ToString().IndexOf(expected));
manager.VerifyAll();
context.VerifyAll();
response.VerifyAll();
contextAccessor.VerifyAll();
claimsFactory.VerifyAll();
manager.Verify();
context.Verify();
response.Verify();
contextAccessor.Verify();
}
[Theory]
@ -352,7 +351,7 @@ namespace Microsoft.AspNet.Identity.Test
{
// Setup
var user = new TestUser { UserName = "Foo" };
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
var provider = "twofactorprovider";
var code = "123456";
manager.Setup(m => m.SupportsUserLockout).Returns(supportsLockout).Verifiable();
@ -361,10 +360,7 @@ namespace Microsoft.AspNet.Identity.Test
manager.Setup(m => m.IsLockedOutAsync(user)).ReturnsAsync(false).Verifiable();
manager.Setup(m => m.ResetAccessFailedCountAsync(user)).ReturnsAsync(IdentityResult.Success).Verifiable();
}
manager.Setup(m => m.FindByIdAsync(user.Id)).ReturnsAsync(user).Verifiable();
manager.Setup(m => m.VerifyTwoFactorTokenAsync(user, provider, code)).ReturnsAsync(true).Verifiable();
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id).Verifiable();
manager.Setup(m => m.GetUserNameAsync(user)).ReturnsAsync(user.UserName).Verifiable();
var context = new Mock<HttpContext>();
var response = new Mock<HttpResponse>();
var contextAccessor = new Mock<IHttpContextAccessor>();
@ -376,30 +372,30 @@ namespace Microsoft.AspNet.Identity.Test
var identityOptions = new IdentityOptions();
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new ClaimsIdentityFactory<TestUser, TestRole>(manager.Object, roleManager.Object, options.Object);
var claimsFactory = new UserClaimsPrincipalFactory<TestUser, TestRole>(manager.Object, roleManager.Object, options.Object);
if (externalLogin)
{
response.Setup(r => r.SignIn(
It.Is<AuthenticationProperties>(v => v.IsPersistent == isPersistent),
It.Is<ClaimsIdentity>(i => i.FindFirstValue(ClaimTypes.NameIdentifier) == user.Id
&& i.FindFirstValue(ClaimTypes.AuthenticationMethod) == loginProvider))).Verifiable();
response.Setup(r => r.SignOut(IdentityOptions.ExternalCookieAuthenticationType)).Verifiable();
IdentityOptions.ApplicationCookieAuthenticationScheme,
It.Is<ClaimsPrincipal>(i => i.FindFirstValue(ClaimTypes.AuthenticationMethod) == loginProvider
&& i.FindFirstValue(ClaimTypes.NameIdentifier) == user.Id),
It.Is<AuthenticationProperties>(v => v.IsPersistent == isPersistent))).Verifiable();
response.Setup(r => r.SignOut(IdentityOptions.ExternalCookieAuthenticationScheme)).Verifiable();
}
else
{
response.Setup(r => r.SignIn(
It.Is<AuthenticationProperties>(v => v.IsPersistent == isPersistent),
It.Is<ClaimsIdentity>(i => i.FindFirstValue(ClaimTypes.NameIdentifier) == user.Id))).Verifiable();
SetupSignIn(response, user.Id);
}
if (rememberClient)
{
response.Setup(r => r.SignIn(
It.Is<AuthenticationProperties>(v => v.IsPersistent == true),
It.Is<ClaimsIdentity>(i => i.FindFirstValue(ClaimTypes.Name) == user.Id
&& i.AuthenticationType == IdentityOptions.TwoFactorRememberMeCookieAuthenticationType))).Verifiable();
IdentityOptions.TwoFactorRememberMeCookieAuthenticationScheme,
It.Is<ClaimsPrincipal>(i => i.FindFirstValue(ClaimTypes.Name) == user.Id
&& i.Identities.First().AuthenticationType == IdentityOptions.TwoFactorRememberMeCookieAuthenticationType),
It.Is<AuthenticationProperties>(v => v.IsPersistent == true))).Verifiable();
}
context.Setup(c => c.Response).Returns(response.Object).Verifiable();
context.Setup(c => c.AuthenticateAsync(IdentityOptions.TwoFactorUserIdCookieAuthenticationType)).ReturnsAsync(authResult).Verifiable();
context.Setup(c => c.AuthenticateAsync(IdentityOptions.TwoFactorUserIdCookieAuthenticationScheme)).ReturnsAsync(authResult).Verifiable();
contextAccessor.Setup(a => a.HttpContext).Returns(context.Object);
var logStore = new StringBuilder();
var logger = MockHelpers.MockILogger<SignInManager<TestUser>>(logStore);
@ -412,10 +408,10 @@ namespace Microsoft.AspNet.Identity.Test
// Assert
Assert.True(result.Succeeded);
Assert.NotEqual(-1, logStore.ToString().IndexOf(expected));
manager.VerifyAll();
context.VerifyAll();
response.VerifyAll();
contextAccessor.VerifyAll();
manager.Verify();
context.Verify();
response.Verify();
contextAccessor.Verify();
}
[Fact]
@ -423,7 +419,7 @@ namespace Microsoft.AspNet.Identity.Test
{
// Setup
var user = new TestUser { UserName = "Foo" };
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
var context = new Mock<HttpContext>();
var response = new Mock<HttpResponse>();
var contextAccessor = new Mock<IHttpContextAccessor>();
@ -431,14 +427,14 @@ namespace Microsoft.AspNet.Identity.Test
var identityOptions = new IdentityOptions();
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new ClaimsIdentityFactory<TestUser, TestRole>(manager.Object, roleManager.Object, options.Object);
var claimsFactory = new UserClaimsPrincipalFactory<TestUser, TestRole>(manager.Object, roleManager.Object, options.Object);
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id).Verifiable();
context.Setup(c => c.Response).Returns(response.Object).Verifiable();
response.Setup(r => r.SignIn(
It.Is<AuthenticationProperties>(v => v.IsPersistent == true),
It.Is<ClaimsIdentity>(i => i.FindFirstValue(ClaimTypes.Name) == user.Id
&& i.AuthenticationType == IdentityOptions.TwoFactorRememberMeCookieAuthenticationType))).Verifiable();
IdentityOptions.TwoFactorRememberMeCookieAuthenticationScheme,
It.Is<ClaimsPrincipal>(i => i.FindFirstValue(ClaimTypes.Name) == user.Id
&& i.Identities.First().AuthenticationType == IdentityOptions.TwoFactorRememberMeCookieAuthenticationType),
It.Is<AuthenticationProperties>(v => v.IsPersistent == true))).Verifiable();
contextAccessor.Setup(a => a.HttpContext).Returns(context.Object).Verifiable();
options.Setup(a => a.Options).Returns(identityOptions).Verifiable();
@ -448,11 +444,11 @@ namespace Microsoft.AspNet.Identity.Test
await helper.RememberTwoFactorClientAsync(user);
// Assert
manager.VerifyAll();
context.VerifyAll();
response.VerifyAll();
contextAccessor.VerifyAll();
options.VerifyAll();
manager.Verify();
context.Verify();
response.Verify();
contextAccessor.Verify();
options.Verify();
}
[Theory]
@ -462,7 +458,7 @@ namespace Microsoft.AspNet.Identity.Test
{
// Setup
var user = new TestUser { UserName = "Foo" };
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
manager.Setup(m => m.GetTwoFactorEnabledAsync(user)).ReturnsAsync(true).Verifiable();
IList<string> providers = new List<string>();
providers.Add("PhoneNumber");
@ -470,25 +466,23 @@ namespace Microsoft.AspNet.Identity.Test
manager.Setup(m => m.SupportsUserLockout).Returns(true).Verifiable();
manager.Setup(m => m.SupportsUserTwoFactor).Returns(true).Verifiable();
manager.Setup(m => m.IsLockedOutAsync(user)).ReturnsAsync(false).Verifiable();
manager.Setup(m => m.FindByNameAsync(user.UserName)).ReturnsAsync(user).Verifiable();
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id).Verifiable();
manager.Setup(m => m.CheckPasswordAsync(user, "password")).ReturnsAsync(true).Verifiable();
var context = new Mock<HttpContext>();
var response = new Mock<HttpResponse>();
context.Setup(c => c.Response).Returns(response.Object).Verifiable();
response.Setup(r => r.SignIn(It.Is<AuthenticationProperties>(v => v.IsPersistent == isPersistent), It.Is<ClaimsIdentity>(i => i.AuthenticationType == IdentityOptions.ApplicationCookieAuthenticationType))).Verifiable();
SetupSignIn(response);
var id = new ClaimsIdentity(IdentityOptions.TwoFactorRememberMeCookieAuthenticationType);
id.AddClaim(new Claim(ClaimTypes.Name, user.Id));
var authResult = new AuthenticationResult(id, new AuthenticationProperties(), new AuthenticationDescription());
context.Setup(c => c.AuthenticateAsync(IdentityOptions.TwoFactorRememberMeCookieAuthenticationType)).ReturnsAsync(authResult).Verifiable();
var authResult = new AuthenticationResult(new ClaimsPrincipal(id), new AuthenticationProperties(), new AuthenticationDescription());
context.Setup(c => c.AuthenticateAsync(IdentityOptions.TwoFactorRememberMeCookieAuthenticationScheme)).ReturnsAsync(authResult).Verifiable();
var contextAccessor = new Mock<IHttpContextAccessor>();
contextAccessor.Setup(a => a.HttpContext).Returns(context.Object);
var roleManager = MockHelpers.MockRoleManager<TestRole>();
var identityOptions = new IdentityOptions();
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new Mock<ClaimsIdentityFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
claimsFactory.Setup(m => m.CreateAsync(user)).ReturnsAsync(new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationType)).Verifiable();
var claimsFactory = new Mock<UserClaimsPrincipalFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
claimsFactory.Setup(m => m.CreateAsync(user)).ReturnsAsync(new ClaimsPrincipal(new ClaimsIdentity(IdentityOptions.ApplicationCookieAuthenticationType))).Verifiable();
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory.Object, options.Object);
// Act
@ -496,34 +490,34 @@ namespace Microsoft.AspNet.Identity.Test
// Assert
Assert.True(result.Succeeded);
manager.VerifyAll();
context.VerifyAll();
response.VerifyAll();
contextAccessor.VerifyAll();
claimsFactory.VerifyAll();
manager.Verify();
context.Verify();
response.Verify();
contextAccessor.Verify();
claimsFactory.Verify();
}
[Theory]
[InlineData("Microsoft.AspNet.Identity.Authentication.Application")]
[InlineData("Foo")]
public void SignOutCallsContextResponseSignOut(string authenticationType)
public void SignOutCallsContextResponseSignOut(string authenticationScheme)
{
// Setup
var manager = MockHelpers.MockUserManager<TestUser>();
var context = new Mock<HttpContext>();
var response = new Mock<HttpResponse>();
context.Setup(c => c.Response).Returns(response.Object).Verifiable();
response.Setup(r => r.SignOut(authenticationType)).Verifiable();
response.Setup(r => r.SignOut(IdentityOptions.TwoFactorUserIdCookieAuthenticationType)).Verifiable();
response.Setup(r => r.SignOut(IdentityOptions.ExternalCookieAuthenticationType)).Verifiable();
response.Setup(r => r.SignOut(authenticationScheme)).Verifiable();
response.Setup(r => r.SignOut(IdentityOptions.TwoFactorUserIdCookieAuthenticationScheme)).Verifiable();
response.Setup(r => r.SignOut(IdentityOptions.ExternalCookieAuthenticationScheme)).Verifiable();
var contextAccessor = new Mock<IHttpContextAccessor>();
contextAccessor.Setup(a => a.HttpContext).Returns(context.Object);
var roleManager = MockHelpers.MockRoleManager<TestRole>();
var identityOptions = new IdentityOptions();
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
IdentityOptions.ApplicationCookieAuthenticationType = authenticationType;
var claimsFactory = new Mock<ClaimsIdentityFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
IdentityOptions.ApplicationCookieAuthenticationScheme = authenticationScheme;
var claimsFactory = new Mock<UserClaimsPrincipalFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var logStore = new StringBuilder();
var logger = MockHelpers.MockILogger<SignInManager<TestUser>>(logStore);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory.Object, options.Object, logger.Object);
@ -532,10 +526,10 @@ namespace Microsoft.AspNet.Identity.Test
helper.SignOut();
// Assert
context.VerifyAll();
response.VerifyAll();
contextAccessor.VerifyAll();
claimsFactory.VerifyAll();
context.Verify();
response.Verify();
contextAccessor.Verify();
claimsFactory.Verify();
}
[Fact]
@ -543,12 +537,10 @@ namespace Microsoft.AspNet.Identity.Test
{
// Setup
var user = new TestUser { UserName = "Foo" };
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
manager.Setup(m => m.SupportsUserLockout).Returns(true).Verifiable();
manager.Setup(m => m.IsLockedOutAsync(user)).ReturnsAsync(false).Verifiable();
manager.Setup(m => m.FindByNameAsync(user.UserName)).ReturnsAsync(user).Verifiable();
manager.Setup(m => m.CheckPasswordAsync(user, "bogus")).ReturnsAsync(false).Verifiable();
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id.ToString()).Verifiable();
var context = new Mock<HttpContext>();
var contextAccessor = new Mock<IHttpContextAccessor>();
contextAccessor.Setup(a => a.HttpContext).Returns(context.Object);
@ -556,7 +548,7 @@ namespace Microsoft.AspNet.Identity.Test
var identityOptions = new IdentityOptions();
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new Mock<ClaimsIdentityFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var claimsFactory = new Mock<UserClaimsPrincipalFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var logStore = new StringBuilder();
var logger = MockHelpers.MockILogger<SignInManager<TestUser>>(logStore);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory.Object, options.Object, logger.Object);
@ -567,9 +559,9 @@ namespace Microsoft.AspNet.Identity.Test
// Assert
Assert.False(result.Succeeded);
Assert.NotEqual(-1, logStore.ToString().IndexOf(expected));
manager.VerifyAll();
context.VerifyAll();
contextAccessor.VerifyAll();
manager.Verify();
context.Verify();
contextAccessor.Verify();
}
[Fact]
@ -585,7 +577,7 @@ namespace Microsoft.AspNet.Identity.Test
var identityOptions = new IdentityOptions();
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new Mock<ClaimsIdentityFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var claimsFactory = new Mock<UserClaimsPrincipalFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory.Object, options.Object);
// Act
@ -593,9 +585,9 @@ namespace Microsoft.AspNet.Identity.Test
// Assert
Assert.False(result.Succeeded);
manager.VerifyAll();
context.VerifyAll();
contextAccessor.VerifyAll();
manager.Verify();
context.Verify();
contextAccessor.Verify();
}
[Fact]
@ -603,7 +595,7 @@ namespace Microsoft.AspNet.Identity.Test
{
// Setup
var user = new TestUser { UserName = "Foo" };
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
var lockedout = false;
manager.Setup(m => m.AccessFailedAsync(user)).Returns(() =>
{
@ -612,7 +604,6 @@ namespace Microsoft.AspNet.Identity.Test
}).Verifiable();
manager.Setup(m => m.SupportsUserLockout).Returns(true).Verifiable();
manager.Setup(m => m.IsLockedOutAsync(user)).Returns(() => Task.FromResult(lockedout));
manager.Setup(m => m.FindByNameAsync(user.UserName)).ReturnsAsync(user).Verifiable();
manager.Setup(m => m.CheckPasswordAsync(user, "bogus")).ReturnsAsync(false).Verifiable();
var context = new Mock<HttpContext>();
var contextAccessor = new Mock<IHttpContextAccessor>();
@ -621,7 +612,7 @@ namespace Microsoft.AspNet.Identity.Test
var identityOptions = new IdentityOptions();
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new Mock<ClaimsIdentityFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var claimsFactory = new Mock<UserClaimsPrincipalFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory.Object, options.Object);
// Act
@ -630,7 +621,7 @@ namespace Microsoft.AspNet.Identity.Test
// Assert
Assert.False(result.Succeeded);
Assert.True(result.IsLockedOut);
manager.VerifyAll();
manager.Verify();
}
[Theory]
@ -640,20 +631,19 @@ namespace Microsoft.AspNet.Identity.Test
{
// Setup
var user = new TestUser { UserName = "Foo" };
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
manager.Setup(m => m.IsEmailConfirmedAsync(user)).ReturnsAsync(confirmed).Verifiable();
if (confirmed)
{
manager.Setup(m => m.CheckPasswordAsync(user, "password")).ReturnsAsync(true).Verifiable();
}
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id.ToString()).Verifiable();
var context = new Mock<HttpContext>();
var response = new Mock<HttpResponse>();
if (confirmed)
{
manager.Setup(m => m.CheckPasswordAsync(user, "password")).ReturnsAsync(true).Verifiable();
context.Setup(c => c.Response).Returns(response.Object).Verifiable();
response.Setup(r => r.SignIn(It.Is<AuthenticationProperties>(v => v.IsPersistent == false), It.IsAny<ClaimsIdentity>())).Verifiable();
SetupSignIn(response);
}
var contextAccessor = new Mock<IHttpContextAccessor>();
contextAccessor.Setup(a => a.HttpContext).Returns(context.Object);
@ -662,7 +652,7 @@ namespace Microsoft.AspNet.Identity.Test
identityOptions.SignIn.RequireConfirmedEmail = true;
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new Mock<ClaimsIdentityFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var claimsFactory = new Mock<UserClaimsPrincipalFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var logStore = new StringBuilder();
var logger = MockHelpers.MockILogger<SignInManager<TestUser>>(logStore);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory.Object, options.Object, logger.Object);
@ -676,10 +666,19 @@ namespace Microsoft.AspNet.Identity.Test
Assert.Equal(confirmed, result.Succeeded);
Assert.NotEqual(confirmed, result.IsNotAllowed);
Assert.NotEqual(-1, logStore.ToString().IndexOf(expected));
manager.VerifyAll();
context.VerifyAll();
response.VerifyAll();
contextAccessor.VerifyAll();
manager.Verify();
context.Verify();
response.Verify();
contextAccessor.Verify();
}
private static void SetupSignIn(Mock<HttpResponse> response, string userId = null, bool? isPersistent = null, string loginProvider = null)
{
response.Setup(r => r.SignIn(IdentityOptions.ApplicationCookieAuthenticationScheme,
It.Is<ClaimsPrincipal>(id =>
(userId == null || id.FindFirstValue(ClaimTypes.NameIdentifier) == userId) &&
(loginProvider == null || id.FindFirstValue(ClaimTypes.AuthenticationMethod) == loginProvider)),
It.Is<AuthenticationProperties>(v => isPersistent == null || v.IsPersistent == isPersistent))).Verifiable();
}
[Theory]
@ -689,16 +688,15 @@ namespace Microsoft.AspNet.Identity.Test
{
// Setup
var user = new TestUser { UserName = "Foo" };
var manager = MockHelpers.MockUserManager<TestUser>();
var manager = SetupUserManager(user);
manager.Setup(m => m.IsPhoneNumberConfirmedAsync(user)).ReturnsAsync(confirmed).Verifiable();
manager.Setup(m => m.GetUserIdAsync(user)).ReturnsAsync(user.Id.ToString()).Verifiable();
var context = new Mock<HttpContext>();
var response = new Mock<HttpResponse>();
if (confirmed)
{
manager.Setup(m => m.CheckPasswordAsync(user, "password")).ReturnsAsync(true).Verifiable();
context.Setup(c => c.Response).Returns(response.Object).Verifiable();
response.Setup(r => r.SignIn(It.Is<AuthenticationProperties>(v => v.IsPersistent == false), It.IsAny<ClaimsIdentity>())).Verifiable();
SetupSignIn(response);
}
var contextAccessor = new Mock<IHttpContextAccessor>();
@ -708,7 +706,7 @@ namespace Microsoft.AspNet.Identity.Test
identityOptions.SignIn.RequireConfirmedPhoneNumber = true;
var options = new Mock<IOptions<IdentityOptions>>();
options.Setup(a => a.Options).Returns(identityOptions);
var claimsFactory = new Mock<ClaimsIdentityFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var claimsFactory = new Mock<UserClaimsPrincipalFactory<TestUser, TestRole>>(manager.Object, roleManager.Object, options.Object);
var logStore = new StringBuilder();
var logger = MockHelpers.MockILogger<SignInManager<TestUser>>(logStore);
var helper = new SignInManager<TestUser>(manager.Object, contextAccessor.Object, claimsFactory.Object, options.Object, logger.Object);
@ -721,11 +719,10 @@ namespace Microsoft.AspNet.Identity.Test
Assert.Equal(confirmed, result.Succeeded);
Assert.NotEqual(confirmed, result.IsNotAllowed);
Assert.NotEqual(-1, logStore.ToString().IndexOf(expected));
manager.VerifyAll();
context.VerifyAll();
response.VerifyAll();
contextAccessor.VerifyAll();
manager.Verify();
context.Verify();
response.Verify();
contextAccessor.Verify();
}
}
}

View File

@ -4,15 +4,14 @@
using System;
using System.Linq;
using System.Security.Claims;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.Framework.OptionsModel;
using Moq;
using Xunit;
using Microsoft.Framework.OptionsModel;
namespace Microsoft.AspNet.Identity.Test
{
public class ClaimsIdentityFactoryTest
public class UserClaimsPrincipalFactoryTest
{
[Fact]
public async Task CreateIdentityNullChecks()
@ -21,10 +20,10 @@ namespace Microsoft.AspNet.Identity.Test
var roleManager = MockHelpers.MockRoleManager<TestRole>().Object;
var options = new Mock<IOptions<IdentityOptions>>();
Assert.Throws<ArgumentNullException>("optionsAccessor",
() => new ClaimsIdentityFactory<TestUser, TestRole>(userManager, roleManager, options.Object));
() => new UserClaimsPrincipalFactory<TestUser, TestRole>(userManager, roleManager, options.Object));
var identityOptions = new IdentityOptions();
options.Setup(a => a.Options).Returns(identityOptions);
var factory = new ClaimsIdentityFactory<TestUser, TestRole>(userManager, roleManager, options.Object);
var factory = new UserClaimsPrincipalFactory<TestUser, TestRole>(userManager, roleManager, options.Object);
await Assert.ThrowsAsync<ArgumentNullException>("user",
async () => await factory.CreateAsync(null));
}
@ -74,14 +73,16 @@ namespace Microsoft.AspNet.Identity.Test
var options = new Mock<IOptions<IdentityOptions>>();
var identityOptions = new IdentityOptions();
options.Setup(a => a.Options).Returns(identityOptions);
var factory = new ClaimsIdentityFactory<TestUser, TestRole>(userManager.Object, roleManager.Object, options.Object);
var factory = new UserClaimsPrincipalFactory<TestUser, TestRole>(userManager.Object, roleManager.Object, options.Object);
// Act
var identity = await factory.CreateAsync(user);
var principal = await factory.CreateAsync(user);
var identity = principal.Identities.First();
// Assert
var manager = userManager.Object;
Assert.NotNull(identity);
Assert.Equal(1, principal.Identities.Count());
Assert.Equal(IdentityOptions.ApplicationCookieAuthenticationType, identity.AuthenticationType);
var claims = identity.Claims.ToList();
Assert.NotNull(claims);