REST风格

  • REST简介
  • 优点
  • 行为动作区分操作
  • 总结
  • 注意事项
  • RESTful
  • RESTful实现
  • 思路分析
  • 代码实现
  • 新增功能
  • 删除功能
  • 修改功能
  • 查询功能
  • 总结
  • 快速开发—RESTful优化
  • 优化方案


REST简介

  • REST(Representational State Transfer),表现性状态转换,它是一种软件架构风格
    表示网络资源的两种方式:
  • 传统风格资源描述形式

http://localhost/user/getById?id=1    查询id为1的用户信息

http://localhost/user/saveUser    保存用户信息

  • REST风格资源描述形式

http://localhost/user/1

http://localhost/user

优点

  • 隐藏资源的访问行为,无法通过地址得知对资源是何种操作
  • 书写简化
  • 原因
  • 传统方式一般是一个请求url对应一种操作,操作繁琐且不安全,在了解程序的人的眼中可能会通过url解读出相对于的操作
     
     

行为动作区分操作

按照REST风格访问资源时使用请求方式区分对资源进行了何种操作

  • http://localhost/users    查询全部用户信息 GET(查询)
  • http://localhost/users/1    查询指定用户信息 GET(查询)
  • http://localhost/users    添加用户信息 POST(新增/保存)
  • http://localhost/users    修改用户信息 PUT(修改/更新)
  • http://localhost/users/1    删除用户信息 DELETE(删除)

总结

通常使用四种请求方式:

  • 发送GET请求是用来做查询
  • 发送POST请求是用来做新增
  • 发送PUT请求是用来做修改
  • 发送DELETE请求是用来做删除

注意事项

  • 上述行为是约定方式,约定不是规范,可以打破,所以称REST风格,而不是REST规范。虽然不是规范,但现在基本都用rest风格
  • REST提供了对应的架构方式,按照这种架构设计项目可以降低开发的复杂性,提高系统的可伸缩性
  • REST中规定GET/POST/PUT/DELETE针对的是查询/新增/修改/删除,但是我们如果非要用GET请求做删除,这点在程序上运行是可以实现的
  • 但是如果绝大多数人都遵循这种风格,你写的代码让别人读起来就有点莫名其妙了。
  • 描述模块的名称通常使用复数,也就是加s的格式描述,表示此类资源,而非单个资源,例如:users、books、accounts…

RESTful

   根据REST风格对资源进行访问称为RESTful
 
 
 
 

RESTful实现

思路分析

需求:将之前的增删改查替换成RESTful的开发方式。
1.之前不同的请求有不同的路径,现在要将其修改为统一的请求路径
修改前: 新增: /save ,修改: /update,删除 /delete…
修改后: 增删改查: /users
2.根据GET查询、POST新增、PUT修改、DELETE删除对方法的请求方式进行限定
3.发送请求的过程中如何设置请求参数?

代码实现

    主要通过 @RequestMapping的method属性@PathVariable实现

新增功能

原方法

@Controller
public class UserController {
    @RequestMapping("/save")
    @ResponseBody
    public String save(@RequestBody User user) {
        System.out.println("user save..."+user);
        return "{'module':'user save'}";
    }
}

RESTful实现后

@Controller
public class UserController {
    //设置当前请求方法为POST,表示REST风格中的添加操作
    @RequestMapping(value = "/users",method = RequestMethod.POST)
    @ResponseBody
    public String save() {
        System.out.println("user save...");
        return "{'module':'user save'}";
    }
}

 
 

删除功能

原方法

@Controller
public class UserController {
    @RequestMapping("/delete")
    @ResponseBody
    public String delete(Integer id) {
        System.out.println("user delete..." + id);
        return "{'module':'user delete'}";
    }
}

RESTful实现后(有缺陷)

@Controller
public class UserController {
    //设置当前请求方法为DELETE,表示REST风格中的删除操作
    @RequestMapping(value = "/users",method = RequestMethod.DELETE)
    @ResponseBody
    public String delete(Integer id) {
        System.out.println("user delete..." + id);
        return "{'module':'user delete'}";
    }
}

缺陷:未携带需删除数据项的id

RESTful实现后(优化后 --通过@PathVariable)
  @PathVariable译作可变路径,作用是声明这个参数来自于路径

@Controller
public class UserController {
    //设置当前请求方法为DELETE,表示REST风格中的删除操作
    @RequestMapping(value = "/users/{id}",method = RequestMethod.DELETE)
    @ResponseBody
    //@PathVariable声明此参数来自于路径。使参数和@RequestMapping中路径中的参数绑定。如果名称不一样,需要起别名再绑定
    public String delete(@PathVariable Integer id) {
        System.out.println("user delete..." + id);
        return "{'module':'user delete'}";
    }
}
1.当形参名和路径中{}中的值不一致时,需要起别名

java restful 語言切換_学习


