logo
Communication

REST / GraphQL / gRPC

API 风格对比

好的 API design 是系统的核心组成部分,而选择合适的 API 技术同样重要。本节快速对比 REST、GraphQL、gRPC。

rest-vs-graphql

Trade-off 快览

  • REST:成熟、简单、生态好,但容易 over/under-fetching
  • GraphQL:一次请求拿到精确数据,但 server 设计与治理成本更高

什么是 API?

API(Application Programming Interface)是一组定义与协议,用于构建与集成应用。它也像一种 contract,约定了 producer 与 consumer 之间的数据交互方式。

简单说,当你想和系统交互(读取信息或执行操作)时,API 是你和系统沟通的方式。

REST

REST API(也称 RESTful API)遵循 REST 架构约束。REST 是 Representational State Transfer,由 Roy Fielding 在 2000 年提出。

在 REST 中,基本单位是 resource。

Concepts

Constraints

要称得上 RESTful,必须符合这些约束:

  • Uniform Interface:统一的交互方式
  • Client-Server:通过 HTTP 的 client-server 架构
  • Stateless:server 不保留 client context
  • Cacheable:响应需声明是否可 cache 及 cache 时长
  • Layered system:多层架构
  • Code on demand:可返回可执行代码(可选)

HTTP Verbs

常见 HTTP verbs:

  • GET:获取资源
  • HEAD:与 GET 类似但无 body
  • POST:提交实体,通常会产生变化或副作用
  • PUT:替换资源
  • DELETE:删除资源
  • PATCH:部分更新

HTTP response codes

常见状态码类别:

  • 1xx - 信息性响应
  • 2xx - 成功响应
  • 3xx - 重定向
  • 4xx - client 错误
  • 5xx - server 错误

例如 HTTP 200 表示成功。

Advantages

  • 简单易理解
  • 灵活、可移植
  • 支持 caching
  • client 与 server 解耦

Disadvantages

  • 容易 over-fetching
  • 可能需要多次 round trips

Use cases

REST 是最通用的 API 设计方式,适用于大多数场景。

Example

users 资源为例:

URIHTTP verbDescription
/usersGETGet all users
/users/{id}GETGet a user by id
/usersPOSTAdd a new user
/users/{id}PATCHUpdate a user by id
/users/{id}DELETEDelete a user by id

想了解更多可参考 HATEOAS

GraphQL

GraphQL 是一种 query language + server runtime,让 client 精准获取所需数据。由 Facebook 开发并在 2015 年开源。

GraphQL API 快、灵活、对开发者友好。它允许 API 维护者新增或废弃 fields 而不影响旧 queries。

在 GraphQL 中,基本单位是 query。

Concepts

Schema

Schema 描述客户端可使用的能力。

Queries

Query 是 client 发出的请求,可以包含 fields 与 arguments。操作类型也可以是 mutation

Resolvers

Resolvers 是处理 GraphQL query 的函数集合。

Advantages

  • 避免 over-fetching
  • 强 schema
  • 支持 code generation
  • payload 优化

Disadvantages

  • 复杂度转移到 server
  • caching 更难
  • versioning 较模糊
  • N+1 问题

Use cases

  • 降低 app bandwidth
  • 快速迭代复杂系统
  • graph-like data model

Example

type Query {
	getUser: User
}

type User {
	id: ID
	name: String
	city: String
	state: String
}
{
	getUser {
		id
		name
		city
	}
}

返回示例:

{
	"getUser": {
		"id": 123,
		"name": "Karan",
		"city": "San Francisco"
	}
}

更多资料见 graphql.org

gRPC

gRPC 是现代高性能 RPC 框架,可用于数据中心内外的服务通信,支持 load balancing、tracing、health checking、auth 等。

Concepts

Protocol buffers

Protocol buffers 是跨语言、跨平台的序列化格式,类似 JSON,但更小更快,并可生成语言绑定。

Service definition

gRPC 通过 protocol buffers 作为 IDL,定义 service 方法与 message 结构。

Advantages

  • 轻量高效
  • 性能高
  • 内置 codegen
  • 支持双向 streaming

Disadvantages

  • 相对新
  • 浏览器支持有限
  • 学习曲线陡
  • 非人类可读

Use cases

  • 双向实时通信
  • microservices 内部通信
  • 低 latency / 高 throughput
  • 多语言环境

Example

service HelloService {
  rpc SayHello (HelloRequest) returns (HelloResponse);
}

message HelloRequest {
  string greeting = 1;
}

message HelloResponse {
  string reply = 1;
}

REST vs GraphQL vs gRPC

对比维度:

  • 是否造成紧耦合
  • chattiness(需要多少次 API 调用)
  • performance
  • 集成复杂度
  • caching 能力
  • codegen 支持
  • API discoverability
  • versioning 难度
TypeCouplingChattinessPerformanceComplexityCachingCodegenDiscoverabilityVersioning
RESTLowHighGoodMediumGreatBadGoodEasy
GraphQLMediumLowGoodHighCustomGoodGoodCustom
gRPCHighMediumGreatLowCustomGreatBadHard

哪个更好?

没有银弹。每种技术都有 trade-offs,关键是结合你的 domain 与需求做选择。

相关练习题

REST / GraphQL / gRPC

暂无相关练习题