Restful Web Service设计规范

简介: Restful Web Service设计规范

这些问题你都遇到过吗?

  • 项目资源的URL应该如何设计?
  • 用名词复数还是用名词单数?
  • 一个资源需要多少个URL?
  • 用哪种HTTP方法来创建一个新的资源?
  • 可选参数应该放在哪里?
  • 那些不涉及资源操作的URL呢?
  • 实现分页和版本控制的最好方法是什么?

本文来探索最佳实践方案。

每个资源使用两个URL

资源集合用一个URL,具体某个资源用一个URL:

/employees         #资源集合的URL
/employees/56      #具体某个资源的URL

用名词代替动词表示资源

这让你的API更简洁,URL数目更少。不要这么设计:

/getAllEmployees

/getAllExternalEmployees

/createEmployee

/updateEmployee

更好的设计:


GET /employees

GET /employees?state=external

POST /employees

PUT /employees/56

image.png

用HTTP方法操作资源

使用URL指定你要用的资源。使用HTTP方法来指定怎么处理这个资源。使用四种HTTP方法POST,GET,PUT,DELETE可以提供CRUD功能(创建,获取,更新,删除)。

获取:使用GET方法获取资源。GET请求从不改变资源的状态。无副作用。GET方法是幂等的。GET方法具有只读的含义。因此,你可以完美的使用缓存。

创建:使用POST创建新的资源。

更新:使用PUT更新现有资源。

删除:使用DELETE删除现有资源。

2个URL乘以4个HTTP方法就是一组很好的功能。看看这个表格:


POST(创建) GET(读取) PUT(更新) DELETE(删除)

/employees 创建一个新员工 列出所有员工 批量更新员工信息 删除所有员工

/employees/56 (错误) 获取56号员工的信息 更新56号员工的信息 删除56号员工

对资源集合的URL使用POST方法,创建新资源

创建一个新资源的时,客户端与服务器是怎么交互的呢?

在资源集合URL上使用POST来创建新的资源过程:

image.png

客户端向资源集合URL/employees发送POST请求。HTTP body 包含新资源的属性 “Albert Stark”。

RESTful Web服务器为新员工生成ID,在其内部模型中创建员工,并向客户端发送响应。这个响应的HTTP头部包含一个Location字段,指示创建资源可访问的URL。

对具体资源的URL使用PUT方法,来更新资源

使用PUT更新已有资源:

image.png

客户端向具体资源的URL发送PUT请求/employee/21。请求的HTTP body中包含要更新的属性值(21号员工的新名称“Bruce Wayne”)。

REST服务器更新ID为21的员工名称,并使用HTTP状态码200表示更改成功。

推荐用复数名词

推荐:


/employees

/employees/21

不推荐:


/employee

/employee/21

事实上,这是个人爱好问题,但复数形式更为常见。此外,在资源集合URL上用GET方法,它更直观,特别是GET /employees?state=external、POST /employees、PUT /employees/56。但最重要的是:避免复数和单数名词混合使用,这显得非常混乱且容易出错。


对可选的、复杂的参数,使用查询字符串(?)。

不推荐做法:


GET /employees

GET /externalEmployees

GET /internalEmployees

GET /internalAndSeniorEmployees

为了让你的URL更小、更简洁。为资源设置一个基本URL,将可选的、复杂的参数用查询字符串表示。


GET /employees?state=internal&maturity=senior

使用HTTP状态码

RESTful Web服务应使用合适的HTTP状态码来响应客户端请求

2xx - 成功 - 一切都很好

4xx - 客户端错误 - 如果客户端发生错误(例如客户端发送无效请求或未被授权)

5xx – 服务器错误 - 如果服务器发生错误(例如,尝试处理请求时出错)

参考维基百科上的HTTP状态代码。但是,其中的大部分HTTP状态码都不会被用到,只会用其中的一小部分。通常会用到一下几个:

2xx:成功 3xx:重定向 4xx:客户端错误 5xx:服务器错误

200 成功 301 永久重定向 400 错误请求 500 内部服务器错误

201 创建 304 资源未修改 401未授权

403 禁止

404 未找到

返回有用的错误提示

除了合适的状态码之外,还应该在HTTP响应正文中提供有用的错误提示和详细的描述。这是一个例子。请求:


GET /employees?state=super

响应:

