SpringCloud升级之路2020.0.x版-15.UnderTow 订制 (3)

HttpRequestJFREvent.java

package com.github.hashjang.spring.cloud.iiford.spring.cloud.webmvc.undertow.jfr; import io.undertow.servlet.spec.HttpServletRequestImpl; import io.undertow.servlet.spec.HttpServletResponseImpl; import jdk.jfr.Category; import jdk.jfr.Event; import jdk.jfr.Label; import jdk.jfr.StackTrace; import javax.servlet.ServletRequest; import javax.servlet.ServletResponse; import java.util.Enumeration; @Category({"Http Request"}) @Label("Http Request") @StackTrace(false) public class HttpRequestJFREvent extends Event { //请求的 http 方法 private final String method; //请求的路径 private final String path; //请求的查询参数 private final String query; //请求的 traceId,来自于 sleuth private String traceId; //请求的 spanId,来自于 sleuth private String spanId; //发生的异常 private String exception; //http 响应码 private int responseStatus; public HttpRequestJFREvent(ServletRequest servletRequest, String traceId, String spanId) { HttpServletRequestImpl httpServletRequest = (HttpServletRequestImpl) servletRequest; this.method = httpServletRequest.getMethod(); this.path = httpServletRequest.getRequestURI(); this.query = httpServletRequest.getQueryParameters().toString(); Enumeration<String> headerNames = httpServletRequest.getHeaderNames(); StringBuilder stringBuilder = new StringBuilder(); headerNames.asIterator().forEachRemaining(s -> stringBuilder.append(s).append(":").append(httpServletRequest.getHeader(s)).append("\n")); this.traceId = traceId; this.spanId = spanId; } public void setResponseStatus(ServletResponse servletResponse, Throwable throwable) { this.responseStatus = ((HttpServletResponseImpl) servletResponse).getStatus(); this.exception = throwable != null ? throwable.toString() : null; } }

然后,我们仿照文中前面关闭的 WebMvcMetricsAutoConfiguration 中的 WebMvcMetricsFilter 编写我们自己的 Filter 并仿照注册,这里我们只展示核心代码:

JFRTracingFilter.java

@Override public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException { HttpRequestJFREvent httpRequestJFREvent = null; try { //从 sleuth 中获取 traceId 和 spanId TraceContext context = tracer.currentSpan().context(); String traceId = context.traceId(); String spanId = context.spanId(); //收到请求就创建 HttpRequestReceivedJFREvent 并直接提交 HttpRequestReceivedJFREvent httpRequestReceivedJFREvent = new HttpRequestReceivedJFREvent(servletRequest, traceId, spanId); httpRequestReceivedJFREvent.commit(); httpRequestJFREvent = new HttpRequestJFREvent(servletRequest, traceId, spanId); httpRequestJFREvent.begin(); } catch (Exception e) { log.error("JFRTracingFilter-doFilter failed: {}", e.getMessage(), e); } Throwable throwable = null; try { filterChain.doFilter(servletRequest, servletResponse); } catch (IOException | ServletException t) { throwable = t; throw t; } finally { try { //无论如何,都会提交 httpRequestJFREvent if (httpRequestJFREvent != null) { httpRequestJFREvent.setResponseStatus(servletResponse, throwable); httpRequestJFREvent.commit(); } } catch (Exception e) { log.error("JFRTracingFilter-doFilter final failed: {}", e.getMessage(), e); } } }

SpringCloud升级之路2020.0.x版-15.UnderTow 订制

我们这一节针对 Undertow 进行了两个定制:分别是需要在 accesslog 中打开响应时间统计以及通过 JFR 监控每个 Http 请求,同时占用空间不能太大。下一节,我们将开始介绍我们微服务的注册中心 Eureka 的使用以及细节配置。

微信搜索“我的编程喵”关注公众号,每日一刷,轻松提升技术,斩获各种offer

SpringCloud升级之路2020.0.x版-15.UnderTow 订制

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/zzjwjw.html