.Net Core Cors中间件的深入讲解(2)

打开CORS源码,主要的是CorsMiddleware、CorsOptions、CorsPolicy、CorsPolicyBuilder、CorsResult、CorsService这几个类。

CorsPolicy:就是我们在Startup中的配置,如允许哪些域名可以跨域请求,允许哪些跨域请求方式,允许哪些额外的请求头,每个配置对应一个名称。
       services.AddCors(options => options.AddPolicy("CorsTest", p => p.AllowAnyOrigin().AllowAnyHeader().AllowAnyMethod()));

CorsOptions:中包含一个字典IDictionary<string, CorsPolicy> PolicyMap,一个项目可能有过个Cors配置,所以这个CorsOptions就是通过配置名称管理这些配置的。

CorsPolicyBuilder:通过它来构造CorsPolicy。

CorsResult:是验证跨域过程得到的结果。如在第一次Options请求时,客户端发送了Origi::8089,服务器会返回Access-Control-Allow-Origin::8089,服务器验证:8089这个域名是否允许跨域,如果允许就将“:8089”这个值存储到CorsResult的AllowedHeaders中,在请求(第一次请求)返回的时候将这些加到HTTP请求头中。

CorsMiddleware:Cors中间件类,主要方法就是Invoke,每次HTTP请求都会调用这个方法。

public async Task Invoke(HttpContext context) {//判断HTTP请求头是否有Origin,由此判断是不是跨域请求 if (context.Request.Headers.ContainsKey(CorsConstants.Origin)) { var corsPolicy = _policy ?? await _corsPolicyProvider?.GetPolicyAsync(context, _corsPolicyName); if (corsPolicy != null) { var accessControlRequestMethod = context.Request.Headers[CorsConstants.AccessControlRequestMethod];            //如果是跨域请求 判断是不是第一次Options请求 if (string.Equals(context.Request.Method,CorsConstants.PreflightHttpMethod,StringComparison.OrdinalIgnoreCase) &&!StringValues.IsNullOrEmpty(accessControlRequestMethod)) {               //判断是否允许当前请求跨域,根据HttpContext的内容和Cors配置 得到CorsResult,然后将CorsResult的内容添加到请求头中(看下面详细解释) ApplyCorsHeaders(context, corsPolicy); context.Response.StatusCode = StatusCodes.Status204NoContent; return; } else {// 执行第二次非Options请求 context.Response.OnStarting(state => { var (httpContext, policy) = (Tuple<HttpContext, CorsPolicy>)state; try { ApplyCorsHeaders(httpContext, policy); } catch (Exception exception) { _logger.FailedToSetCorsHeaders(exception); } return Task.CompletedTask; }, Tuple.Create(context, corsPolicy)); } } } await _next(context); }      private void ApplyCorsHeaders(HttpContext context, CorsPolicy corsPolicy) {  //通过HTTP上下文请求的数据和Cors配置 得到CorsResult        如在第一次Options请求时,客户端发送了Origi::8089,Access-Control-Resquest-Methods:GET        服务器会返回Access-Control-Allow-Origin::8089,Access-Control-Allow-Methods:GET        服务器验证:8089这个域名以GET请求方式是否允许跨域,        如果允许就将“:8089”这个值存储到CorsResult的AllowedHeaders中        将"GET"存储到CorsResult的AllowedMethods中 var corsResult = _corsService.EvaluatePolicy(context, corsPolicy);        //将CorsResult中的值添加到相应头中的,返回到客户端 _corsService.ApplyResult(corsResult, context.Response); }

相对来说Cors源码还是比较简单的,很容易看懂。可以自己写一个项目,然后挂上源码单步调试。

总结

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/wdsxjw.html