webclient java_spring5 webclient使用指南详解

之前写了一篇restTemplate使用实例,由于spring 5全面引入reactive,同时也有了restTemplate的reactive版webclient,本文就来对应展示下webclient的基本使用。

请求携带header

携带cookie

@Test

public void testWithCookie(){

Mono resp = WebClient.create()

.method(HttpMethod.GET)

.uri("http://baidu.com")

.cookie("token","xxxx")

.cookie("JSESSIONID","XXXX")

.retrieve()

.bodyToMono(String.class);

LOGGER.info("result:{}",resp.block());

}

携带basic auth

@Test

public void testWithBasicAuth(){

String basicAuth = "Basic "+ Base64.getEncoder().encodeToString("user:pwd".getBytes(StandardCharsets.UTF_8));

LOGGER.info(basicAuth);

Mono resp = WebClient.create()

.get()

.uri("http://baidu.com")

.header(HttpHeaders.AUTHORIZATION,basicAuth)

.retrieve()

.bodyToMono(String.class);

LOGGER.info("result:{}",resp.block());

}

设置全局user-agent

@Test

public void testWithHeaderFilter(){

WebClient webClient = WebClient.builder()

.defaultHeader(HttpHeaders.USER_AGENT, "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/63.0.3239.132 Safari/537.36")

.filter(ExchangeFilterFunctions

.basicAuthentication("user","password"))

.filter((clientRequest, next) -> {

LOGGER.info("Request: {} {}", clientRequest.method(), clientRequest.url());

clientRequest.headers()

.forEach((name, values) -> values.forEach(value -> LOGGER.info("{}={}", name, value)));

return next.exchange(clientRequest);

})

.build();

Mono resp = webClient.get()

.uri("https://baidu.com")

.retrieve()

.bodyToMono(String.class);

LOGGER.info("result:{}",resp.block());

}

get请求

使用placeholder传递参数

@Test

public void testUrlPlaceholder(){

Mono resp = WebClient.create()

.get()

//多个参数也可以直接放到map中,参数名与placeholder对应上即可

.uri("http://www.baidu.com/s?wd={key}&other={another}","北京天气","test") //使用占位符

.retrieve()

.bodyToMono(String.class);

LOGGER.info("result:{}",resp.block());

}

使用uriBuilder传递参数

@Test

public void testUrlBiulder(){

Mono resp = WebClient.create()

.get()

.uri(uriBuilder -> uriBuilder

.scheme("http")

.host("www.baidu.com")

.path("/s")

.queryParam("wd", "北京天气")

.queryParam("other", "test")

.build())

.retrieve()

.bodyToMono(String.class);

LOGGER.info("result:{}",resp.block());

}

post表单

@Test

public void testFormParam(){

MultiValueMap formData = new LinkedMultiValueMap<>();

formData.add("name1","value1");

formData.add("name2","value2");

Mono resp = WebClient.create().post()

.uri("http://www.w3school.com.cn/test/demo_form.asp")

.contentType(MediaType.APPLICATION_FORM_URLENCODED)

.body(BodyInserters.fromFormData(formData))

.retrieve().bodyToMono(String.class);

LOGGER.info("result:{}",resp.block());

}

post json

使用bean来post

static class Book {

String name;

String title;

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public String getTitle() {

return title;

}

public void setTitle(String title) {

this.title = title;

}

}

@Test

public void testPostJson(){

Book book = new Book();

book.setName("name");

book.setTitle("this is title");

Mono resp = WebClient.create().post()

.uri("http://localhost:8080/demo/json")

.contentType(MediaType.APPLICATION_JSON_UTF8)

.body(Mono.just(book),Book.class)

.retrieve().bodyToMono(String.class);

LOGGER.info("result:{}",resp.block());

}

直接post raw json

@Test

public void testPostRawJson(){

Mono resp = WebClient.create().post()

.uri("http://localhost:8080/demo/json")

.contentType(MediaType.APPLICATION_JSON_UTF8)

.body(BodyInserters.fromObject("{\n" +

" \"title\" : \"this is title\",\n" +

" \"author\" : \"this is author\"\n" +

"}"))

.retrieve().bodyToMono(String.class);

LOGGER.info("result:{}",resp.block());

}

post二进制--上传文件

@Test

public void testUploadFile(){

HttpHeaders headers = new HttpHeaders();

headers.setContentType(MediaType.IMAGE_PNG);

HttpEntity entity = new HttpEntity<>(new ClassPathResource("parallel.png"), headers);

MultiValueMap parts = new LinkedMultiValueMap<>();

parts.add("file", entity);

Mono resp = WebClient.create().post()

.uri("http://localhost:8080/upload")

.contentType(MediaType.MULTIPART_FORM_DATA)

.body(BodyInserters.fromMultipartData(parts))

.retrieve().bodyToMono(String.class);

LOGGER.info("result:{}",resp.block());

}

下载二进制

下载图片

@Test

public void testDownloadImage() throws IOException {

Mono resp = WebClient.create().get()

.uri("http://www.toolip.gr/captcha?complexity=99&size=60&length=9")

.accept(MediaType.IMAGE_PNG)

.retrieve().bodyToMono(Resource.class);

Resource resource = resp.block();

BufferedImage bufferedImage = ImageIO.read(resource.getInputStream());

ImageIO.write(bufferedImage, "png", new File("captcha.png"));

}

下载文件

@Test

public void testDownloadFile() throws IOException {

Mono resp = WebClient.create().get()

.uri("http://localhost:8080/file/download")

.accept(MediaType.APPLICATION_OCTET_STREAM)

.exchange();

ClientResponse response = resp.block();

String disposition = response.headers().asHttpHeaders().getFirst(HttpHeaders.CONTENT_DISPOSITION);

String fileName = disposition.substring(disposition.indexOf("=")+1);

Resource resource = response.bodyToMono(Resource.class).block();

File out = new File(fileName);

FileUtils.copyInputStreamToFile(resource.getInputStream(),out);

LOGGER.info(out.getAbsolutePath());

}

错误处理

@Test

public void testRetrieve4xx(){

WebClient webClient = WebClient.builder()

.baseUrl("https://api.github.com")

.defaultHeader(HttpHeaders.CONTENT_TYPE, "application/vnd.github.v3+json")

.defaultHeader(HttpHeaders.USER_AGENT, "Spring 5 WebClient")

.build();

WebClient.ResponseSpec responseSpec = webClient.method(HttpMethod.GET)

.uri("/user/repos?sort={sortField}&direction={sortDirection}",

"updated", "desc")

.retrieve();

Mono mono = responseSpec

.onStatus(e -> e.is4xxClientError(),resp -> {

LOGGER.error("error:{},msg:{}",resp.statusCode().value(),resp.statusCode().getReasonPhrase());

return Mono.error(new RuntimeException(resp.statusCode().value() + " : " + resp.statusCode().getReasonPhrase()));

})

.bodyToMono(String.class)

.doOnError(WebClientResponseException.class, err -> {

LOGGER.info("ERROR status:{},msg:{}",err.getRawStatusCode(),err.getResponseBodyAsString());

throw new RuntimeException(err.getMessage());

})

.onErrorReturn("fallback");

String result = mono.block();

LOGGER.info("result:{}",result);

}

可以使用onStatus根据status code进行异常适配

可以使用doOnError异常适配

可以使用onErrorReturn返回默认值

小结

webclient是新一代的async rest template,api也相对简洁,而且是reactive的,非常值得使用。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持脚本之家。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值