再见RESTful,你好GraphQL
1.GraphQL
1.1.GraphQL介绍
GraphQL是由Facebook创造的用于描述复杂数据模型的一种查询语言,这里查询语言所指的并不是常规意义上的类似SQL语句的查询语言,而是一种用于前后端数据查询方式的规范。
官网
规范地址
1.2.分析RESTful存在的问题
RESTful在查询的时候,往往是这样的:
#请求
GET http://127.0.0.1/user/1001
#响应
{
id:1001,
name:"张三",
age:20,
address:"北京市"
}
这样似乎是没有问题的,如果,对于这次请求,我只要id和name属性,其他的属性我都不需要,如果我依然拿到的是全部属性,就是一种资源浪费。
#查询用户信息
GET http://127.0.0.1/user/1001
#响应
{
id:1001,
name:"张三",
age:20,
address:"北京市"
}
#查询用户的身份信息
GET http://127.0.0.1/card/8888
#响应
{
id:8888,
name:"张三",
cardNumber:"999999999999",
address:"北京市"
}
查询用户以及身份证信息,需要进行2次查询才能完成,这样对于前段等接口的使用方法是很不友好的,试想查询信息有10个,那么需要发起10次请求才能完成。
1.3.GraphQL特点
1.3.1.按需索取数据,避免浪费
可以看出,当请求中只有name属性时,响应结果中只包含name属性,如果请求中添加appearsin属性,那么结果中就会返回appearsin的值。
1.3.2.一次查询多个数据
可以看到,一次请求,不仅查询到了hero数据,而且还查询到了friends数据,节省了网络请求次数。
1.3.3.API的演进无需划分版本
可以看出,当API进行升级的时候,客户端可以不进行升级,等到后期一起升级,这样就大大减少了客户端和服务端的耦合度。
1.4.GraphQL的查询规范
GraphQL定义了一套规范,用来描述语法定义,仅仅是规范,并不是具体的实现,需要各种语言进行实现。
1.4.1.字段(Fields)
在GraphQL的查询中,请求结构中包含了所预期结果的结构,这个就是字段,并且响应的结构和请求结构基本一致,这是GraphQL的一个特性,这样就可以让请求者很清楚自己想要什么。
1.4.2.参数(Arguments)
在查询数据时,离不开传递参数,在GraphQL的查询中,也是可以传递参数的,语法:(参数名:参数值)
1.4.3.别名(Aliases)
如果一次查询多个相同的对象,但是值不同,这个时候就需要起别名,否则json的语法就不能通过了
1.4.4.片段(Fragments)
查询结果的属性如果相同,可以采用片段的方式进行简化定义
1.5.GraphQL的Schema和类型规范
Schema是用于定义数据结构的,比如说,User对象中有哪些属性,对象与对象之间是什么关系等。
1.5.1.Schema定义结构
schema {
#定义查询
query:UserQuery
}
type UserQuery {
#定义查询的类型
user(id:ID):User #指定对象以及参数类型
}
type User {
#定义对象
id:ID! # !表示该属性是非空项
name:String
age:Int
}
1.5.2.标量类型
GraphQL规范中,默认定义了5种类型
Int
:有符号32位整数;Float
:有符号双精度浮点值;String
: UTF-8字符序列;Boolean
:true
或者false
;ID
:ID
标量类型表示一个唯一标识符,通常用以重新获取对象或者作为缓存中的键。
规范中定义的这5种类型,显然是不能同时满足需求的,所以在各种语言实现中,都有对类型进行了补充,
也就是GraphQL支持自定义类型,比如在graphQL-j