API 接口设计原则:RESTful 与 GraphQL

RESTful 接口

REST 的全称是 REpresentational State Transfer,是一种 Web API 的设计风格

RESTful API 设计 6 大原则

一个 RESTful 风格的接口应该满足如下的 6 点原则:

在这里插入图片描述

  • 统一接口:For example, the HTTP-based REST APIs make use of the standard HTTP methods (GET, POST, PUT, DELETE, etc.) and the URIs (Uniform Resource Identifiers) to identify resources
  • 使用 client-server 架构解耦
  • 无状态:server 不能保存与 client 的会话状态
  • 可缓存的:响应数据应该声明自己能否被缓存
  • 分层系统:采用反向代理服务器屏蔽 server 和 client
  • 按需返回可执行代码:server 能够向 client 返回一段代码用以执行

RESTful API 最佳实践

  • URL 中不要使用动词,动作交给 HTTP 的不同请求来区分
  • 状态码必须准确,错误信息就要响应对应的错误状态码

下面使用 nodejs 编写了一个简单的 web 服务,提供了查询 user 的 RESTful get 接口:

var express = require('express');
var mysql = require("mysql");
var client = mysql.createConnection({
    host: '192.168.93.12',
    user: 'root',
    password: 'xxx',
    port: '3306',
    database: 'big_event',
});
client.connect();
var app = express();

app.get("/user/:id", (req, res) => {
    let { id } = req.params;
    client.query(`select id, username, password, email from user where id=${id}`, (err, users) => {
        if (err) {
            console.warn(err);
        }
        if (users && users.length == 1) {
            res.send(users[0]);
        } else {
            res.send("wrong result");
        }
    });
})

app.listen(5000, () => console.log('Now browse to localhost:5000/restful'));

对于上面的 API,使用 http://localhost:5000/user/1 即可获取到 id 为 1 的 user 信息

RESTfull API 的缺点

  • 获取数据不够灵活:batch 获取数据时要发送多次请求。也容易过度获取数据:本来只需要2~3个值,结果返回了20个值
  • 弱类型:js 的类型系统薄弱,除了 number、string、array、object 等,不支持自定义类型

针对这些缺点,提出了 GraphQL

GraphQL 接口

GraphQL 是一个用于 API 的查询语言,是一个使用基于类型系统来执行查询的服务端运行时

用 GraphQL 将上面的查询接口重写如下:

const { graphqlHTTP } = require('express-graphql');
const { buildSchema } = require('graphql');

// 定义 GraphQL schema
const schema = buildSchema(`
    type User {
        id: Int
        username: String
        password: String
        email: String
    }

    type Query {
        user(id: Int!): User
    }
`);

// 定义 resolver 函数,用于处理查询
const root = {
    user: ({ id }) => {
        return new Promise((resolve, reject) => {
            client.query(`SELECT id, username, password, email FROM user WHERE id = ${id}`, (err, result) => {
                if (err) {
                    reject(err);
                } else {
                    resolve(result[0]);
                }
            });
        });
    }
};

const app = express();

app.use('/graphql', graphqlHTTP({
    schema: schema,
    rootValue: root,
    graphiql: true // 启用 GraphiQL 可视化工具
}));

app.listen(5000, () => {
    console.log('GraphQL Server is running on http://localhost:5000/graphql');
});

启动后,我们在浏览器中能够访问到一个调试界面:

在这里插入图片描述
输入查询条件:

{
  user(id: 1) {
    id
    username
    password
  }
}

就可以得到查询结果:

{
  "data": {
    "user": {
      "id": 1,
      "username": "wangba",
      "password": "124bd1296bec0d9d93c7b52a71ad8d5b"
    }
  }
}

GraphQL 的优点

  • 前端变被动为主动,能够决定要获取哪些数据,不再依赖于和后端的 API 接口文档。前端能够专注于 UI 设计
  • 增减字段很容易,易于扩展
  • 批量获取数据只需要发送一次 HTTP 请求,节省了网络带宽

GraphQL 的缺点

  • 缓存实现困难
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值