ASP.NET Web API自身对CORS的支持: CORS授权检验的实施

简介:

通过《EnableCorsAttribute特性背后的故事》我们知道:由CorsPolicyProvider提供的CorsPolicy表示目标Action采用的资源授权策略,ASP.NET Web API最终需要利用它对具体的跨域资源请求实施授权检验并生成相应的CORS响应报头。在ASP.NET Web API的应用编程接口中,资源授权检验的结果通过类型CorsResult来表示。

一、CorsResult

CorsResult定义在命名空间“System.Web.Cors”下,表示资源提供者针对具体跨域资源请求进行授权检验得到的结果,最终写入响应的CORS报头均通过此对象来生成。如下面的代码片断所示,CorsResult依然具有与6个CORS响应报头对应的属性,通过其方法ToResponseHeaders方法的字典表示由此6个属性生成的CORS相应报头,字典对象的Key和Value分别表示报头名称和值。

   1: public class CorsResult
   2: {
   3:     public string            AllowedOrigin { get; set; }
   4:     public IList<string>     AllowedExposedHeaders { get; }
   5:     public IList<string>     AllowedHeaders { get; }
   6:     public IList<string>     AllowedMethods { get; }
   7:     public long?             PreflightMaxAge { get; set; }
   8:     public bool              SupportsCredentials { get; set; }
   9:     
  10:     public IList<string>     ErrorMessages { get; }
  11:     public bool              IsValid { get; }
  12:  
  13:     public virtual IDictionary<string, string> ToResponseHeaders();
  14: }

CorsResult具有一个布尔类型的属性IsValid表示请求是否通过资源授权检验。如果该属性返回False(没有通过资源授权检验),另一个相关的属性ErrorMessages会提供导致检验失败的原因。IsValid是一个只读属性,它的值取决于通过ErrorMessages属性表示的字符串列表是否为空。

二、CorsRequestContext

针对CORS的支持其实并不限于仅被使用在ASP.NET Web API上,用于根据提供的资源授权策略对跨域资源请求进行授权检验得引擎定义在程序集System.Web.Cors.dll中,定义在另一个程序集对于这些类型来说,除了CorsPolicy定义在程序集System.Web.Cors.dll,其余的类型均定义在程序集System.Web.Http.Cors.dll中的相关类型可以视为对这个核心CORS引擎的扩展。对于本节引入的类型来说,它具有的命名空间其实也体现了它所在的程序集。

对于ASP.NET Web API来说,CORS资源授权检验实施的目标是表示当请求的HttpRequestMessage对象,这个对象自然不可能使用在ASP.NET的核心CORS引擎中。对于后者,授权检验是针对一个System.Web.Cors.CorsRequestContext对象,它代表针对当前请求的上下文。如下面的代码片断所示,我们可以通过CorsRequestContext对象得到对应HTTP请求的地址(RequestUri)、主机名称(Host)和采用的HTTP方法(HttpMethod)。

   1: public class CorsRequestContext
   2: {
   3:     public Uri         RequestUri { get; set; }
   4:     public string      Host { get; set; }
   5:     public string      HttpMethod { get; set; }    
   6:    
   7:     public string          Origin { get; set; }
   8:     public bool            IsPreflight { get; }
   9:     public string          AccessControlRequestMethod { get; set; }
  10:     public ISet<string>    AccessControlRequestHeaders { get; }
  11:  
  12:     public IDictionary<string, object> Properties { get; }
  13: }

CorsRequestContext的Origin属性返回通过请求的“Origin”报头表示的源站点。我们可以利用其IsPreflight属性判断HTTP请求是否为一个预检请求,这里对预检请求的判断标准与我们前面演示实例采用的完全一致:采用HTTP-OPTIONS方法摒弃同时具有“Origin”和“Access-Control-Request-Method”报头。

对于针对预检请求的CorsRequestContext,我们可以通过其属性AccessControlRequestMethod和AccessControlRequestHeaders得到请求报头“Access-Control-Request-Method”和“Access-Control-Request-Headers”的值。通过另一个字典类型的只读属性Properties,我们可以将任意对象作为属性附加到该CorsRequestContext对象上。

三、CorsEngine

