Asp.net
Web API 2 身份。/Token 總是返回 404 錯誤
我在採用 Web API 2 身份時遇到了一些問題。在項目中。
我添加 StartUp.cs
像這樣:
using Microsoft.Owin; using Owin; [assembly: OwinStartup(typeof(MyNamespace.Startup))] namespace MyNamespace { public partial class Startup { public void Configuration(IAppBuilder app) { ConfigureAuth(app); } } }之後,我添加部分類以啟用令牌授權:
namespace MyNamespace { public partial class Startup { public static OAuthAuthorizationServerOptions OAuthOptions { get; private set; } public static string PublicClientId { get; private set; } public void ConfigureAuth(IAppBuilder app) { app.UseCookieAuthentication(new CookieAuthenticationOptions()); app.UseExternalSignInCookie(DefaultAuthenticationTypes.ExternalCookie); PublicClientId = "self"; OAuthOptions = new OAuthAuthorizationServerOptions { TokenEndpointPath = new PathString("/Token"), Provider = new ApplicationOAuthProvider(PublicClientId), AuthorizeEndpointPath = new PathString("/api/Account/ExternalLogin"), AccessTokenExpireTimeSpan = TimeSpan.FromDays(14) }; app.UseOAuthBearerTokens(OAuthOptions); } } }同樣,我實現了使用者功能(如 UserStore、UserManager)。
我從範例中採用“ExternalLogin”方法並進行更改。
// GET api/Account/ExternalLogin [OverrideAuthentication] [HostAuthentication(DefaultAuthenticationTypes.ExternalCookie)] [AllowAnonymous] [Route("ExternalLogin", Name = "ExternalLogin")] public async Task<IHttpActionResult> GetExternalLogin(string provider, string error = null) { if (error != null) { return Redirect(Url.Content("~/") + "#error=" + Uri.EscapeDataString(error)); } if (!User.Identity.IsAuthenticated) { return new ChallengeResult(provider, this); } ExternalLoginData externalLogin = ExternalLoginData.FromIdentity(User.Identity as ClaimsIdentity); if (externalLogin == null) { return InternalServerError(); } if (externalLogin.LoginProvider != provider) { Authentication.SignOut(DefaultAuthenticationTypes.ExternalCookie); return new ChallengeResult(provider, this); } User user = await UserManager.FindAsync(new UserLoginInfo(externalLogin.LoginProvider, externalLogin.ProviderKey)); bool hasRegistered = user != null; if (hasRegistered) { Authentication.SignOut(DefaultAuthenticationTypes.ExternalCookie); ClaimsIdentity oAuthIdentity = await UserManager.CreateIdentityAsync(user, OAuthDefaults.AuthenticationType); ClaimsIdentity cookieIdentity = await UserManager.CreateIdentityAsync(user, CookieAuthenticationDefaults.AuthenticationType); AuthenticationProperties properties = ApplicationOAuthProvider.CreateProperties(user.UserName); Authentication.SignIn(properties, oAuthIdentity, cookieIdentity); } else { IEnumerable<Claim> claims = externalLogin.GetClaims(); ClaimsIdentity identity = new ClaimsIdentity(claims, OAuthDefaults.AuthenticationType); Authentication.SignIn(identity); } return Ok(); }之後我執行我的應用程序並嘗試像這樣登錄到應用程序:
var loginData = { grant_type: 'password', username: "test", password: "test" }; $.ajax({ type: 'POST', url: '/Token', data: loginData }).done(function (data) { alert(data.username); sessionStorage.setItem(tokenKey, data.access_token); }).fail(function (data) { alert(data); });我收到了 404 錯誤。我嘗試通過提琴手向 /Token 發送自定義請求,結果相同。然後我檢查我的 api/Account/ExternalLogin 操作是否可用,此響應 401 狀態程式碼。我檢查引用 Owin,Microsoft.Owin 都正確。有什麼問題?我哪裡有問題?
UPS:
public class ApplicationOAuthProvider : OAuthAuthorizationServerProvider { private readonly string _publicClientId; [Dependency] public ICustomUserManager UserManager { get;set; } public ApplicationOAuthProvider(string publicClientId) { if (publicClientId == null) { throw new ArgumentNullException("publicClientId"); } _publicClientId = publicClientId; } public override async Task GrantResourceOwnerCredentials(OAuthGrantResourceOwnerCredentialsContext context) { var userManager = context.OwinContext.GetUserManager<ICustomUserManager>(); User user = await userManager.FindAsync(context.UserName, context.Password); if (user == null) { context.SetError("invalid_grant", "The user name or password is incorrect."); return; } ClaimsIdentity oAuthIdentity = await UserManager.CreateIdentityAsync(user, OAuthDefaults.AuthenticationType); ClaimsIdentity cookieIdentity = await UserManager.CreateIdentityAsync(user, CookieAuthenticationDefaults.AuthenticationType); AuthenticationProperties properties = CreateProperties(user.UserName); AuthenticationTicket ticket = new AuthenticationTicket(oAuthIdentity, properties); var val = context.Validated(ticket); context.Request.Context.Authentication.SignIn(cookieIdentity); } public override Task TokenEndpoint(OAuthTokenEndpointContext context) { foreach (KeyValuePair<string, string> property in context.Properties.Dictionary) { context.AdditionalResponseParameters.Add(property.Key, property.Value); } return Task.FromResult<object>(null); } public override Task ValidateClientAuthentication(OAuthValidateClientAuthenticationContext context) { // Resource owner password credentials does not provide a client ID. if (context.ClientId == null) { context.Validated(); } return Task.FromResult<object>(null); } public override Task ValidateClientRedirectUri(OAuthValidateClientRedirectUriContext context) { if (context.ClientId == _publicClientId) { Uri expectedRootUri = new Uri(context.Request.Uri, "/"); if (expectedRootUri.AbsoluteUri == context.RedirectUri) { context.Validated(); } } return Task.FromResult<object>(null); } public static AuthenticationProperties CreateProperties(string userName) { IDictionary<string, string> data = new Dictionary<string, string> { { "userName", userName } }; return new AuthenticationProperties(data); } }
我在這個問題上弄清楚了。
OAuthAuthorizationServerOptions有財產AllowInsecureHttp。我使用了不安全的 http 協議。在這種情況下,您可以設置AllowInsecureHttp = true,也可以將 Https 過濾器添加到 Filters 管道。
我在生產環境中遇到了同樣的問題,但在本地(IIS Express)沒有。沒有什麼幫助
web.config。解決方案是將明確的 NuGet 包引用添加到:Microsoft.Owin.Host.SystemWeb