// 400 Bad Request
{
    "message": "You submitted an invalid state. Valid state values are 'internal' or 'external'",
    "errorCode": 352,
    "additionalInformation" : 
    "http://www.domain.com/rest/errorcode/352"
}

使用小驼峰命名法

使用小驼峰命名法作为属性标识符。

{ “yearOfBirth”: 1982 }

不要使用下划线(year_of_birth)或大驼峰命名法(YearOfBirth)。通常,RESTful Web服务将被JavaScript编写的客户端使用。客户端会将JSON响应转换为JavaScript对象(通过调用var person = JSON.parse(response)),然后调用其属性。因此,最好遵循JavaScript代码通用规范。

对比:


person.year_of_birth // 不推荐,违反JavaScript代码通用规范

person.YearOfBirth // 不推荐,JavaScript构造方法命名

person.yearOfBirth // 推荐

在URL中强制加入版本号

从始至终,都使用版本号发布您的RESTful API。将版本号放在URL中以是必需的。如果您有不兼容和破坏性的更改,版本号将让你能更容易的发布API。发布新API时,只需在增加版本号中的数字。这样的话,客户端可以自如的迁移到新API,不会因调用完全不同的新API而陷入困境。 使用直观的 “v” 前缀来表示后面的数字是版本号。


/v1/employees

你不需要使用次级版本号(“v1.2”),因为你不应该频繁的去发布API版本。

提供分页信息

一次性返回数据库所有资源不是一个好主意。因此,需要提供分页机制。通常使用数据库中众所周知的参数offset和limit。

/employees?offset=30&limit=15 #返回30 到 45的员工

如果客户端没有传这些参数,则应使用默认值。通常默认值是offset = 0和limit = 10。如果数据库检索很慢,应当减小limit值。


/employees #返回0 到 10的员工

此外,如果您使用分页,客户端需要知道资源总数。例:请求:


GET /employees

响应:

{
  "offset": 0,
  "limit": 10,
  "total": 3465,
  "employees": [
    //...
  ]
}

非资源请求用动词

有时API调用并不涉及资源(如计算,翻译或转换)。例:

GET /translate?from=de_DE&to=en_US&text=Hallo

GET /calculate?para2=23&para2=432

在这种情况下,API响应不会返回任何资源。而是执行一个操作并将结果返回给客户端。因此,您应该在URL中使用动词而不是名词,来清楚的区分资源请求和非资源请求。

考虑特定资源搜索和跨资源搜索

提供对特定资源的搜索很容易。只需使用相应的资源集合URL,并将搜索字符串附加到查询参数中即可。

GET /employees?query=Paul

如果要对所有资源提供全局搜索,则需要用其他方法。前文提到,对于非资源请求URL,使用动词而不是名词。因此,您的搜索网址可能如下所示:


GET /search?query=Paul //返回 employees, customers, suppliers 等等.

在响应参数中添加浏览其它API的链接

理想情况下,不会让客户端自己构造使用REST API的URL。让我们思考一个例子。

客户端想要访问员工的薪酬表。为此,他必须知道他可以通过在员工URL(例如/employees/21/salaryStatements)中附加字符串“salaryStatements”来访问薪酬表。这个字符串连接很容易出错,且难以维护。如果你更改了访问薪水表的REST API的方式(例如变成了/employees/21/salary-statement或/employees/21/paySlips),所有客户端都将中断。

更好的方案是在响应参数中添加一个links字段,让客户端可以自动变更。

请求:


GET /employees/

响应:

//...
   {
      "id":1,
      "name":"Paul",
      "links": [
         {
            "rel": "salary",
            "href": "/employees/1/salaryStatements"
         }
      ]
   },
//...

如果客户端完全依靠links中的字段获得薪资表,你更改了API,客户端将始终获得一个有效的URL(只要你更改了link字段,请求的URL会自动更改),不会中断。另一个好处是,你的API变得可以自我描述,需要写的文档更少。

在分页时,您还可以添加获取下一页或上一页的链接示例。只需提供适当的偏移和限制的链接示例。

