如果授权失败并且仅返回401错误代码,是否可以忽略所有身份验证方案?

时间:2019-07-19 09:30:16

标签: c# asp.net-core .net-core

我正在开发一个Web-api,该API对我们的另一个应用程序使用某种授权,以验证用户仍在登录并且可以继续执行他们所请求的操作。但是,当用户未通过身份验证时,服务器将响应500内部服务器错误,可以在下面找到堆栈跟踪。 我似乎无法使配置进入正确的状态。从堆栈跟踪中,我可以看出它尝试回退到一些默认的身份验证方案,该方案尚未定义,理想情况下不感兴趣,因为我们一直希望对第三方进行授权,如果返回第三方,则只会失败错误。

Startup.cs

public void ConfigureServices(IServiceCollection services)
{
    services.AddScoped<IAuthService>(_ =>
        new AuthService(damInfo.BaseUrl, damInfo.SystemUsername, damInfo.SystemPassword));
    services.AddScoped<IAuthorizationHandler, AuthenticationHandler>();

    services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);

    services.AddAuthorization(options =>
    {
        options.AddPolicy("ServicePolicy", policy =>
            policy.Requirements.Add(new ServiceRequirement("")));
        /*options.DefaultPolicy = new AuthorizationPolicyBuilder().AddAuthenticationSchemes(Constants.NoOp).RequireAuthenticatedUser().Build(); // keep#1#*/
        options.InvokeHandlersAfterFailure = false;
    });

    services.AddAuthentication(options =>
    {
        options.DefaultScheme = Constants.NoOp;
        options.DefaultChallengeScheme = Constants.NoOp;
    });
}

public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
    if (env.IsDevelopment())
        app.UseDeveloperExceptionPage();
    else
        app.UseHsts();

    app.UseCors(builder =>
    {
        builder.AllowAnyHeader();
        builder.AllowAnyMethod();
        builder.AllowAnyOrigin();
    });

    app.UseHttpsRedirection();
    app.UseMvc();
}

政策:

using Microsoft.AspNetCore.Authorization;

namespace Core.Services.Authentication
{
    public class ServiceRequirement : IAuthorizationRequirement
    {
        public string CurrentToken { get; private set; }

        public ServiceRequirement(string token)
        {
            CurrentToken = token;
        }       
    }
}

授权属性:

[Authorize(Policy = "ServicePolicy")]

身份验证处理程序:

using System.Net.Http.Headers;
using System.Threading.Tasks;
using Digizuite.Services.Authentication;
using Microsoft.AspNetCore.Authorization;
using Microsoft.Extensions.Primitives;
using Microsoft.Net.Http.Headers;

namespace Core.Services.Authentication
{
    public class AuthenticationHandler : AuthorizationHandler<ServiceRequirement>
    {
        readonly IAuthService _authService;

        /// <summary>
        /// Authentication handler that check if user is logged in
        /// </summary>
        /// <param name="authService"></param>
        public AuthenticationHandler(IAuthService authService)
        {
            _authService = authService;
        }

        /// <summary>
        /// Handle requirement and check isLoggedIn
        /// </summary>
        /// <param name="context"></param>
        /// <param name="requirement"></param>
        /// <returns></returns>
        protected override async Task HandleRequirementAsync(AuthorizationHandlerContext context,
            ServiceRequirement requirement)
        {
            var authFilterCtx = (Microsoft.AspNetCore.Mvc.Filters.AuthorizationFilterContext)context.Resource;
            var httpContext = authFilterCtx.HttpContext;

            var headers = httpContext.Request.Headers[HeaderNames.Authorization];

            if (StringValues.IsNullOrEmpty(headers) == true)
            {
                context.Fail();
            }
            else
            {
                var auth = AuthenticationHeaderValue.Parse(headers);
                var loginResponse = _authService.IsLoggedInRequest(auth.Parameter).Result;
                if (loginResponse.IsLoggedIn == false)
                {
                    context.Fail();
                }
                else
                {
                    context.Succeed(requirement);
                }
            }
        }
    }
}

StackTrace:

fail: Microsoft.AspNetCore.Server.Kestrel[13]
      Connection id "0HLOC48NR5MP4", Request id "0HLOC48NR5MP4:00000001": An unhandled exception was thrown by the application.
System.InvalidOperationException: No authenticationScheme was specified, and there was no DefaultChallengeScheme found.
   at Microsoft.AspNetCore.Authentication.AuthenticationService.ChallengeAsync(HttpContext context, String scheme, AuthenticationProperties properties)
   at Microsoft.AspNetCore.Mvc.ChallengeResult.ExecuteResultAsync(ActionContext context)
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.InvokeResultAsync(IActionResult result)
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.InvokeAlwaysRunResultFilters()
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.InvokeFilterPipelineAsync()
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.InvokeAsync()
   at Microsoft.AspNetCore.Builder.RouterMiddleware.Invoke(HttpContext httpContext)
   at Microsoft.AspNetCore.Cors.Infrastructure.CorsMiddleware.Invoke(HttpContext context)
   at Microsoft.AspNetCore.Authentication.AuthenticationMiddleware.Invoke(HttpContext context)
   at Digizuite.Logging2.LogClient.LoggerRequestMiddleware.InvokeAsync(HttpContext context, RequestDelegate next) in C:\dev\digizuite.core\Libs\LogClient\LoggerRequestMiddleware.cs:line 40
   at Microsoft.AspNetCore.Builder.UseMiddlewareExtensions.<>c__DisplayClass5_1.<<UseMiddlewareInterface>b__1>d.MoveNext()

0 个答案:

没有答案