跳转至

第2章:Web APIs

在我们开始使用 Django 构建自己的 Web API 之前,重要的是回顾一下网络的真正工作原理。毕竟,"Web API"字面上是坐在万维网现有架构的顶部,并依赖许多技术,包括 HTTP、TCP/IP 等。

在本章中,我们将回顾 Web API 的基本术语:端点、资源、HTTP 动词、HTTP 状态码和 REST。即使您已经对这些术语感到满意,我也鼓励您完整阅读本章。

万维网

互联网是一个互联计算机网络系统,至少从 20 世纪 60 年代就存在了。然而,互联网的早期使用仅限于少数孤立的网络,主要是政府、军事或科学性质,它们以电子方式交换信息。

20 世纪 80 年代,许多研究机构和大学正在使用互联网共享数据。在欧洲,最大的互联网节点位于瑞士日内瓦的 CERN(欧洲核子研究组织),该组织运营着世界上最大的粒子物理学实验室。这些实验产生了大量的数据,需要远程与全世界的科学家共享。

然而,与今天相比,20 世纪 80 年代的总体互联网使用量微不足道。大多数人无法访问它,甚至不明白为什么它很重要。少数互联网节点为所有流量提供动力,使用它的计算机主要在同一小型网络内。

这一切在 1989 年发生了变化,当时 CERN 的研究科学家 Tim Berners-Lee 发明了 HTTP,并引入了现代万维网。他的伟大见解是,现有的超文本系统(计算机屏幕上显示的文本包含指向其他文档的链接(超链接))可以移到互联网上。

他的发明,超文本传输​​协议(HTTP),是第一种标准的、通用的在互联网上共享文档的方式。它引入了网页的概念:具有 URL、链接和资源(如图像、音频或视频)的离散文档。

今天,当大多数人想到"互联网"时,他们会想到万维网,它现在是数十亿人和计算机在线交流的主要方式。

URLs