我们说ASP.NET 的核心CORS引擎定义在程序集System.Web.Cors.dll中,它主要体验为这个名为CorsEngine的对象,其主要的使命在于:根据提供的资源授权策略(通过CorsPolicy类型表示)针对具体的跨域资源请求(通过CorsRequestContext类型表示)实施授权检验并得到相应的授权结果(通过CorsResult表示)。所有的CorsEngine类型均实现System.Web.Cors.ICorsEngine接口,如下面的代码片断所示,跨域资源请求的授权检查就实现在其唯一的EvaluatePolicy方法中。

   1: public interface ICorsEngine
   2: {
   3:     CorsResult EvaluatePolicy(CorsRequestContext requestContext, CorsPolicy policy);
   4: }

在程序集System.Web.Cors.dll中定义了唯一的实现了ICorsEngine接口,即具有如下定义的类型System.Web.Cors.CorsEngine。如下面的代码片断所示,CorsEngine类型定义了3个辅助的虚方法(TryValidateOrigin、TryValidateMethod 和TryValidateHeaders)分别针对请求的源站点以及请求采用的HTTP方法和自定义报头实施授权检验,其中后面两个方法是专门为预检请求设计的。

   1: public class CorsEngine : ICorsEngine
   2: {
   3:     public virtual CorsResult EvaluatePolicy(CorsRequestContext requestContext, CorsPolicy policy);
   4:  
   5:     public virtual bool TryValidateOrigin(CorsRequestContext requestContext, CorsPolicy policy, CorsResult result);
   6:     public virtual bool TryValidateMethod(CorsRequestContext requestContext, CorsPolicy policy, CorsResult result);
   7:     public virtual bool TryValidateHeaders(CorsRequestContext requestContext, CorsPolicy policy, CorsResult result); 
   8: }

CorsPolicyProviderFactory一样,ASP.NET Web API使用的CorsEngine需要注册到当前HttpConfiguration,注册的CorsEngine同样是被添加到HttpConfiguration的属性字典之中。CorsEngine的注册可以通过调用HttpConfiguration如下所示的扩展方法SetCorsEngine来完成。另一个扩展方法GetCorsEngine用于获取注册的CorsEngine,如果在调用此方法时CorsEngine尚未被注册,一个CorsEngine对象会被创建出来并自动注册到HttpConfiguration上。

   1: public static class CorsHttpConfigurationExtensions
   2: {
   3:     //其他成员
   4:     public static void SetCorsEngine(this HttpConfiguration httpConfiguration, ICorsEngine corsEngine);
   5:     public static ICorsEngine GetCorsEngine(this HttpConfiguration httpConfiguration);
   6: }

 

CORS系列文章
[1] 同源策略与JSONP
[2] 利用扩展让ASP.NET Web API支持JSONP
[3] W3C的CORS规范
[4] 利用扩展让ASP.NET Web API支持CORS
[5] ASP.NET Web API自身对CORS的支持: 从实例开始
[6] ASP.NET Web API自身对CORS的支持: CORS授权策略的定义和提供
[7] ASP.NET Web API自身对CORS的支持: CORS授权检验的实施
[8] ASP.NET Web API自身对CORS的支持: CorsMessageHandler


