|
|
@@ -0,0 +1,79 @@
|
|
|
+package cn.reghao.tnb.data.app.filter;
|
|
|
+
|
|
|
+import io.netty.buffer.ByteBufAllocator;
|
|
|
+import org.springframework.core.Ordered;
|
|
|
+import org.springframework.core.io.buffer.DataBuffer;
|
|
|
+import org.springframework.core.io.buffer.DataBufferUtils;
|
|
|
+import org.springframework.core.io.buffer.NettyDataBufferFactory;
|
|
|
+import org.springframework.http.server.reactive.ServerHttpRequest;
|
|
|
+import org.springframework.http.server.reactive.ServerHttpRequestDecorator;
|
|
|
+import org.springframework.web.server.ServerWebExchange;
|
|
|
+import org.springframework.web.server.WebFilter;
|
|
|
+import org.springframework.web.server.WebFilterChain;
|
|
|
+import reactor.core.publisher.Flux;
|
|
|
+import reactor.core.publisher.Mono;
|
|
|
+
|
|
|
+import java.net.URI;
|
|
|
+import java.nio.CharBuffer;
|
|
|
+import java.nio.charset.StandardCharsets;
|
|
|
+import java.util.concurrent.atomic.AtomicReference;
|
|
|
+
|
|
|
+/**
|
|
|
+ * @author reghao
|
|
|
+ * @date 2025-07-18 15:26:51
|
|
|
+ */
|
|
|
+public class GetRequestBodyFilter implements WebFilter, Ordered {
|
|
|
+ public Mono<Void> filter(ServerWebExchange exchange, WebFilterChain chain) {
|
|
|
+ ServerHttpRequest serverHttpRequest = exchange.getRequest();
|
|
|
+ String method = serverHttpRequest.getMethodValue();
|
|
|
+ //从请求里获取Post请求体
|
|
|
+ String bodyStr = resolveBodyFromRequest(serverHttpRequest);
|
|
|
+
|
|
|
+ //下面的将请求体再次封装写回到request里,传到下一级,否则,由于请求体已被消费,后续的服务将取不到值
|
|
|
+ URI uri = serverHttpRequest.getURI();
|
|
|
+ ServerHttpRequest request = serverHttpRequest.mutate().uri(uri).build();
|
|
|
+ DataBuffer bodyDataBuffer = stringBuffer(bodyStr);
|
|
|
+ Flux<DataBuffer> bodyFlux = Flux.just(bodyDataBuffer);
|
|
|
+
|
|
|
+ request = new ServerHttpRequestDecorator(request) {
|
|
|
+ public Flux<DataBuffer> getBody() {
|
|
|
+ return bodyFlux;
|
|
|
+ }
|
|
|
+ };
|
|
|
+ ServerWebExchange newExchange = exchange.mutate().request(request).build();
|
|
|
+ newExchange.getAttributes().put("bodyCache",bodyStr);
|
|
|
+ //封装request,传给下一级
|
|
|
+ return chain.filter(newExchange);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 从Flux<DataBuffer>中获取字符串的方法
|
|
|
+ *
|
|
|
+ * @return 请求体
|
|
|
+ */
|
|
|
+ private String resolveBodyFromRequest(ServerHttpRequest serverHttpRequest) {
|
|
|
+ //获取请求体
|
|
|
+ Flux<DataBuffer> body = serverHttpRequest.getBody();
|
|
|
+
|
|
|
+ AtomicReference<String> bodyRef = new AtomicReference<>();
|
|
|
+ body.subscribe(buffer -> {
|
|
|
+ CharBuffer charBuffer = StandardCharsets.UTF_8.decode(buffer.asByteBuffer());
|
|
|
+ DataBufferUtils.release(buffer);
|
|
|
+ bodyRef.set(charBuffer.toString());
|
|
|
+ });
|
|
|
+ //获取request body
|
|
|
+ return bodyRef.get();
|
|
|
+ }
|
|
|
+
|
|
|
+ private DataBuffer stringBuffer(String value) {
|
|
|
+ byte[] bytes = value.getBytes(StandardCharsets.UTF_8);
|
|
|
+ NettyDataBufferFactory nettyDataBufferFactory = new NettyDataBufferFactory(ByteBufAllocator.DEFAULT);
|
|
|
+ DataBuffer buffer = nettyDataBufferFactory.allocateBuffer(bytes.length);
|
|
|
+ buffer.write(bytes);
|
|
|
+ return buffer;
|
|
|
+ }
|
|
|
+
|
|
|
+ public int getOrder() {
|
|
|
+ return 0;
|
|
|
+ }
|
|
|
+}
|