這一章講述了RESTful API的基本概念和設計原則。通過比較傳統方式和RESTful方式操作資源的URL定義,能明顯看出RESTful的簡潔和意圖明確。RESTful的API設計使用不同的HTTP方法來操作資源,比如GET用於查詢、POST用於新增、PUT用於更新全部欄位、PATCH用於更新部分... ...
第十六章、RestFul API
-
什麼是REST
REST 全稱是 Resource Representational State Transfer,中文意思是表述性狀態轉移,它首次出現在2000年Roy Fielding的博士論文中,Roy Fielding是HTTP規範的主要編寫者之一。他在論文中表示:我這篇文章的目的就是想在符合架構原理的前提下,理解和評估以網路為基礎的應用軟體的架構設計,得到一個功能強、性能好、適宜通信的架構。REST指的是一組架構約束條條件和原則,“如果一個架構複合REST的約束條件和原則,我們就稱它為RESTful架構”
RestFul:是一種以網路為基礎構架一種架構一種架構風格,一個符合Rest設計原則和約束成這個架構為RestFul。
REST本身並沒有創造新的技術、組件和服務、而隱藏在RESTful背後的理念就是使用web的現有特征和能力,更好地使用現有web標準中的一些準則和約束。
-
RestFul遵循的架構約束
- 客戶端-伺服器架構:由客戶端、伺服器和資源組成,通過HTTP管理請求。
- 無狀態的客戶端-伺服器通信:每個請求都是獨立的,不會在請求之間保存客戶端信息。
- 可緩存的數據:通過緩存數據來優化客戶端-伺服器交互。
- 統一的介面:信息以標準形式傳輸,包括資源的標識和表示之間的分離,以及自描述的消息返回給客戶端。
-
總結
RestFul是一種架構風格,不是標準,只是提供了一組設計原則和約束條件,它主要用於客戶端和伺服器交互類的軟體,基於這個風格設計的軟體可以更簡潔、更有層次,更易於實現緩存等機制。
-
URL定義
- 資源:互聯網所有的事務都可以稱為資源:一張圖片、一段文本、一條記錄…..
- 資源操作:使用POST添加、DELETE刪除,PUT修改,GET查詢,使用不同請求方法對資源進行操作
- 刪除 delete
- 查詢 get
- 添加 post
- 修改 put(修改全部欄位) patch(更新部分欄位)
-
傳統方式操作資源
- http://127.0.0.1/item/queryUser.action?id=1 查詢 GET
- http://127.0.0.1/item/saveUser 新增 POST
- http://127.0.0.1/item/updateUser.action 更新 PUT
- http://127.0.0.1/item/deleteUser.action?id=1 刪除 DELETE
註意:傳統的操作是沒有問題的,大神認為有問題的:你每次請求的介面或者地址都是在做描述,其實完全沒有這個必要,我使用了get請求,就是代表查詢,使用post就是代表新增請求,我的意圖很明顯,完全沒有必要做描述,這就是為什麼有了restful。
-
使用RESTful操作資源
- 【GET】 /users 查詢用戶信息列表
- 【GET】 /users/1001 查看某個用戶信息
- 【POST】 /users 新增用戶信息
- 【PUT】 /users/1001 更新用戶信息(全部欄位)
- 【PATCH】 /users/1001 更新用戶信息(部分欄位)
- 【DELETE】 /users/1001 刪除用戶信息
第一個RestFul風格的API
@RestController // 專用於restful風格的註解,只能返回json/Xml格式的數據
@RequestMapping("/v1/users")
public class UserController {
private static final Logger log = LoggerFactory.getLogger(UserController.class);
/**
* 獲取單個用戶
* @param id
* @return
*/
@GetMapping("/{id}")
public User user(@PathVariable("id") Integer id) {
log.info("id:{}", id);
return new User(21, "小明", 2000.2, new Date());
}
/**
* 用戶列表
* @return
*/
@GetMapping()
public List<User> users() {
ArrayList<User> users = new ArrayList<>();
users.add(new User(21, "小明", 2000.2, new Date()));
users.add(new User(16, "小紅", 3000.2, new Date()));
return users;
}
/**
* 添加用戶
* @param user
*/
@PostMapping
public void saveUser(@RequestBody User user) {
log.info("用戶信息:{}", user);
//調用業務方法...
}
/**
* 修改用戶
* @param user
*/
@PutMapping("/{id}")
public void update(@PathVariable("id") Integer id, @RequestBody User user) {
log.info("更新用戶的id:{}",id);
log.info("修改信息:{}", user);
//調用業務方法...
}
/**
* 刪除用戶
* @param id
*/
@DeleteMapping("/{id}")
public void delete(@PathVariable("id") Integer id) {
log.info("id:{}",id);
}
}
**@RestController
註解**
**@RestController**
註解則是用來創建 REST API 控制器的。在 REST API 中,通常需要返回 JSON 或 XML 格式的數據,而不是 HTML 視圖。因此,@RestController
註解結合了 @Controller
和 @ResponseBody
註解的功能,可以方便地實現 REST API 的開發。
@RequestBody
註解
@RequestBody
註解將請求體中的 JSON 數據轉換為 Java 對象。
**@PathVariable
註解**
這個註解用於處理RESTful API中的URL路徑參數。例如**@GetMapping("/{id}")
** ,我們需要使用@PathVariable
註解來提取URI中的{id},並將其作為方法的參數。
@PathVariable
還有一些屬性可以使用:
-
指定路徑變數的名稱: 如果路徑變數的名稱與方法參數的名稱不同,我們可以在
@PathVariable
註解中指定路徑變數的名稱。@GetMapping("/api/employees/{empId}") public String getEmployeeById(@PathVariable("empId") String id) { return "ID: " + id; }
-
指定預設值: 我們還可以在@PathVariable註解中指定預設值,以防路徑變數未提供。
@GetMapping("/api/employees/{id}") public String getEmployeeById(@PathVariable(name = "id", required = false, defaultValue = "0") String id) { return "ID: " + id; }
-
如果業務邏輯還要往深一層查,比如查某個人的某個寵物,那麼可以這樣
/** * 獲取某個人的所有寵物信息 */ @GetMapping("/{id}/pets") public List<Pet> pets(@PathVariable("id") Integer id) { log.info("查詢人的id:{}", id); return Arrays.asList(new Pet(2, "旺財", 2),new Pet(3,"花花",1)); } /** * 獲取某個人的某個寵物信息 */ @GetMapping("/{id}/pets/{pid}") public Pet pets(@PathVariable("id") Integer id,@PathVariable("pid") Integer pid) { log.info("查詢人的id:{}", id); Pet pet = new Pet(2, "旺財", 2); return pet; }
ResponseEntity
和 HttpStatus
ResponseEntity
代表了整個 HTTP 響應,包括狀態碼、頭部信息和響應體。可以完全配置 HTTP 響應。ResponseEntity
提供了泛型,所以我們可以使用它來代替API中的返回值
-
示例
//ResponseEntity springmvc中用於restful響應類,可以提供響應的狀態碼,以及自定義響應頭信息 // HttpStatus:springmvc提供的枚舉類型類 網路狀態碼 /** * 獲取單個用戶 */ @GetMapping("/{id}") public ResponseEntity<User> user(@PathVariable("id") Integer id) { log.info("id:{}", id); User user = new User(21, "小明", 2000.2, new Date()); return new ResponseEntity<>(user, HttpStatus.OK);// 狀態碼:200 } /** * 用戶列表 */ @GetMapping() public ResponseEntity<List<User>> users() { ArrayList<User> users = new ArrayList<>(); users.add(new User(21, "小明", 2000.2, new Date())); users.add(new User(16, "小紅", 3000.2, new Date())); return new ResponseEntity<>(users,HttpStatus.OK);// 狀態碼:200 } /** * 添加用戶 */ @PostMapping public ResponseEntity<Void> saveUser(@RequestBody User user) { log.info("用戶信息:{}", user); //調用業務方法... return new ResponseEntity<>(HttpStatus.NO_CONTENT);//沒有內容,狀態碼204 }
作者:揚眉劍出鞘
出處: https://www.cnblogs.com/eyewink/
本文版權歸作者和博客園共有,歡迎轉載,但未經作者同意必須保留此段聲明,且在文章頁面明顯位置給出原文連接,否則保留追究法律責任的權利。