GET /employees?offset=20&limit=10
{
  "offset": 20,
  "limit": 10,
  "total": 3465,
  "employees": [
    //...
  ],
  "links": [
     {
        "rel": "nextPage",
        "href": "/employees?offset=30&limit=10"
     },
     {
        "rel": "previousPage",
        "href": "/employees?offset=10&limit=10"
     }
  ]
}
目录
相关文章
|
1月前
|
Java API 数据库
构建RESTful API已经成为现代Web开发的标准做法之一。Spring Boot框架因其简洁的配置、快速的启动特性及丰富的功能集而备受开发者青睐。
【10月更文挑战第11天】本文介绍如何使用Spring Boot构建在线图书管理系统的RESTful API。通过创建Spring Boot项目,定义`Book`实体类、`BookRepository`接口和`BookService`服务类,最后实现`BookController`控制器来处理HTTP请求,展示了从基础环境搭建到API测试的完整过程。
48 4
|
3月前
【Azure 应用服务】Web App Service 中的 应用程序配置(Application Setting) 怎么获取key vault中的值
【Azure 应用服务】Web App Service 中的 应用程序配置(Application Setting) 怎么获取key vault中的值
|
21天前
|
JavaScript 前端开发 开发工具
web项目规范配置(husky、eslint、lint-staged、commit)
通过上述配置,可以确保在Web项目开发过程中自动进行代码质量检查和规范化提交。Husky、ESLint、lint-staged和Commitlint共同作用,使得每次提交代码之前都会自动检查代码风格和语法问题,防止不符合规范的代码进入代码库。这不仅提高了代码质量,还保证了团队协作中的一致性。希望这些配置指南能帮助你建立高效的开发流程。
34 5
|
25天前
【Azure App Service】PowerShell脚本批量添加IP地址到Web App允许访问IP列表中
Web App取消公网访问后,只允许特定IP能访问Web App。需要写一下段PowerShell脚本,批量添加IP到Web App的允许访问IP列表里!
|
26天前
|
JSON API 数据格式
如何使用Python和Flask构建一个简单的RESTful API。Flask是一个轻量级的Web框架
本文介绍了如何使用Python和Flask构建一个简单的RESTful API。Flask是一个轻量级的Web框架,适合小型项目和微服务。文章从环境准备、创建基本Flask应用、定义资源和路由、请求和响应处理、错误处理等方面进行了详细说明,并提供了示例代码。通过这些步骤,读者可以快速上手构建自己的RESTful API。
28 2
|
3月前
|
关系型数据库 MySQL Linux
【Azure 应用服务】在创建Web App Service的时候,选Linux系统后无法使用Mysql in App
【Azure 应用服务】在创建Web App Service的时候,选Linux系统后无法使用Mysql in App
【Azure 应用服务】在创建Web App Service的时候,选Linux系统后无法使用Mysql in App
|
3月前
|
Java 网络架构 数据格式
Struts 2 携手 RESTful:颠覆传统,重塑Web服务新纪元的史诗级组合!
【8月更文挑战第31天】《Struts 2 与 RESTful 设计:构建现代 Web 服务》介绍如何结合 Struts 2 框架与 RESTful 设计理念,构建高效、可扩展的 Web 服务。Struts 2 的 REST 插件提供简洁的 API 和约定,使开发者能快速创建符合 REST 规范的服务接口。通过在 `struts.xml` 中配置 `<rest>` 命名空间并使用注解如 `@Action`、`@GET` 等,可轻松定义服务路径及 HTTP 方法。
64 0
|
3月前
|
前端开发 API 开发者
JSF与RESTful服务的完美邂逅:如何打造符合现代Web潮流的数据交互新体验
【8月更文挑战第31天】随着互联网技术的发展,RESTful架构风格因其实现简便与无状态特性而在Web服务构建中日益流行。本文探讨如何结合JavaServer Faces (JSF) 和 JAX-RS 构建RESTful API,展示从前端到后端分离的完整解决方案。通过定义资源类、配置 `web.xml` 文件以及使用依赖注入等步骤,演示了在JSF项目中实现RESTful服务的具体过程,为Java开发者提供了实用指南。
41 0
|
3月前
|
Shell PHP Windows
【Azure App Service】Web Job 报错 UNC paths are not supported. Defaulting to Windows directory.
【Azure App Service】Web Job 报错 UNC paths are not supported. Defaulting to Windows directory.
|
3月前
|
Linux 应用服务中间件 网络安全
【Azure 应用服务】查看App Service for Linux上部署PHP 7.4 和 8.0时,所使用的WEB服务器是什么?
【Azure 应用服务】查看App Service for Linux上部署PHP 7.4 和 8.0时,所使用的WEB服务器是什么?
下一篇
无影云桌面