2.需要传递多个参数时,路径后加斜杠新增参数
@Controllerpublic class UserController {
   //设置当前请求方法为DELETE,表示REST风格中的删除操作
   @RequestMapping(value = "/users/{id}/{name}",method = >RequestMethod.DELETE)
   @ResponseBody
   public String delete(@PathVariable Integer id,@PathVariable String name) >{
       System.out.println("user delete..." + id+","+name);
       return "{'module':'user delete'}";
   }
}


 

修改功能

原方法

@Controller
public class UserController {
    @RequestMapping("/update")
    @ResponseBody
    public String update(@RequestBody User user) {
        System.out.println("user update..." + user);
        return "{'module':'user update'}";
    }
}

RESTful实现后

@Controller
public class UserController {
    //设置当前请求方法为PUT,表示REST风格中的修改操作
    @RequestMapping(value = "/users",method = RequestMethod.PUT)
    @ResponseBody
    public String update(@RequestBody User user) {
        System.out.println("user update..." + user);
        return "{'module':'user update'}";
    }
}

 
 

查询功能

根据ID查询

原方法

@Controller
public class UserController {
    @RequestMapping("/getById")
    @ResponseBody
    public String getById(Integer id) {
        System.out.println("user getById..." + id);
        return "{'module':'user getById'}";
    }
}

RESTful实现后

@Controller
public class UserController {
    //设置当前请求方法为GET,表示REST风格中的查询操作
    @RequestMapping(value = "/users/{id}" ,method = RequestMethod.GET)
    @ResponseBody
    public String getById(@PathVariable Integer id){
        System.out.println("user getById..."+id);
        return "{'module':'user getById'}";
    }
}

查询所有

原方法

@Controller
public class UserController {
    @RequestMapping("/findAll")
    @ResponseBody
    public String getAll() {
        System.out.println("user getAll...");
        return "{'module':'user getAll'}";
    }
}

RESTful实现后

@Controller
public class UserController {
    //设置当前请求方法为GET,表示REST风格中的查询操作
    @RequestMapping(value = "/users" ,method = RequestMethod.GET)
    @ResponseBody
    public String getAll() {
        System.out.println("user getAll...");
        return "{'module':'user getAll'}";
    }
}

总结

(1)设定Http请求动作(动词)
    @RequestMapping(value=“”,method = RequestMethod.POST|GET|PUT|DELETE)
(2)设定请求参数(路径变量)
  

@RequestMapping(value=“/users/{id}”,method = RequestMethod.DELETE)
     @ReponseBody
     public String delete(@PathVariable Integer id){
     }

 
 
 
 

快速开发—RESTful优化

    上述RESTful风格开发中的缺陷

java restful 語言切換_java_02

问题1

:每个方法的@RequestMapping注解中都定义了访问路径/books,重复性太高。


问题2

:每个方法的@RequestMapping注解中都要使用method属性定义请求方式,重复性太高。


问题3

:每个方法响应json都需要加上@ResponseBody注解,重复性太高。

优化方案

  • @RestController合并@Controller和@ResponseBody
  • @GetMapping @PostMapping @PutMapping @DeleteMapping代替@RequestMapping(免除method的重复)

优化后各功能代码

@RestController //@Controller + ReponseBody
@RequestMapping("/books")
public class BookController {
 
    //@RequestMapping(method = RequestMethod.POST)
    @PostMapping
    public String save(@RequestBody Book book){
        System.out.println("book save..." + book);
        return "{'module':'book save'}";
    }
 
    //@RequestMapping(value = "/{id}",method = RequestMethod.DELETE)
    @DeleteMapping("/{id}")
    public String delete(@PathVariable Integer id){
        System.out.println("book delete..." + id);
        return "{'module':'book delete'}";
    }
 
    //@RequestMapping(method = RequestMethod.PUT)
    @PutMapping
    public String update(@RequestBody Book book){
        System.out.println("book update..." + book);
        return "{'module':'book update'}";
    }
 
    //@RequestMapping(value = "/{id}",method = RequestMethod.GET)
    @GetMapping("/{id}")
    public String getById(@PathVariable Integer id){
        System.out.println("book getById..." + id);
        return "{'module':'book getById'}";
    }
 
    //@RequestMapping(method = RequestMethod.GET)
    @GetMapping
    public String getAll(){
        System.out.println("book getAll...");
        return "{'module':'book getAll'}";
    }
}

注解

名称

@RestController

类型

类注解

位置

基于SpringMVC的RESTful开发控制器定义上方

作用

设置当前控制器类为RESTful风格,等同于@Controller与@ResponseBody两个注解组合功能

名称

@GetMapping @PostMapping @PutMapping @DeleteMapping

类型

方法注解

位置

基于SpringMVC的RESTful开发控制器方法定义上方

作用

设置当前控制器方法请求访问路径与请求动作,每种对应一个请求动作,例如@GetMapping对应GET请求

相关属性

value(默认):请求访问路径