当前位置:  开发笔记 > 后端 > 正文

OAuth调用TokenEndpointPath导致找不到路径控制器

如何解决《OAuth调用TokenEndpointPath导致找不到路径控制器》经验,为你挑选了0个好方法。

遵循本手册并构建了令牌认证.它在调试模式下完美运行,但在发布模式下,调用TokenEndpointPath会导致调用

未找到路径'/ bps/oauth/token'的控制器或未实现IController.

由于Web.config文件中的WebBaseUri,URI具有/ bps/part.






Startup类如下:

    public class Startup
{
    public void Configuration(IAppBuilder app)
    {
        app.Use();

        var container = new WindsorContainer().Install(new WindsorInstaller());
        container.Register(Component.For().Instance(app));
        var httpDependencyResolver = new WindsorHttpDependencyResolver(container);

        HttpConfiguration config = new HttpConfiguration();
        config.MapHttpAttributeRoutes();

        config.DependencyResolver = httpDependencyResolver;
        app.CreatePerOwinContext(() => container.Resolve());
        GlobalConfiguration.Configuration.Services.Replace(typeof(IHttpControllerActivator), new WindsorControllerActivator(container));


        ConfigureOAuthTokenGeneration(app, container);

        ConfigureOAuthTokenConsumption(app);

        app.UseWebApi(config);
    }

    private void ConfigureOAuthTokenGeneration(IAppBuilder app, IWindsorContainer container)
    {
        var OAuthServerOptions = new OAuthAuthorizationServerOptions
        {
            //For Dev enviroment only (on production should be AllowInsecureHttp = false)
            AllowInsecureHttp = true,
            TokenEndpointPath = new PathString("/oauth/token"),
            AccessTokenExpireTimeSpan = TimeSpan.FromDays(1),
            Provider = container.Resolve(),
            AccessTokenFormat = container.Resolve(),
        };

        app.UseOAuthAuthorizationServer(OAuthServerOptions);
    }

    private void ConfigureOAuthTokenConsumption(IAppBuilder app)
    {
        var issuer = ConfigurationManager.AppSettings["ServerAddress"];
        string audienceId = ConfigurationManager.AppSettings["AudienceId"];
        byte[] audienceSecret = TextEncodings.Base64Url.Decode(ConfigurationManager.AppSettings["AudienceSecret"]);

        // Api controllers with an [Authorize] attribute will be validated with JWT
        app.UseJwtBearerAuthentication(
            new JwtBearerAuthenticationOptions
            {
                AuthenticationMode = AuthenticationMode.Active,
                AllowedAudiences = new[] { audienceId },
                IssuerSecurityTokenProviders = new IIssuerSecurityTokenProvider[]
                {
                    new SymmetricKeyIssuerSecurityTokenProvider(issuer, audienceSecret)
                }
            });
    }
}

这是为Provider属性解析的IOAuthAuthorizationServerProvider的实现:

    public class OAuthService : OAuthAuthorizationServerProvider
{
    private readonly IApplicationUserService _userService;
    private readonly ICredentialsValidatior _credentialsValidatior;

    public OAuthService(IApplicationUserService userService, ICredentialsValidatior credentialsValidatior)
    {
        this._userService = userService;
        _credentialsValidatior = credentialsValidatior;
    }

    public override Task ValidateClientAuthentication(OAuthValidateClientAuthenticationContext context)
    {
        context.Validated();
        return Task.FromResult(null);
    }

    public override async Task GrantResourceOwnerCredentials(OAuthGrantResourceOwnerCredentialsContext context)
    {
        var allowedOrigin = context.OwinContext.Get("as:clientAllowedOrigin");
        if (allowedOrigin == null) allowedOrigin = "*";
        context.OwinContext.Response.Headers.Add("Access-Control-Allow-Origin", new[] { allowedOrigin });

        /* Some user validation logick */

        var user = await _userService.FindByNameAsync(context.UserName);

        ClaimsIdentity oAuthIdentity = await GenerateUserIdentityAsync(user);

        var ticket = new AuthenticationTicket(oAuthIdentity, null);

        context.Validated(ticket);
    }

    private async Task GenerateUserIdentityAsync(ApplicationUser user)
    {
        const string authenticationType = "JWT";
        var userIdentity = await _userService.CreateIdentityAsync(user, authenticationType);

        return userIdentity;
    }
}


正在为AccessTokenFormat属性解析的类:

    public class CustomJwtFormat : ISecureDataFormat
{
    private readonly string _issuer;

    public CustomJwtFormat(string issuer)
    {
        _issuer = issuer;
    }

    public string Protect(AuthenticationTicket data)
    {
        if (data == null)
        {
            throw new ArgumentNullException("data");
        }

        string audienceId = ConfigurationManager.AppSettings["AudienceId"];

        string symmetricKeyAsBase64 = ConfigurationManager.AppSettings["AudienceSecret"];

        var keyByteArray = TextEncodings.Base64Url.Decode(symmetricKeyAsBase64);

        var signingKey = new HmacSigningCredentials(keyByteArray);

        var issued = data.Properties.IssuedUtc;

        var expires = data.Properties.ExpiresUtc;

        var token = new JwtSecurityToken(_issuer, audienceId, data.Identity.Claims, issued.Value.UtcDateTime, expires.Value.UtcDateTime, signingKey);

        var handler = new JwtSecurityTokenHandler();

        var jwt = handler.WriteToken(token);

        return jwt;
    }

    public AuthenticationTicket Unprotect(string protectedText)
    {
        throw new NotImplementedException();
    }
}

此代码在我的本地计算机上运行,​​并在调试和发布模式下正常运行.

将此代码以调试模式发布到开发服务器时,会出现此问题.

我发现在本地计算机上将AllowInsecureHttp属性切换为false会导致此错误,但dev服务器上的版本完全相同.我检查了IL代码,并且AllowInsecureHttp属性设置为1.

UPDATE

我试图将/ bps/part添加到TokenEndpointPath但它没有帮助.

由于未知原因,它甚至在本地也不起作用.我发现项目的设置是这样的 在此输入图像描述

不幸的是,我试图在开发服务器上找到这些设置,因为我缺乏关于IIS的知识,我没有找到任何东西.

我还尝试检查OWIN管道,发现通过管道传递的URL与Startup.cs中配置的URL相同.

在此输入图像描述

我还在StackOverflow上发现了这个问题.

推荐阅读
k78283381
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有