gatway filter post修改参数
package com.feifan.aida.gateway.filter; import cn.hutool.json.JSONObject; import com.alibaba.fastjson.JSON; import com.feifan.aida.gateway.common.AidaConstant; import com.feifan.aida.gateway.common.RandomUtils; import io.netty.buffer.ByteBufAllocator; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang.StringUtils; import org.springframework.cloud.gateway.filter.GatewayFilterChain; import org.springframework.cloud.gateway.filter.GlobalFilter; 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.HttpHeaders; import org.springframework.http.server.reactive.ServerHttpRequest; import org.springframework.http.server.reactive.ServerHttpRequestDecorator; import org.springframework.stereotype.Component; import org.springframework.web.server.ServerWebExchange; import org.springframework.web.util.UriComponentsBuilder; import reactor.core.publisher.Flux; import reactor.core.publisher.Mono; import redis.clients.jedis.JedisCluster; import java.io.UnsupportedEncodingException; import java.net.URI; import java.nio.charset.StandardCharsets; /*** * * * 获取请求参数RequestBody * * */ @Slf4j //@Component public class HttpRequestFilter implements GlobalFilter, Ordered { private JedisCluster jedisCluster; @Override public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) { ServerHttpRequest request = exchange.getRequest(); String contentType = request.getHeaders().getFirst("Content-Type"); return DataBufferUtils.join(exchange.getRequest().getBody()) .flatMap(dataBuffer -> { byte[] bytes = new byte[dataBuffer.readableByteCount()]; dataBuffer.read(bytes);
//释放堆外内存 不然会有内存泄漏
DataBufferUtils.release(dataBuffer); try { String bodyString = new String(bytes, "utf-8"); //修改测试 com.alibaba.fastjson.JSONObject jsonObject = JSON.parseObject(bodyString); com.alibaba.fastjson.JSONObject user = jsonObject.getJSONObject("user"); Long wid = user.getLong("wid"); user.put("group","B"); bodyString = com.alibaba.fastjson.JSONObject.toJSONString(jsonObject); URI uri = request.getURI(); URI newUri = UriComponentsBuilder.fromUri(uri).build(true).toUri(); log.info(newUri.getPath()); ServerHttpRequest serverHttpRequest = exchange.getRequest().mutate().uri(newUri).build(); DataBuffer bodyDataBuffer = stringBuffer(bodyString); Flux<DataBuffer> bodyFlux = Flux.just(bodyDataBuffer); // 定义新的消息头 HttpHeaders headers = new HttpHeaders(); headers.putAll(exchange.getRequest().getHeaders()); // 由于修改了传递参数,需要重新设置CONTENT_LENGTH,长度是字节长度,不是字符串长度 int length = bodyString.getBytes().length; headers.remove(HttpHeaders.CONTENT_LENGTH); headers.setContentLength(length); // 设置CONTENT_TYPE if (StringUtils.isNotBlank(contentType)) { headers.set(HttpHeaders.CONTENT_TYPE, contentType); } serverHttpRequest = new ServerHttpRequestDecorator(serverHttpRequest) { @Override public HttpHeaders getHeaders() { long contentLength = headers.getContentLength(); HttpHeaders httpHeaders = new HttpHeaders(); httpHeaders.putAll(super.getHeaders()); if (contentLength > 0) { httpHeaders.setContentLength(contentLength); } else { httpHeaders.set(HttpHeaders.TRANSFER_ENCODING, "chunked"); } return httpHeaders; } @Override public Flux<DataBuffer> getBody() { return bodyFlux; } }; //封装request,传给下一级 serverHttpRequest.mutate().header(HttpHeaders.CONTENT_LENGTH, Integer.toString(bodyString.length())); return chain.filter(exchange.mutate().request(serverHttpRequest).build()); //exchange.getAttributes().put("POST_BODY", bodyString); } catch (UnsupportedEncodingException e) { e.printStackTrace(); } DataBufferUtils.release(dataBuffer); Flux<DataBuffer> cachedFlux = Flux.defer(() -> { DataBuffer buffer = exchange.getResponse().bufferFactory() .wrap(bytes); return Mono.just(buffer); }); ServerHttpRequest mutatedRequest = new ServerHttpRequestDecorator( exchange.getRequest()) { @Override public Flux<DataBuffer> getBody() { return cachedFlux; } }; return chain.filter(exchange.mutate().request(mutatedRequest) .build()); }); } @Override public int getOrder() { return 0; } /** * 是否存在 * @param wid * @param userJSONObject */ private void existsAB(String wid, JSONObject userJSONObject){ String userGroup = jedisCluster.get(AidaConstant.AB_REDIS_USER_GROUP+"_"+wid); //判断 if(StringUtils.equals(userGroup,AidaConstant.A_REDIS_USER_GROUP)){ userJSONObject.put("group","A"); }else if(StringUtils.equals(userGroup,AidaConstant.B_REDIS_USER_GROUP)){ userJSONObject.put("group","B"); } } private void isNotExistsAB(String wid, JSONObject userJSONObject){ if(RandomUtils.nextBoolean()){ //随机分配A组人群 jedisCluster.incr(AidaConstant.A_REDIS_USER_GROUP); jedisCluster.set(AidaConstant.AB_REDIS_USER_GROUP+"_"+wid,AidaConstant.A_REDIS_USER_GROUP); userJSONObject.put("group","A"); }else{ //随机分配B组人群 jedisCluster.incr(AidaConstant.B_REDIS_USER_GROUP); jedisCluster.set(AidaConstant.AB_REDIS_USER_GROUP+"_"+wid,AidaConstant.B_REDIS_USER_GROUP); userJSONObject.put("group","B"); } } 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; } }