在istio或spring webflux处理头“ Content-Encoding:deflate”中是否有任何内置过滤器来解压缩请求主体

时间:2019-06-05 00:01:55

标签: spring-webflux istio

我有一个在Spring Cloud功能webflux上运行的微服务,需要处理以http请求正文形式发送的压缩数据

是否有用于处理数据解压缩的spring web过滤器或内置配置

$ echo '{ "key":"hello" }' > body
$ curl -X POST -H "Content-Type: application/json" --data-binary @body http://localhost:8080 # prints 'hello'
$ echo '{ "key":"hello" }' | deflate > body.dat
$ curl -X POST -H "Content-Type: application/json" -H "Content-Encoding: deflate" --data-binary @body.dat http://localhost:8080 # fails

这可以在istio使节过滤器中处理吗?

1 个答案:

答案 0 :(得分:0)

    public class GzipFilter implements WebFilter {

private static final String ENCODING_VALUE = "deflate";

/**
 * Process the Web request and (optionally) delegate to the next
 * {@code WebFilter} through the given {@link WebFilterChain}.
 *
 * @param exchange the current server exchange
 * @param chain    provides a way to delegate to the next filter
 * @return {@code Mono<Void>} to indicate when request processing is complete
 */
@Override
public Mono<Void> filter(ServerWebExchange exchange, WebFilterChain chain) {
    List<String> strings = exchange.getRequest().getHeaders().get(HttpHeaders.CONTENT_ENCODING);
    if(strings != null && strings.contains(ENCODING_VALUE)){
        return chain.filter(new GzippedInputStreamWrapper(exchange));
    } else {
        return chain.filter(exchange);
    }
}

}

public final class GzippedInputStreamWrapper extends ServerWebExchangeDecorator {


private final ServerHttpRequestDecorator requestDecorator;


protected GzippedInputStreamWrapper(ServerWebExchange delegate) {
    super(delegate);
    this.requestDecorator = new GzipRequestDecorator(delegate.getRequest());
}

@Override
public ServerHttpRequest getRequest() {
    return this.requestDecorator;
}

}

public class GzipRequestDecorator extends ServerHttpRequestDecorator {

private final DataBufferFactory dataBufferFactory = new DefaultDataBufferFactory();

public GzipRequestDecorator(ServerHttpRequest delegate) {
    super(delegate);
}


@Override
public Flux<DataBuffer> getBody() {
    log.info("get body of the payload");
    return super.getBody().flatMap(dataBuffer -> {
        try {
            final InputStream gzipInputStream = new InflaterInputStream(dataBuffer.asInputStream());
            return DataBufferUtils.readInputStream(() -> gzipInputStream, this.dataBufferFactory, gzipInputStream.available());
        } catch (Exception e) {
            log.error("Error is {}", e.getMessage());
            return Flux.error(e);
        }

    });
}

}

定义webfilter GzipFilter,它拦截指定标头的每个请求和处理。 GzipRequestDecorator进行主体转换,以扩大内容并将其发送给下游处理程序函数