引入依赖
<dependency>
<groupId>io.esastack</groupId>
<artifactId>restlight-springmvc-provider</artifactId>
<version>${restlight.version}</version>
</dependency>
This is the multi-page printable view of this section. Click here to print.
Restlight
支持了Spring MVC的使用习惯,你可以按照Spring MVC的方式使用Restlight引入依赖
<dependency>
<groupId>io.esastack</groupId>
<artifactId>restlight-springmvc-provider</artifactId>
<version>${restlight.version}</version>
</dependency>
@Controller
@RestController
@RequestMapping
@GetMapping
@PostMapping
@PutMapping
@DeleteMapping
@PatchMapping
@ResponseStatus
@ControllerAdvice
@ExceptionHandler
@RequestParam
@RequestHeader
@PathVariable
@CookieValue
@MatrixVariable
@RequestAttribute
@RequestParam
, @ReqeustHeader
,@PathVariable
,@CookieValue
, @MatrixVariable
,@RequestAttribute
参数绑定相关注解除SpringMVC
用法外,同时支持
Constructor
接收一个String
类型的参数eg.
public void foo(@RequestParam User user) {
//...
}
static class User {
final String name;
public User(String str) {
this.name = name;
}
}
valueOf()
或者fromString()
方法eg.
public void foo(@RequestParam User user, @RequestHeader Car car) {
//...
}
static class User {
String name;
public static User valueOf(String str) {
User user = new User();
user.name = name;
return user;
}
}
static class Car {
String name;
public static Car fromString(String str) {
Car car = new Car();
car.name = name;
return car;
}
}
@RequestParam
除普通用法外, 当未指定value()
或者name
且参数对象为Map<String, List<String>
类型时, 将整个ParameterMap(即AsyncRequest.getParameterMap)作为参数的值。
eg.
public void foo(@RequestParam Map<String, List<String> params) {
//...
}
@CookieValue
普通String类型
public void foo(@CookieValue String c) {
//...
}
Cookie对象(io.netty.handler.codec.http.cookie.Cookie)
public void foo(@CookieValue Cookie c) {
//...
}
获取所有的Cookie
public void foo(@CookieValue Set<Cookie> cookies) {
//...
}
@RequestHeader
除获取单个header之外, 可以如果参数类型为io.netty.handler.codec.http.HttpHeaders
则以所有的Header作为参数的值
eg:
public void foo(@RequestHeader HttpHeaders headers) {
//...
}
Restlight
支持业务自定义异常处理逻辑。对于Controller方法中抛出的异常,处理逻辑和顺序如下(注意:一个异常只会被处理一次):
1.尝试在Controller内部查找异常处理方法来处理当前异常,未找到进入2 2.尝试寻找全局异常处理方法来处理当前异常,未找到则返回错误信息
局部异常处理方法只能处理当前Controller中抛出的异常,示例如下:
@RestController
@RequestMapping("/exception")
public class LocalExceptionResolver {
@RequestMapping("/willBeHandled")
public void willBeHandled() {
throw new IllegalArgumentException("IllegalArgumentException...");
}
@RequestMapping("/willNotBeHandled")
public void willNotBeHandled() {
throw new RuntimeException("RuntimeException...");
}
@ExceptionHandler(IllegalArgumentException.class)
public String handleLocalException(IllegalArgumentException ex) {
return "HandleLocalException [" + ex.getMessage() + "]";
}
}
handleLocalException(XXX)
方法会处理当前类中所有的IllegalArgumentException
异常。
@ControllerAdvice
全局异常处理通过@ControllerAdvice
或@RestControllerAdvice
来标识全局异常处理类,并可通过相应的属性设置该全局异常处理类生效的范围。使用示例如下:
@RestControllerAdvice(basePackages = {"esa.restlight.samples.starter.exceptionhandler", "esa.restlight.samples.starter.controller"})
public class GlobalExceptionResolver {
@ExceptionHandler(Exception.class)
public Result handleException(Exception ex) {
return Result.ok();
}
static class Result {
private int status;
private String msg;
static Result ok() {
Result r = new Result();
r.status = 200;
return r;
}
// getter and setter
}
}
如上所示, handleException(XXX)
方法会处理esa.restlight.samples.starter.exceptionhandler
和esa.restlight.samples.starter.controller
包中抛出的所有Exception
。
为了让用户更方便的使用异常处理, 类似的我们支持像Controller上一样的去使用一些注解的功能如 @RequestParam
, @RequestHeader
, @CookieValue
等方便的进行参数绑定而不是自己手动的去Request里面取并做一次参数转换的操作。
eg:
@ControllerAdvice
public class GlobalExceptionResolver {
@ExceptionHandler(Exception.class)
public String handleException(@RequestParam("foo") String foo, Exception ex) {
// do something here...
return "HandleGlobalException [" + ex.getMessage() + "]";
}
}
@RequestBody
的功能
异常处理器可以类似Controller中异步处理一样完成异步的处理
Restlight
异步支持
使用CompletableFuture异步方式:
@ExceptionHanlder(Exception.class)
public CompletableFuture<String> handleExcption(Exception ex) {
return CompletableFuture.supplyAsync(() -> {
// ...
return "Hello Restlight!";
});
}
ListenableFuture(Guava)
与Future(io.netty.util.concurrent.Future)
同理。