多年来,人们一直在使用RESTAPI来满足开发需求,但得完成大量不必要的调用后,开发者才能灵活使用。例如,如果Web和移动设备所需的数据不同,我们还须针对Web和移动设备创建两个不同的端点。
因此,Facebook创建了一种查询语言——GraphQL,该语言可以准确地给出开发者查询的内容,干净利落,也让 API更容易地随着时间推移而演进,还能用于构建强大的开发者工具。
本文将重点介绍GraphQL的主要功能,以及就API而言它存在的优缺点。文末将展示一个使用Golang的简单程序(已搭建GraphQL)。
什么是GraphQL?
GraphQL是用于API的查询语言,它是服务器端运行时,通过为数据定义的类型系统执行查询。
GraphQL是一种查询语言,适用许多领域,但通常用来在客户端和服务器应用程序之间搭桥。无所谓使用的是哪个网络层,所以可以在客户端和服务器应用程序之间读取和写入数据。(RobinWieruch《GraphQL指南》)
虽然GraphQL是查询语言,但它与数据库没有直接关系,也就是GraphQL不限于任意SQL或是NoSQL的数据库。GraphQL位于客户端和服务器端,通过API连接/访问。开发这种查询语言的目的之一是通过提供所需的数据来促进后端、前端或移动应用程序之间的数据通信。
GraphQL的操作
1. 查询(Query)
查询用于读取或获取值。无论哪种情况,操作都是一个简单的字符串,GraphQL服务器可以解析该字符串并以特定格式的数据进行响应。
你可以使用查询操作从API请求数据。查询描述需要从GraphQL服务器获取的数据,发送查询其实是按字段要求提取数据。(Eve Porcello、AlexBanks著《学习GraphQL》)
2. 模式(Schema)
GraphQL使用Schema描述数据图的形状。这样的Schema定义类型的层次结构,依托的是从后端数据存储区填充的字段,也准确表示客户端可以对数据图执行哪些查询和突变。
3. 分解器(Resolver)
分解器是负责为Schema单一字段填充数据的功能。它可以用你定义的任何方式填充该数据,例如从后端数据库或第三方API提取数据。
4. 突变(Mutation)
修改数据存储中的数据并返回一个值,它可用于插入、更新或删除数据。
突变与查询原理相同:它具有字段和对象、参数和变量、片段和操作名称,以及返回结果的指令和嵌套对象。(RobinWieruch著《GraphQL之路》)
5. 订阅(Subscription)
将数据从服务器推送到客户端的方法是选择侦听来自服务器的实时消息。
GraphQL的订阅来自Facebook的真实用例。开发团队希望找到一种方法,不刷新页面就能实时显示发文获得的有效点赞(Live Likes)。(EvePorcello、Alex Banks著《学习GraphQL》)
GraphQL的优势与劣势
1. 优势
(1) 开发迅速
来看一个案例:如何得到图书借阅者的数据。在视图中,首先我要显示书籍列表,书籍列表菜单显示中出现一个借阅者的列表。在RESTAPI中,需要创建新的端点以返回图书清单,再创建一个新的端点以返回每本书的借阅人。
与REST API不同,GraphQL中仅使用一个端点就可以返回书籍列表和借阅者列表了。
使用以下示例GraphQL查询:
(2) 灵活性
来看一个案例:如何获取书籍详细信息。在网络视图上,我想展示书籍详细信息,例如名称、价格和介绍。在RESTAPI中需要创建一个新的端点以返回名称、价格、介绍等的书籍详细信息。
如果在移动端查看时,只想展示图书详细信息中的名称和价格怎么办?如果使用与Web视图相同的端点,则会浪费介绍的数据。所以需要更改该端点内部的现有逻辑,或创建一个新的端点。
与REST API不同,GraphQL中仅使用一个端点即可按照Web或移动设备的需求返回书籍详细信息。在GraphQL中,只需更改查询。
(3) 维护简单,易于使用
2. 缺点
代码实现
实现过程使用了Golang编程语言,这里是项目架构:
在依赖版本和依赖管理功能上使用的是go模块。用graphql-go来支持查询、突变和订阅;用graphql-go-handler来支持处理器。此时,我将创建一个简单的程序,这里使用GraphQL为详细书目创建CRUD。步骤如下:
先新建一个环境文件夹,然后新建一个名为connection.yml的文件:
然后创建一个架构文件夹,创建名为databaseConfiguration.go、environmentConfiguration.go和model.go的文件。这个文件夹用来配置数据库并从connection.yml读取数据。
(1)>