Asp.net core OAuthMiddleware:the';认证方案';必须提供选项
各位! 我正试图用ASP.NET内核实现OpenIDDict,以保护我的Web API。但是,在遵循OpenIDDict github页面中的说明后,我在浏览器中遇到了以下错误: ArgumentException:必须提供“AuthenticationScheme”选项。 Microsoft.AspNetCore.Authentication.OAuth.OAuthMiddleware..ctor(RequestDelegate next、IDataProtectionProvider dataProtectionProvider、ILoggerFactory loggerFactory、UrlEncoder编码器、IOptions共享选项、IOptions选项) 开发环境和软件版本:Asp.net core OAuthMiddleware:the';认证方案';必须提供选项,asp.net-core,Asp.net Core,各位! 我正试图用ASP.NET内核实现OpenIDDict,以保护我的Web API。但是,在遵循OpenIDDict github页面中的说明后,我在浏览器中遇到了以下错误: ArgumentException:必须提供“AuthenticationScheme”选项。 Microsoft.AspNetCore.Authentication.OAuth.OAuthMiddleware..ctor(RequestDelegate next、IDataProtectionProvider dat
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Security.Claims;
using System.Threading.Tasks;
using AspNet.Security.OpenIdConnect.Extensions;
using AspNet.Security.OpenIdConnect.Primitives;
using AspNet.Security.OpenIdConnect.Server;
using AuthorizationServer.Models;
using Microsoft.AspNetCore.Authentication;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Http.Authentication;
using Microsoft.AspNetCore.Identity;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Options;
using OpenIddict.Core;
namespace AuthorizationServer.Controllers
{
public class AuthorizationController : Controller
{
private readonly IOptions<IdentityOptions> _identityOptions;
private readonly SignInManager<ApplicationUser> _signInManager;
private readonly UserManager<ApplicationUser> _userManager;
public AuthorizationController(
IOptions<IdentityOptions> identityOptions,
SignInManager<ApplicationUser> signInManager,
UserManager<ApplicationUser> userManager)
{
_identityOptions = identityOptions;
_signInManager = signInManager;
_userManager = userManager;
}
[HttpPost("~/connect/token"), Produces("application/json")]
public async Task<IActionResult> Exchange(OpenIdConnectRequest request)
{
Debug.Assert(request.IsTokenRequest(),
"The OpenIddict binder for ASP.NET Core MVC is not registered. " +
"Make sure services.AddOpenIddict().AddMvcBinders() is correctly called.");
if (request.IsPasswordGrantType())
{
var user = await _userManager.FindByNameAsync(request.Username);
if (user == null)
{
return BadRequest(new OpenIdConnectResponse
{
Error = OpenIdConnectConstants.Errors.InvalidGrant,
ErrorDescription = "The username/password couple is invalid."
});
}
// Ensure the user is allowed to sign in.
if (!await _signInManager.CanSignInAsync(user))
{
return BadRequest(new OpenIdConnectResponse
{
Error = OpenIdConnectConstants.Errors.InvalidGrant,
ErrorDescription = "The specified user is not allowed to sign in."
});
}
// Reject the token request if two-factor authentication has been enabled by the user.
if (_userManager.SupportsUserTwoFactor && await _userManager.GetTwoFactorEnabledAsync(user))
{
return BadRequest(new OpenIdConnectResponse
{
Error = OpenIdConnectConstants.Errors.InvalidGrant,
ErrorDescription = "The specified user is not allowed to sign in."
});
}
// Ensure the user is not already locked out.
if (_userManager.SupportsUserLockout && await _userManager.IsLockedOutAsync(user))
{
return BadRequest(new OpenIdConnectResponse
{
Error = OpenIdConnectConstants.Errors.InvalidGrant,
ErrorDescription = "The username/password couple is invalid."
});
}
// Ensure the password is valid.
if (!await _userManager.CheckPasswordAsync(user, request.Password))
{
if (_userManager.SupportsUserLockout)
{
await _userManager.AccessFailedAsync(user);
}
return BadRequest(new OpenIdConnectResponse
{
Error = OpenIdConnectConstants.Errors.InvalidGrant,
ErrorDescription = "The username/password couple is invalid."
});
}
if (_userManager.SupportsUserLockout)
{
await _userManager.ResetAccessFailedCountAsync(user);
}
// Create a new authentication ticket.
var ticket = await CreateTicketAsync(request, user);
return SignIn(ticket.Principal, ticket.Properties, ticket.AuthenticationScheme);
}
return BadRequest(new OpenIdConnectResponse
{
Error = OpenIdConnectConstants.Errors.UnsupportedGrantType,
ErrorDescription = "The specified grant type is not supported."
});
}
private async Task<AuthenticationTicket> CreateTicketAsync(OpenIdConnectRequest request, ApplicationUser user)
{
// Create a new ClaimsPrincipal containing the claims that
// will be used to create an id_token, a token or a code.
var principal = await _signInManager.CreateUserPrincipalAsync(user);
// Create a new authentication ticket holding the user identity.
var ticket = new AuthenticationTicket(principal,
new AuthenticationProperties(),
OpenIdConnectServerDefaults.AuthenticationScheme);
// Set the list of scopes granted to the client application.
ticket.SetScopes(new[]
{
OpenIdConnectConstants.Scopes.OpenId,
OpenIdConnectConstants.Scopes.Email,
OpenIdConnectConstants.Scopes.Profile,
OpenIddictConstants.Scopes.Roles
}.Intersect(request.GetScopes()));
ticket.SetResources("resource-server");
// Note: by default, claims are NOT automatically included in the access and identity tokens.
// To allow OpenIddict to serialize them, you must attach them a destination, that specifies
// whether they should be included in access tokens, in identity tokens or in both.
foreach (var claim in ticket.Principal.Claims)
{
// Never include the security stamp in the access and identity tokens, as it's a secret value.
if (claim.Type == _identityOptions.Value.ClaimsIdentity.SecurityStampClaimType)
{
continue;
}
var destinations = new List<string>
{
OpenIdConnectConstants.Destinations.AccessToken
};
// Only add the iterated claim to the id_token if the corresponding scope was granted to the client application.
// The other claims will only be added to the access_token, which is encrypted when using the default format.
if ((claim.Type == OpenIdConnectConstants.Claims.Name && ticket.HasScope(OpenIdConnectConstants.Scopes.Profile)) ||
(claim.Type == OpenIdConnectConstants.Claims.Email && ticket.HasScope(OpenIdConnectConstants.Scopes.Email)) ||
(claim.Type == OpenIdConnectConstants.Claims.Role && ticket.HasScope(OpenIddictConstants.Claims.Roles)))
{
destinations.Add(OpenIdConnectConstants.Destinations.IdentityToken);
}
claim.SetDestinations(destinations);
}
return ticket;
}
}
}
使用System.Collections.Generic;
使用系统诊断;
使用System.Linq;
使用System.Security.Claims;
使用System.Threading.Tasks;
使用AspNet.Security.OpenIdConnect.Extensions;
使用AspNet.Security.OpenIdConnect.Primitives;
使用AspNet.Security.OpenIdConnect.Server;
使用AuthorizationServer.Models;
使用Microsoft.AspNetCore.Authentication;
使用Microsoft.AspNetCore.Builder;
使用Microsoft.AspNetCore.Http.Authentication;
使用Microsoft.AspNetCore.Identity;
使用Microsoft.AspNetCore.Mvc;
使用Microsoft.Extensions.Options;
使用OpenIddict.Core;
命名空间授权服务器.控制器
{
公共类授权控制器:控制器
{
私有只读IOptions _identityOptions;
专用只读签名管理器\u签名管理器;
私有只读用户管理器_UserManager;
公共授权控制器(
IOptions标识选项,
SignInManager SignInManager,
用户管理器(用户管理器)
{
_identityOptions=identityOptions;
_signInManager=signInManager;
_userManager=userManager;
}
[HttpPost(“~/connect/token”),生成(“应用程序/json”)]
公共异步任务交换(OpenIdConnectRequest)
{
Assert(request.IsTokenRequest(),
“ASP.NET Core MVC的OpenIddict活页夹未注册。”+
“确保正确调用了services.AddOpenIddict().AddMvcBinders()”);
if(request.IsPasswordGrantType())
{
var user=await\u userManager.FindByNameAsync(request.Username);
if(user==null)
{
返回BadRequest(新的OpenIdConnectResponse
{
Error=OpenIdConnectConstants.Errors.InvalidGrant,
ErrorDescription=“用户名/密码对无效。”
});
}
//确保允许用户登录。
如果(!wait _signInManager.CanSignInAsync(用户))
{
返回BadRequest(新的OpenIdConnectResponse
{
Error=OpenIdConnectConstants.Errors.InvalidGrant,
ErrorDescription=“不允许指定的用户登录。”
});
}
//如果用户已启用双因素身份验证,则拒绝令牌请求。
if(_userManager.SupportsUserTwoFactor&&wait_userManager.gettwofacturenabledasync(用户))
{
返回BadRequest(新的OpenIdConnectResponse
{
Error=OpenIdConnectConstants.Errors.InvalidGrant,
ErrorDescription=“不允许指定的用户登录。”
});
}
//确保用户未被锁定。
if(_userManager.SupportsUserLockout&wait_userManager.IsLockedOutAsync(用户))
{
返回BadRequest(新的OpenIdConnectResponse
{
Error=OpenIdConnectConstants.Errors.InvalidGrant,
ErrorDescription=“用户名/密码对无效。”
});
}
//确保密码有效。
如果(!wait_userManager.CheckPasswordAsync(user,request.Password))
{
if(_userManager.SupportsUserLockout)
{
wait_userManager.AccessFailedAsync(用户);
}
返回BadRequest(新的OpenIdConnectResponse
{
Error=OpenIdConnectConstants.Errors.InvalidGrant,
ErrorDescription=“用户名/密码对无效。”
});
}
if(_userManager.SupportsUserLockout)
{
wait_userManager.ResetAccessFailedCountAsync(用户);
}
//创建新的身份验证票证。
var ticket=wait CreateTicketAsync(请求,用户);
返回签名(ticket.Principal、ticket.Properties、ticket.AuthenticationScheme);
}
返回BadRequest(新的OpenIdConnectResponse
{
Error=OpenIdConnectConstants.Errors.UnsupportedGrantType,
ErrorDescription=“不支持指定的授权类型。”
});
}
专用异步任务CreateTicketAsync(OpenIdConnectRequest请求,ApplicationUser用户)
{
//创建一个新的ClaimsPrincipal,其中包含
//将用于创建id_令牌、令牌或代码。
var principal=await _signInManager.CreateUserPrincipalAsync(用户);
//创建一个新的au