URL(统一资源定位符)是互联网上资源的地址。例如,Google 主页位于 [[https://www.google.com](https://www.google.com](https://www.google.com](https://www.google.com`))。

当您想转到 Google 主页时,可以在 Web 浏览器中键入完整的 URL 地址。您的浏览器然后通过互联网发送请求,并神奇地连接到响应所需数据的服务器,以便在浏览器中呈现 Google 主页。

这种请求和响应模式是所有 Web 通信的基础。客户端(通常是 Web 浏览器,但也可以是本机应用程序或任何互联网连接的设备)请求信息,服务器响应响应。

由于 Web 通信是通过 HTTP 进行的,因此它们更正式地称为 HTTP 请求和 HTTP 响应。

在给定的 URL 中,还有几个离散的组件。例如,考虑位于 [[https://www.google.com](https://www.google.com](https://www.google.com](https://www.google.com)) 的 Google 主页。第一部分https指的是使用的方案。它告诉 Web 浏览器如何访问位置中的资源。对于网站,这通常是httphttps,但也可能是用于文件的ftp、用于电子邮件的smtp等。下一节www.google.com` 是主机名或站点的实际名称。每个 URL 都包含方案和主机。

许多网页还包含可选路径。如果您转到 [[https://www.python.org](https://www.python.org](https://www.python.org](https://www.python.org)) 的 Python 主页,然后单击"About"页面的链接,您将被重定向到[https://www.python.org/about//about/](https://www.python.org/about//about/) 部分是路径。

总之,每个像 [[https://python.org/about/](https://python.org/about/](https://python.org/about/](https://python.org/about/)) 这样的 URL 都有三个潜在部分: - 一个方案 -https- 一个主机名 -www.python.org- 和一个(可选)路径 -/about/`

互联网协议套件

一旦我们知道资源的实际 URL,一整套其他技术就必须正常工作(一起)以将客户端与服务器连接起来并加载实际的网页。这被广泛称为互联网协议套件,并且有关于这个主题的整本书。然而,就我们的目的而言,我们可以坚持广泛的基础知识。

当用户在其 Web 浏览器中键入 [[https://www.google.com](https://www.google.com](https://www.google.com](https://www.google.com`)) 并按 Enter 时,会发生几件事。首先,浏览器需要在广阔的互联网上的某处找到所需的服务器。它使用域名服务(DNS)将域名"google.com"转换为 IP 地址,这是代表互联网上每个连接设备的唯一数字序列。使用域名是因为人类更容易记住像"google.com"这样的域名,而不是像"172.217.164.68"这样的 IP 地址。

在浏览器获得给定域的 IP 地址后,它需要一种方法与所需服务器建立一致的连接。这是通过传输控制协议(TCP)发生的,它提供两个应用程序之间可靠、有序和错误检查的字节传递。

要在两台计算机之间建立 TCP 连接,客户端和服务器之间会发生三次"握手": 1. 客户端发送 SYN 以请求建立连接 2. 服务器响应 SYN-ACK 以确认请求并传递连接参数 3. 客户端向服务器发送 ACK 以确认连接

一旦建立 TCP 连接,两台计算机就可以通过 HTTP 进行通信。

HTTP 动词

每个网页都包含地址(URL)以及已批准操作的列表,称为 HTTP 动词。到目前为止,我们主要讨论了获取网页,但也可以创建、编辑和删除内容。

考虑 Facebook 网站。登录后,您可以阅读时间线、创建新帖子或编辑/删除现有帖子。这四个操作创建-读取-更新-删除通常被称为"CRUD",代表了在线采取的大部分操作。

HTTP 协议包含许多请求方法,可以在从服务器请求信息时使用。最常见的四种映射到 CRUD 功能:POSTGETPUTDELETE

CRUD HTTP Verbs
Create POST
Read GET
Update PUT
Delete DELETE

要创建内容,您使用 POST,要读取内容使用 GET,要更新它使用 PUT,要删除它使用 DELETE

端点

传统网站由具有 HTML、CSS、图像、JavaScript 等的网页组成。每个页面都有一个专用的 URL,例如 example.com/1/。Web API 也依赖于 URL,相应的可能是 example.com/api/1/,但与其提供人类可读的网页,不如生成 API 端点。端点包含数据(通常是 JSON 格式)以及可用操作(HTTP 动词)的列表。

例如,我们可以为名为 mysite 的新网站创建以下 API 端点: - [[https://www.mysite.com/api/users](https://www.mysite.com/api/users](https://www.mysite.com/api/users](https://www.mysite.com/api/users)) - GET 返回所有用户 -[https://www.mysite.com/api/users/](https://www.mysite.com/api/users/` - GET 返回单个用户

在第一个端点 /api/users 中,可用的 GET 请求返回所有可用用户的列表。返回多个数据资源的这种类型的端点被称为集合。

第二个端点 /api/users/<id> 表示单个用户。GET 请求只返回关于那一个用户的信息。

如果我们在第一个端点添加 POST,我们可以创建一个新用户,而在第二个端点添加 DELETE 将允许我们删除单个用户。

在本书的过程中,我们将对 API 端点更加熟悉,但最终创建 API 涉及制作一系列端点:公开 JSON 数据和关联 HTTP 动词的 URL。

HTTP

我们在本章中已经谈论了很多关于 HTTP 的内容,但现在我们将描述它实际上是什么以及它是如何工作的。

HTTP 是两个具有现有 TCP 连接的计算机之间的请求-响应协议。发出请求的计算机被称为客户端,而响应的计算机被称为服务器。通常,客户端是 Web 浏览器,但它也可以是 iOS 应用程序或任何互联网连接的设备。服务器是任何优化为通过互联网工作的计算机的通用名称。将基本笔记本电脑转换为服务器所需要做的就是一些特殊软件和持久互联网连接。

(继续翻译剩余内容...)

HTTP 消息

每个 HTTP 消息都由状态行、标头和可选正文数据组成。例如,以下是浏览器可能发送的示例 HTTP 消息,以请求位于 [[https://www.google.com](https://www.google.com](https://www.google.com](https://www.google.com`)) 的 Google 主页。

Diagram

GET / HTTP/1.1
Host: google.com
Accept_Language: en-US

顶行被称为请求行,它指定要使用的 HTTP 方法(GET)、路径(/)和要使用的 HTTP 特定版本(HTTP/1.1)。

随后两行是 HTTP 标头:Host 是域名,Accept_Language 是要使用的语言,在这种情况下是美式英语。有许多可用的 HTTP 标头。

HTTP 消息也有可选的第三部分,称为正文,但我们只在包含数据的 HTTP 响应中看到正文消息。

为简单起见,让我们假设 Google 主页只包含 HTML"Hello, World!"。这将是来自 Google 服务器的 HTTP 响应消息可能的样子。

Diagram

HTTP/1.1 200 OK
Date: Mon, 24 Jan 2022 23:26:07 GMT
Server: gws
Accept-Ranges: bytes
Content-Length: [13](https://en.wikipedia.org/wiki/Internet)
Content-Type: text/html; charset=UTF-8

Hello, world!

顶行是响应行,它指定我们正在使用 HTTP/1.1。状态码 200 OK 表示客户端的请求成功(稍后将详细介绍状态码)。

接下来的五行是 HTTP 标头。最后,在换行符之后,是我们的实际正文内容"Hello, world!"。

因此,每个 HTTP 消息(无论是请求还是响应)都具有以下格式:

Diagram

Response/request line
Headers...
(optional) Body

大多数网页包含需要多个 HTTP 请求/响应周期的多个资源。如果网页有 HTML、一个 CSS 文件和一张图像,则在可以在浏览器中呈现完整网页之前,客户端和服务器之间需要三次单独的往返。

状态码

一旦您的 Web 浏览器在 URL 上执行了 HTTP 请求,就不能保证事情实际上会工作!因此,有一个相当长的 HTTP 状态码列表可用于伴随每个 HTTP 响应。

您可以根据以下系统判断状态码的一般类型: - 2xx Success - 客户端请求的操作已被接收、理解和接受 - 3xx Redirection - 请求的 URL 已移动 - 4xx Client Error - 出现错误,通常是客户端请求的错误 URL - 5xx Server Error - 服务器未能解析请求

无需记住所有可用的状态码。通过练习,您将熟悉最常见的状态码,如 200 (OK)201 (Created)301 (Moved Permanently)404 (Not Found)500 (Server Error)

要记住的重要事情是,一般来说,任何给定的 HTTP 请求只有四种可能的结果:它工作了(2xx)、它以某种方式被重定向(3xx)、客户端犯了错误(4xx)或服务器犯了错误(5xx)。

这些状态码自动放置在每个 HTTP 消息顶部的请求/响应行中。

无状态性

关于 HTTP 的最后一点重要的是,它是一种无状态协议。这意味着每个请求/响应对都完全独立于前一个。没有过去交互的存储记忆,这在计算机科学中被称为状态。

无状态性为 HTTP 带来了许多好处。由于所有电子通信系统都会随着时间的推移而丢失信号,如果我们没有无状态协议,如果其中一个请求/响应周期没有通过,事情就会不断中断。因此,HTTP 被称为一种非常有弹性的分布式协议。

缺点是在 Web 应用程序中管理状态确实非常重要。状态是网站记住您已登录的方式,以及电子商务网站管理购物车的方式。这是我们如何使用现代网站的基础,但它本身不受 HTTP 支持。

从历史上看,状态在服务器上维护,但在现代前端框架(如 React、Angular 和 Vue)中,它已越来越多地转移到客户端(Web 浏览器)。当我们介绍用户认证时,我们将了解更多关于状态的信息,但请记住 HTTP 是无状态的。这使得它非常擅长在两个计算机之间可靠地发送信息,但不擅长记住每个单独请求/响应对之外的任何内容。

REST

表现层状态转移(REST)是一种架构,最初由 Roy Fielding 在 2000 年的博士论文中提出。它是一种在 Web 之上构建 API 的方法,这意味着在 HTTP 协议之上。

关于是什么使 API 真正具有 RESTful 或非 RESTful 的整本书都已经写好了。但是有三个主要特征,我们在这里将重点关注。每个 RESTful API: - 是无状态的,就像 HTTP 一样 - 支持常见的 HTTP 动词(GETPOSTPUTDELETE 等) - 以 JSON 或 XML 格式返回数据

任何 RESTful API 必须至少具有这三个原则。该标准很重要,因为它提供了一种设计和消耗 Web API 的一致方式。

结论

虽然现代万维网底层有很多技术,但我们作为开发人员不必从头开始实现所有这些技术。Django 和 Django REST Framework 的完美组合正确地处理了与 Web API 相关的大部分复杂性。然而,至少广泛了解所有部分如何组合在一起是很重要的。

最终,Web API 是公开底层数据库的某些部分的端点集合。作为开发人员,我们控制每个端点的 URL、可用的底层数据以及通过 HTTP 动词可以采取的操作。通过使用 HTTP 标头,我们还可以设置各种级别的认证和权限,正如我们将在本书后面看到的那样。