该任务运行时,客户端可以继续执行其自己的处理。 它可以定期向先前收到的 URI 发送请求。
URI 中的 Web API 在表中查询相应任务的状态并返回带有 HTTP 状态代码 200(正常)的响应消息,该消息包含以下状态:正在运行、完成或失败。 如果该任务已完成或失败,则响应消息还可以包括处理的结果或获得的有关失败原因的任何信息。
如果长时间运行的进程存在其他中间状态,最好使用支持 saga 模式的库,例如 NServiceBus 或 MassTransit。
用于实现通知的选项包括:
使用通知中心将异步响应推送到客户端应用程序。 关于更多信息,请参阅使用 Azure 通知中心向特定用户发送通知。
使用 Comet 模型来保持客户端与托管 Web API 的服务器之间的永久网络连接,并使用此连接将消息从服务器推送回客户端。 MSDN 杂志文章 Building a Simple Comet Application in the Microsoft .NET Framework(在 Microsoft .NET Framework 中构建简单的 Comet 应用程序)介绍了一个示例解决方案。
使用 SignalR 通过永久网络连接将 Web 服务器中的实时数据推送到客户端。 SignalR 可作为 NuGet 程序包用于 ASP.NET Web 应用程序。 可以在 ASP.NET SignalR 网站上找到详细信息。
确保每个请求都是无状态的
每个请求应视为原子的。 客户端应用程序发出的一个请求应与同一客户端提交的任何后续请求之间没有任何依赖关系。 此方法可帮助你实现伸缩性;可以在多个服务器上部署 Web 服务的实例。 客户端请求可以定向到其中任一实例,并且结果应始终相同。 由于类似的原因,它还提高了可用性;如果某个 Web 服务器失败,可以将请求路由到其他实例(通过使用 Azure 流量管理器),同时重新启动该服务器,对客户端应用程序没有任何不良影响。
跟踪客户端并实现限制以降低 DoS 攻击的可能性
如果特定客户端在给定的时间段内发出了大量请求,则它可能会独占服务并影响其他客户端的性能。 若要缓解此问题,Web API 可以通过跟踪所有传入请求的 IP 地址或通过记录每次经过身份验证的访问来监视客户端应用程序的调用。 可以使用此信息来限制资源访问。 如果客户端超出定义的限制,Web API 可以返回包含状态 503(服务不可用)的响应消息并在其中包括 Retry-After 标头以指定客户端可以发送下一个请求而不会被拒绝的时间。 此策略可帮助降低停止系统的一组客户端发起拒绝服务 (DoS) 攻击的可能性。
小心管理永久 HTTP 连接
HTTP 协议支持永久 HTTP 连接(在这些连接可用时)。 HTTP 1.0 规范已添加 Connection:Keep-Alive 标头以允许客户端应用程序向服务器表明它可能使用同一连接发送后续请求而不是打开新连接。 如果客户端在主机定义的时间段内未重用连接,则该连接会自动关闭。 此行为在 Azure 服务使用的 HTTP 1.1 中是默认设置,因此无需在消息中包括 Keep-Alive 标头。
让连接保持打开状态可以减少延迟和网络拥塞,从而有助于提高响应能力,但让不必要的连接保持打开状态的时间大于所需时间可能会不利于可扩展性,从而限制了其他并发客户端进行连接的能力。 如果客户端应用程序运行在移动设备上,则还会影响电池使用寿命;如果应用程序只偶尔向服务器发出请求,则维持连接的打开状态可能会导致电池更快耗尽。 若要确保不使用 HTTP 1.1 建立永久连接,客户端可以在消息中包括 Connection:Close 标头以覆盖默认行为。 同样,如果服务器正在处理大量客户端请求,它可以在响应消息中包括 Connection:Close 标头,这会关闭连接并节省服务器资源。
永久 HTTP 连接是纯粹的可选功能,用于减少与反复建立通信通道关联的网络开销。 Web API 和客户端应用程序都不应依赖于可用的永久 HTTP 连接。 不要使用永久 HTTP 连接实现 Comet 样式通知系统,而是应利用 TCP 层的套接字(或可用的 Web 套接字)。 最后,请注意:如果客户端应用程序通过代理与服务器通信,则 Keep-Alive 标头的作用有限;只有与客户端和代理的连接将是持久的。
发布和管理 Web API
要使 Web API 可供客户端应用程序使用,Web API 必须部署到主机环境中。 此环境通常是 Web 服务器,尽管它可能是某种其他类型的主机进程。 发布 Web API 时,应考虑以下几点:
所有请求都必须经过身份验证和授权,必须强制实施相应的访问控制级别。
商业 Web API 可能会受到与响应时间有关的各种质量保证约束。 如果负载随着时间的推移会发生显著变化,请务必确保主机环境是可缩放的。
出于盈利目的,可能有必要计量请求。
可能需要使用 Web API 调控通信流量,并对已用完其配额的特定客户端实施限制。
法规要求可能会强制执行所有请求和响应的记录和审核。
为了确保可用性,可能有必要监视托管 Web API 的服务器的运行状况并在必要时重新启动它。
如果能够将这些问题从有关 Web API 的实现的技术问题中分离出来,则很有帮助。 因此,可考虑创建一个外观,作为独立的进程运行,并将请求路由到 Web API。 外观可用于进行管理操作,并将验证过的请求转发到 Web API。 使用外观还有许多功能优势,包括:
充当多个 Web API 的集成点。
转换消息并转换使用不同技术生成的客户端的通信协议。
缓存请求和响应以减少托管 Web API 的服务器上的负载。
测试 Web API
Web API 应和软件的任何其他部分一样进行全面测试。 应考虑创建单元测试来验证功能。
Web API 的性质带来了其自己的验证是否正常运行的附加要求。 应特别注意以下几个方面:
测试所有路由以验证它们是否调用正确的操作。 特别要注意意外返回的 HTTP 状态代码 405(不允许的方法),因为这可能指示路由与可分派给该路由的 HTTP 方法(GET、POST、PUT、DELETE)不匹配。
将 HTTP 请求发送到不支持这些请求的路由,例如,将 POST 请求提交到特定资源(POST 请求只应发送到资源集合)。 在这些情况下,唯一有效的响应应为状态代码“405 (不允许)”。
验证所有路由是否都得到正确保护并受相应身份验证和授权检查的制约。
安全性的某些方面(如用户身份验证)最有可能是主机环境(而不是 Web API)的职责,但仍有必要在部署过程中进行安全测试。
测试每个操作执行的异常处理,并验证是否将相应的有意义的 HTTP 响应传递回客户端应用程序。
验证请求和响应消息的格式是否正确。 例如,如果 HTTP POST 请求包含 x-www-form-urlencoded 格式的新资源数据,请确认相应的操作正确分析数据、创建该资源,并返回包含新资源的详细信息的响应,包括正确的 Location 标头。
验证响应消息中的所有链接和 URI。 例如,HTTP POST 消息应返回新创建的资源的 URI。 所有 HATEOAS 链接都应有效。
确保每个操作针对不同输入组合返回正确的状态代码。 例如:
如果查询成功,则应返回状态代码 200(正常)
如果未找到资源,则操作应返回 HTTP 状态代码 404(未找到)。
如果客户端发送的请求成功删除资源,则状态代码应为 204(无内容)。
如果客户端发送的请求创建了新资源,则状态代码应为 201(已创建)
密切注意 5xx 范围内的异常响应状态代码。 这些消息通常由主机服务器报告,以指示无法完成有效请求。
测试客户端应用程序可以指定的不同请求标头组合并确保 Web API 在响应消息中返回预期的信息。
测试查询字符串。 如果操作可以接受可选参数(例如分页请求),则测试参数的不同组合和顺序。
验证异步操作是否成功完成。 如果 Web API 支持对返回大型二进制对象(如视频或音频)的请求进行流式处理,请确保在流式传输数据时不会阻止客户端请求。 如果 Web API 实现了轮询长时间运行的数据修改操作,请验证这些操作在执行时正确报告其状态。
还应创建并运行性能测试以检查 Web API 在压力下令人满意地运行。 可以使用 Visual Studio Ultimate 构建一个 Web 性能和负载测试项目。
使用 Azure API 管理
在 Azure 上,可以考虑使用 Azure API 管理发布和管理 Web API。 使用此工具,可以生成一个充当一个或多个 Web API 的外观的服务。 该服务本身是一个可缩放的 Web 服务,可以使用 Azure 门户对其创建和配置。 可以使用此服务发布和管理 Web API,如下所示:
将 Web API 部署到网站、Azure 云服务或 Azure 虚拟机。
将 API 管理服务连接到 Web API。 发送到管理 API 的 URL 的请求将映射到 Web API 中的 URI。 同一 API 管理服务可以将请求路由到多个 Web API。 这样便可以将多个 Web API 聚合为单个管理服务。 同样,如果需要限制或分隔可用于不同应用程序的功能,则可以从多个 API 管理服务引用同一 Web API。
作为 HTTP GET 请求的响应的一部分生成的 HATEOAS 链接中的 URI 应引用 API 管理服务(而不是托管 Web API 的 Web 服务器)的 URL。
对于每个 Web API,指定该 Web API 公开的 HTTP 操作以及操作可以获取为输入的任何可选参数。 还可以配置 API 管理服务是否应缓存从 Web API 接收的响应以优化对相同数据的重复请求。 记录每个操作可以生成的 HTTP 响应的详细信息。 此信息用于为开发人员生成文档,因此它应准确且完整。
可以使用 Azure 门户提供的向导手动定义操作,也可以从包含 WADL 或 Swagger 格式的定义的文件中导入操作。
为 API 管理服务与托管 Web API 的 Web 服务器之间的通信配置安全设置。 API 管理服务目前支持使用证书和 Open Authorization (OAuth) 2.0 用户授权的基本身份验证和相互身份验证。
创建产品。 产品是发布的单元;可将先前连接到管理服务的 Web API 添加到产品。 发布产品后,该 Web API 便可供开发人员使用了。
在发布产品之前,还可以定义可以访问该产品的用户组,并将用户添加到这些组。 这让可以控制使用该 Web API 的开发人员的应用程序的访问。 如果 Web API 需要批准,则在能够访问它之前,开发人员必须向产品管理员发送请求。 管理员可以授予或拒绝开发人员的访问权限。 如果情况发生变化,也可以阻止现有开发人员。
为每个 Web API 配置策略。 策略可以控制以下方面:是否应允许跨域调用、如何对客户端进行身份验证、是否要在 XML 和 JSON 数据格式之间透明地进行转换、是否要限制从给定 IP 范围发起的调用、使用配额,以及是否要限制调用率等。 策略可以对整个产品全局应用、对产品中的单个 Web API 应用,或者对 Web API 中的单个操作应用。
有关详细信息,请参阅API 管理文档。
Azure 提供了使用 Azure 流量管理器,使用它可以实现故障转移和负载均衡,并可以减少在不同地理位置托管的多个网站实例之间的延迟。 可以将 Azure 流量管理器与 API 管理服务结合使用;API 管理服务可以通过 Azure 流量管理器将请求路由到网站实例。 有关详细信息,请参阅流量管理器路由方法。
在此结构中,如果你对网站使用自定义 DNS 名称,则应将每个网站的相应 CNAME 记录配置为指向 Azure 流量管理器网站的 DNS 名称。
为客户端开发人员提供支持
构造客户端应用程序的开发人员通常需要了解有关如何访问 Web API 和与参数、数据类型、返回类型和返回代码(描述 Web 服务和客户端应用程序之间的不同请求和响应)相关的文档的信息。
记录 Web API 的 REST 操作
Azure API 管理服务包括一个开发人员门户,其中描述了由 Web API 公开的 REST 操作。 产品发布后,便会显示在此门户上。 开发人员可以使用此门户注册访问;然后,管理员可以批准或拒绝该请求。 如果开发人员获得批准,则会向其分配一个订阅密钥,用于对所开发的客户端应用程序发出的调用进行身份验证。 此密钥必须与每个 Web API 调用一起提供,否则会被拒绝。
此门户还提供了:
产品的文档,列出它公开的操作、所需参数和可以返回的不同响应。 请注意,此信息从通过使用 Microsoft Azure API 管理服务发布 Web API 部分的列表中的步骤 3 所提供的详细信息生成。
演示如何通过多种语言(包括 JavaScript、C#、Java、Ruby、Python 和 PHP)调用操作的代码片段。
开发人员使用开发人员控制台,能够发送 HTTP 请求以测试产品中的每个操作并查看结果。
在此页中开发人员可以报告发现的任何问题。
使用 Azure 门户可以自定义开发人员门户,以便更改样式和布局以匹配组织的品牌。
实现客户端 SDK
构建调用 REST 请求以访问 Web API 的客户端应用程序需要编写大量代码来构造每个请求并相应地设置其格式,将请求发送到托管 Web 服务的服务器,分析响应以确定请求是成功还是失败并提取返回的任何数据。 要使客户端应用程序免除这些问题,可以提供这样一个 SDK:包装 REST 接口并在一组功能更强的方法内抽象这些低级别的详细信息。 客户端应用程序使用这些方法,这些方法透明地将调用转换为 REST 请求,然后将响应转换回方法返回值。 这是许多服务(包括 Azure SDK)已实现的一种常用技术。
创建客户端 SDK 是一项要求相当高的任务,因为它必须一致地实现,并经过严格测试。 但是,此过程的大部分操作可以机械地进行,并且许多供应商提供了可自动执行上述许多任务的工具。
监视 Web API
根据你发布和部署 Web API 的方式,可以直接监视 Web API,也可以分析通过 API 管理服务传递的流量来收集使用情况和运行状况信息。
直接监视 Web API
如果已通过使用 ASP.NET Web API 模板(不管作为 Web API 项目还是作为 Azure 云服务中的 Web 角色)和 Visual Studio 2013 实现 Web API,则可以通过使用 ASP.NET Application Insights 收集可用性、性能和使用情况数据。 Application Insights 是在 Web API 部署到云中后透明地跟踪和记录有关请求和响应的信息的程序包;安装并配置该包后,无需修改 Web API 中的任何代码即可使用它。 将 Web API 部署到 Azure 网站时,会检查所有通信并收集以下统计信息:
服务器响应时间。
服务器请求数和每个请求的详细信息。
就平均响应时间而言,速度最慢的前几个请求。
任何失败的请求的详细信息。
由不同浏览器和用户代理启动的会话数。
最经常查看的网页(主要适用于 Web 应用程序而不是 Web API)。
访问 Web API 的不同用户角色。
可以在 Azure 门户实时查看此数据。 还可以创建监视 Web API 健康状况的 Web 测试。 Web 测试将定期请求发送到 Web API 中指定的 URI,并捕获响应。 可以指定成功响应的定义(如 HTTP 状态代码 200),如果请求未返回此响应,可以安排向管理员发送警报。 如有必要,管理员可以重新启动托管 Web API 的服务器(如果它出现故障)。
有关详细信息,请参阅 Application Insights - ASP.NET 入门。
通过 API 管理服务监视 Web API
如果已通过使用 API 管理服务发布 Web API,则 Azure 门户上的 API 管理页包含一个可用于查看该服务的整体性能的仪表板。 使用“分析”页,可向下钻取到该产品的使用方式的详细信息。 此页包含以下选项卡:
使用情况。 此选项卡提供有关随着时间推移已进行的 API 调用数和用于处理这些调用的带宽的信息。 可以按产品、API 和操作筛选使用情况详细信息。
运行状况。 使用此选项卡可查看 API 请求的结果(返回的 HTTP 状态代码)、缓存策略的有效性、API 响应时间和服务响应时间。 同样,可以按产品、API 和操作筛选运行状况数据。
参加过的活动。 此选项卡提供了以下信息的文本摘要:成功的调用数、失败的调用数、阻止的调用数、平均响应时间以及每个产品、Web API 和操作的响应时间。 此页还列出了每个开发人员进行的调用数。
速览。 此选项卡显示性能数据的摘要,包括负责进行大多数 API 调用的开发人员,以及接收这些调用的产品、Web API 和操作。
可以使用此信息来确定是否是特定 Web API 或操作导致了瓶颈问题,如有必要,扩展主机环境并添加更多服务器。 还可以确定一个或多个应用程序是否正在使用不相称的资源量,从而应用适当的策略以设置配额并限制调用率。
可以更改已发布产品的详细信息,所做的更改将立即应用。 例如,可以在 Web API 中添加或删除操作,而无需重新发布包含该 Web API 的产品。
ASP.NET Web API OData 包含有关如何使用 ASP.NET 实现 OData Web API 的示例和更多信息。
Introducing batch support in Web API and Web API OData(Web API 和 Web API OData 中的批处理支持简介)介绍了如何使用 OData 在 Web API 中实现批处理操作。
Jonathan Oliver 博客上的幂等性模式概述了幂等性以及它如何与数据管理操作相关。
W3C 网站上的 Status Code Definitions(状态代码定义)包含 HTTP 状态代码及其说明的完整列表。
使用 WebJobs 运行后台任务提供了有关如何使用 WebJobs 执行后台操作的信息和示例。
Azure 通知中心通知用户介绍了如何使用 Azure 通知中心将异步响应推送到客户端应用程序。
API 管理介绍了如何发布可对 Web API 进行受控安全访问的产品。
Azure API 管理 REST API 参考介绍了如何使用 API 管理 REST API 生成自定义管理应用程序。
流量管理器路由方法概述了如何使用 Azure 流量管理器对托管 Web API 的多个网站实例上的请求进行负载均衡操作。
Application Insights - ASP.NET 入门详细介绍了如何在 ASP.NET Web API 项目中安装和配置 Application Insights。