作者:蒋金楠
微信公众账号:大内老A
微博: www.weibo.com/artech
如果你想及时得到个人撰写文章以及著作的消息推送,或者想看看个人推荐的技术资料,可以扫描左边二维码(或者长按识别二维码)关注个人公众号(原来公众帐号 蒋金楠的自媒体将会停用)。
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。
相关文章
|
28天前
|
人工智能 算法 搜索推荐
拼多多:通过用户分组API实施差异化营销策略,提高客单价
拼多多通过用户分组API实现差异化营销,精准提升客单价。基于用户行为数据自动分类,针对不同群体推送专属优惠,如高频用户推高端商品、新用户送礼包、低频用户唤醒激励。结合满减、捆绑销售等策略,有效提高单笔订单金额。该策略提升营销效率,增强用户粘性,助力平台实现数据驱动的可持续增长。
81 0
|
12月前
|
Java API 数据库
构建RESTful API已经成为现代Web开发的标准做法之一。Spring Boot框架因其简洁的配置、快速的启动特性及丰富的功能集而备受开发者青睐。
【10月更文挑战第11天】本文介绍如何使用Spring Boot构建在线图书管理系统的RESTful API。通过创建Spring Boot项目,定义`Book`实体类、`BookRepository`接口和`BookService`服务类,最后实现`BookController`控制器来处理HTTP请求,展示了从基础环境搭建到API测试的完整过程。
166 4
|
12月前
|
XML JSON API
ServiceStack:不仅仅是一个高性能Web API和微服务框架,更是一站式解决方案——深入解析其多协议支持及简便开发流程,带您体验前所未有的.NET开发效率革命
【10月更文挑战第9天】ServiceStack 是一个高性能的 Web API 和微服务框架,支持 JSON、XML、CSV 等多种数据格式。它简化了 .NET 应用的开发流程,提供了直观的 RESTful 服务构建方式。ServiceStack 支持高并发请求和复杂业务逻辑,安装简单,通过 NuGet 包管理器即可快速集成。示例代码展示了如何创建一个返回当前日期的简单服务,包括定义请求和响应 DTO、实现服务逻辑、配置路由和宿主。ServiceStack 还支持 WebSocket、SignalR 等实时通信协议,具备自动验证、自动过滤器等丰富功能,适合快速搭建高性能、可扩展的服务端应用。
645 3
|
6月前
|
人工智能 搜索推荐 IDE
突破网页数据集获取难题:Web Unlocker API 助力 AI 训练与微调数据集全方位解决方案
本文介绍了Web Unlocker API、Web-Scraper和SERP API三大工具,助力解决AI训练与微调数据集获取难题。Web Unlocker API通过智能代理和CAPTCHA绕过技术,高效解锁高防护网站数据;Web-Scraper支持动态内容加载,精准抓取复杂网页信息;SERP API专注搜索引擎结果页数据抓取,适用于SEO分析与市场研究。这些工具大幅降低数据获取成本,提供合规保障,特别适合中小企业使用。粉丝专属体验入口提供2刀额度,助您轻松上手!
323 2
|
9月前
|
人工智能 前端开发 API
Gemini Coder:基于 Google Gemini API 的开源 Web 应用生成工具,支持实时编辑和预览
Gemini Coder 是一款基于 Google Gemini API 的 AI 应用生成工具,支持通过文本描述快速生成代码,并提供实时代码编辑和预览功能,简化开发流程。
492 38
Gemini Coder:基于 Google Gemini API 的开源 Web 应用生成工具,支持实时编辑和预览
|
7月前
|
XML JSON API
Understanding RESTful API and Web Services: Key Differences and Use Cases
在现代软件开发中,RESTful API和Web服务均用于实现系统间通信,但各有特点。RESTful API遵循REST原则,主要使用HTTP/HTTPS协议,数据格式多为JSON或XML,适用于无状态通信;而Web服务包括SOAP和REST,常用于基于网络的API,采用标准化方法如WSDL或OpenAPI。理解两者区别有助于选择适合应用需求的解决方案,构建高效、可扩展的应用程序。
|
7月前
|
机器学习/深度学习 开发框架 API
Python 高级编程与实战:深入理解 Web 开发与 API 设计
在前几篇文章中,我们探讨了 Python 的基础语法、面向对象编程、函数式编程、元编程、性能优化、调试技巧以及数据科学和机器学习。本文将深入探讨 Python 在 Web 开发和 API 设计中的应用,并通过实战项目帮助你掌握这些技术。
|
9月前
|
开发框架 数据可视化 .NET
.NET 中管理 Web API 文档的两种方式
.NET 中管理 Web API 文档的两种方式
153 14
|
10月前
|
Kubernetes 安全 Devops
有效抵御网络应用及API威胁,聊聊F5 BIG-IP Next Web应用防火墙
有效抵御网络应用及API威胁,聊聊F5 BIG-IP Next Web应用防火墙
264 10
有效抵御网络应用及API威胁,聊聊F5 BIG-IP Next Web应用防火墙
|
11月前
|
开发框架 .NET 程序员
驾驭Autofac,ASP.NET WebApi实现依赖注入详细步骤总结
Autofac 是一个轻量级的依赖注入框架,专门为 .NET 应用程序量身定做,它就像是你代码中的 "魔法师",用它来管理对象的生命周期,让你的代码更加模块化、易于测试和维护
413 4
驾驭Autofac,ASP.NET WebApi实现依赖注入详细步骤总结