@Override
    protected Mono<ResponseEntity<Flux<DataBuffer>>> doRequest(final ServerWebExchange exchange, final String httpMethod,
                                             final URI uri, final Flux<DataBuffer> body) {
        // springWebflux5.3 mark #exchange() deprecated. because #echange maybe make memory leak.
        // https://github.com/spring-projects/spring-framework/issues/25751
        // exchange is deprecated, so change to {@link WebClient.RequestHeadersSpec#exchangeToMono(Function)}
        ServerHttpRequest request = exchange.getRequest();
        final HttpHeaders httpHeaders = new HttpHeaders(request.getHeaders());
        this.duplicateHeaders(exchange, httpHeaders, UniqueHeaderEnum.REQ_UNIQUE_HEADER);
        final WebClient.ResponseSpec responseSpec = webClient.method(HttpMethod.valueOf(httpMethod)).uri(uri)
                .headers(headers -> {
                    headers.addAll(exchange.getRequest().getHeaders());
                    headers.remove(HttpHeaders.HOST);
                    Boolean preserveHost = exchange.getAttributeOrDefault(Constants.PRESERVE_HOST, Boolean.FALSE);
                    if (preserveHost) {
                        headers.add(HttpHeaders.HOST, request.getHeaders().getFirst(HttpHeaders.HOST));
                    }
                })
                .body((outputMessage, context) -> {
                    MediaType mediaType = exchange.getRequest().getHeaders().getContentType();
                    if (MediaTypeUtils.isByteType(mediaType)) {
                        return outputMessage.writeWith(body);
                    }
                    // fix chinese garbled code
                    return outputMessage.writeWith(DataBufferUtils.join(body));
                })
                .retrieve()
                // cover DefaultResponseSpec#DEFAULT_STATUS_HANDLER
                .onRawStatus(httpStatus -> httpStatus >= 400, clientResponse -> Mono.empty());
        return responseSpec.toEntityFlux(DataBuffer.class)
                .flatMap(fluxResponseEntity -> {
                    if (fluxResponseEntity.getStatusCode().is2xxSuccessful()) {
                        exchange.getAttributes().put(Constants.CLIENT_RESPONSE_RESULT_TYPE, ResultEnum.SUCCESS.getName());
                    } else {
                        exchange.getAttributes().put(Constants.CLIENT_RESPONSE_RESULT_TYPE, ResultEnum.ERROR.getName());
                    }
                    HttpHeaders headers = new HttpHeaders();
                    headers.addAll(fluxResponseEntity.getHeaders());
                    this.duplicateHeaders(exchange, headers, UniqueHeaderEnum.RESP_UNIQUE_HEADER);
                    exchange.getResponse().getHeaders().putAll(headers);
                    exchange.getResponse().setStatusCode(fluxResponseEntity.getStatusCode());
                    exchange.getAttributes().put(Constants.CLIENT_RESPONSE_ATTR, fluxResponseEntity);
                    return Mono.just(fluxResponseEntity);
                });
    }
Instantiates a new Web client plugin.

@param webClient the web client
shenyu-plugin/shenyu-plugin-httpclient/src/main/java/org/apache/shenyu/plugin/httpclient/WebClientPlugin.java