. net основных сердечников с несколькими источниками и несколькими заголовками - PullRequest
1 голос
/ 09 января 2020

У меня разные источники с разными заголовками, необходимо разрешить с помощью политик cors.

Например:

1 / - Источник: ab c .com - Заголовки: A, B

2 / - Происхождение: bcd.com - Заголовки: A, C

Это мой код:

services.AddCors(opt =>
            {
                opt.AddPolicy(
                    "ABC",
                    builder =>
                    {
                      builder.WithOrigins("abc.com")
                          .WithHeaders("A", "B");
                    });
        opt.AddPolicy(
                    "BCD",
                    builder =>
                    {
                      builder.WithOrigins("bcd.com")
                          .WithHeaders("A", "C");
                    });
        });

и в Startup.Configure:

builder.UseCors("ABC");
builder.UseCors("BCD");

Все с источником работает нормально, но проблема в заголовках. Заголовки работают только для первой политики. В приведенном выше коде заголовки работают нормально с Policy AB C. Я могу отправить запрос с заголовком A или заголовком B, как и ожидалось, но для политики BCD, если я отправлю запрос без заголовков. Это работало, но если я отправляю запрос с заголовком A или C, это не работает.

И если я перемещаю BCD поверх AB C, заголовки BCD работают нормально.

1 Ответ

0 голосов
/ 09 января 2020

Вы можете создать пользовательское промежуточное ПО, которое проверяет политики на основе источника запроса.

public class CustomCorsMiddleware
{
    private readonly RequestDelegate _next;
    private readonly ICorsService _corsService;
    private readonly ICorsPolicyProvider _corsPolicyProvider;
    private readonly IDictionary<string, string> _policies;

    public CustomCorsMiddleware(
        RequestDelegate next,
        ICorsService corsService,
        ICorsPolicyProvider policyProvider,
        IDictionary<string, string> policies)
    {
        _next = next ?? throw new ArgumentNullException(nameof(next));
        _corsService = corsService ?? throw new ArgumentNullException(nameof(corsService));
        _corsPolicyProvider = policyProvider ?? throw new ArgumentNullException(nameof(policyProvider));
        _policies = policies;
    }

    public async Task Invoke(HttpContext context)
    {
        if (context.Request.Headers.ContainsKey(CorsConstants.Origin))
        {
            string policyName;
            bool hasPolicy = this._policies.TryGetValue(context.Request.Headers[CorsConstants.Origin], out policyName);

            if (!String.IsNullOrEmpty(policyName) && hasPolicy)
            {
                CorsPolicy corsPolicy = await _corsPolicyProvider.GetPolicyAsync(context, policyName);
                if (corsPolicy != null)
                {
                    var corsResult = _corsService.EvaluatePolicy(context, corsPolicy);
                    _corsService.ApplyResult(corsResult, context.Response);

                    var accessControlRequestMethod = context.Request.Headers[CorsConstants.AccessControlRequestMethod];
                    if (string.Equals(
                            context.Request.Method,
                            CorsConstants.PreflightHttpMethod,
                            StringComparison.OrdinalIgnoreCase) &&
                            !StringValues.IsNullOrEmpty(accessControlRequestMethod))
                    {
                        // Since there is a policy which was identified,
                        // always respond to preflight requests.
                        context.Response.StatusCode = StatusCodes.Status204NoContent;
                        return;
                    }
                }
            }
        }

        await _next(context);
    }
}

В ваших файлах Startup.cs вы должны определить политики и предоставить сопоставления для промежуточного программного обеспечения.

public void ConfigureServices(IServiceCollection services) 
{
  services.AddCors(opt => {
    opt.AddPolicy(
      "ABC",
      builder => {
        builder.WithOrigins("abc.com")
          .WithHeaders("A", "B");
      }
    );
    opt.AddPolicy(
      "BCD",
      builder => {
        builder.WithOrigins("bcd.com")
          .WithHeaders("A", "C");
      }
    );
  });
}

public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
    IDictionary<string, string> mappings = new Dictionary<string, string>();
    mappings["abc.com"] = "ABC";
    mappings["bcd.com"] = "BCD";
    app.UseMiddleware<CustomCorsMiddleware>(mappings);
}

Надеюсь, это поможет!

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...