本文共 10733 字,大约阅读时间需要 35 分钟。
如题,也许有人觉得做这个有点多此一举,但是个人感觉这个的必要性还是有的。不为别的就为了省那么几秒中的查找时间。总体对微服务开发调试上就会有一些微小的提升那也是方便开发小伙伴的一种优化,好的框架就是这么一点一滴的优化过来的。废话不多说,先谈谈总体思路最后给个实现。
1、首先要对头部进行操作我们可以在拦截器或者过滤器中动手脚 2、需要获取到skywalking的服务地址以及traceId 思路就是这两步看着就很简单show your code
maven依赖,包头请随意omsa-all com.qimo 0.0.1-SNAPSHOT 4.0.0 com.qimo.trace omsa-trace jar org.apache.skywalking apm-toolkit-trace 8.2.0 org.apache.skywalking apm-toolkit-logback-1.x 8.2.0 org.springframework spring-webmvc 5.1.5.RELEASE provided javax.servlet javax.servlet-api 3.0.1 provided org.springframework.boot spring-boot 2.1.3.RELEASE org.springframework.boot spring-boot-configuration-processor 2.1.3.RELEASE true
定义属性oap_ui的地址skywalkingUrl
package com.qimo.trace;import org.springframework.boot.context.properties.ConfigurationProperties;/** * @Description TODO * @Author 姚仲杰#80998699 * @Date 2021/6/20 23:51 */@ConfigurationProperties(prefix = "omsa.trace")public class OmsaTraceProperties { private String skywalkingUrl="http://"; public String getSkywalkingUrl() { return skywalkingUrl; } public void setSkywalkingUrl(String skywalkingUrl) { this.skywalkingUrl = skywalkingUrl; }}
定义拦截器往头部塞traceId和skywalkingUrl拼接的地址最后效果是这样http://127.0.0.1:10800/trace?traceId=0a0cb455e8bf44718a70589e5818d5f9.66.16242401437190001
package com.qimo.trace;import com.qimo.trace.configuration.OmsaTraceConst;import javax.servlet.http.HttpServletRequest;import javax.servlet.http.HttpServletResponse;import org.apache.skywalking.apm.toolkit.trace.TraceContext;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.util.StringUtils;import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;/** * @Description TODO * @Author 姚仲杰#80998699 * @Date 2021/6/20 23:36 */public class OmsaTraceHeaderInterceptor extends HandlerInterceptorAdapter { @Autowired OmsaTraceProperties omsaTraceProperties; public OmsaTraceHeaderInterceptor() { super(); } @Override public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { String traceId=TraceContext.traceId(); if (StringUtils.isEmpty(traceId)){ traceId=OmsaTraceConst.NULL_TRACE_ID; } response.setHeader(OmsaTraceConst.OMSA_TRACE_VISIT_URL_KEY, omsaTraceProperties.getSkywalkingUrl().replace("@{traceId}",traceId)); return true; } }
以上代码已经将功能完整写完了,剩下就是bean的加载了
我们这里使用一个@Enable*加载这个包的功能 1、声明注解package com.qimo.trace.annotation;import com.qimo.trace.OmsaTraceProperties;import com.qimo.trace.configuration.OmsaTraceConfigurationImportSelector;import java.lang.annotation.Documented;import java.lang.annotation.ElementType;import java.lang.annotation.Retention;import java.lang.annotation.RetentionPolicy;import java.lang.annotation.Target;import org.springframework.boot.context.properties.EnableConfigurationProperties;import org.springframework.context.annotation.Import;/** * @Description TODO * @Author 姚仲杰#80998699 * @Date 2021/6/21 0:20 */@Target(ElementType.TYPE)@Retention(RetentionPolicy.RUNTIME)@Documentedpublic @interface EnableOmsaTrace { String[] includePatterns() default { "/**/**"}; String[] excludePatterns() default { "/**/*.js", "/**/*.css", "/**/*.html"}; }
2、编写registrar配置bean
package com.qimo.trace.configuration;import com.qimo.trace.annotation.EnableOmsaTrace;import org.springframework.beans.factory.config.RuntimeBeanReference;import org.springframework.beans.factory.support.BeanDefinitionReaderUtils;import org.springframework.beans.factory.support.BeanDefinitionRegistry;import org.springframework.beans.factory.support.GenericBeanDefinition;import org.springframework.context.annotation.ImportBeanDefinitionRegistrar;import org.springframework.core.annotation.AnnotationAttributes;import org.springframework.core.type.AnnotationMetadata;import org.springframework.web.servlet.handler.MappedInterceptor;/** * @Description TODO * @Author 姚仲杰#80998699 * @Date 2021/6/21 0:23 */public class OmsaTraceBeanRegistrar implements ImportBeanDefinitionRegistrar { public void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry) { String[] includePatterns = getAnnotationAttributesValue(importingClassMetadata, "includePatterns"); String[] excludePatterns = getAnnotationAttributesValue(importingClassMetadata, "excludePatterns"); GenericBeanDefinition beanDefinition = new GenericBeanDefinition(); beanDefinition.setBeanClass(MappedInterceptor.class); beanDefinition.getConstructorArgumentValues().addIndexedArgumentValue(0, includePatterns); beanDefinition.getConstructorArgumentValues().addIndexedArgumentValue(1, excludePatterns); beanDefinition.getConstructorArgumentValues().addIndexedArgumentValue(2, new RuntimeBeanReference( OmsaTraceConst.OMSA_TRACE_HEADER_INTERCEPTOR_BEAN_NAME)); BeanDefinitionReaderUtils.registerWithGeneratedName(beanDefinition, registry); } private String[] getAnnotationAttributesValue(AnnotationMetadata metadata, String attribute) { AnnotationAttributes attributes = AnnotationAttributes.fromMap( metadata.getAnnotationAttributes(EnableOmsaTrace.class.getName())); String[] basePackages = attributes.getStringArray(attribute); return basePackages; }}
3、编写Configuration配置bean
package com.qimo.trace.configuration;import com.qimo.trace.OmsaTraceHeaderInterceptor;import org.springframework.context.annotation.Bean;/** * @Description TODO * @Author 姚仲杰#80998699 * @Date 2021/6/20 23:57 */public class OmsaTraceConfiguration { @Bean(OmsaTraceConst.OMSA_TRACE_HEADER_INTERCEPTOR_BEAN_NAME) public OmsaTraceHeaderInterceptor omsaTraceHeaderInterceptor(){ return new OmsaTraceHeaderInterceptor(); }}
4、编写selectort收集需要加载的bean
package com.qimo.trace.configuration;import java.util.ArrayList;import java.util.List;import org.springframework.context.annotation.ImportSelector;import org.springframework.core.type.AnnotationMetadata;/** * @Description TODO * @Author 姚仲杰#80998699 * @Date 2021/6/21 0:22 */public class OmsaTraceConfigurationImportSelector implements ImportSelector { public String[] selectImports(AnnotationMetadata annotationMetadata) { ListimportList=new ArrayList (); importList.add(OmsaTraceConfiguration.class.getName()); importList.add(OmsaTraceBeanRegistrar.class.getName()); return importList.toArray(new String[importList.size()]); }}
修改注解导入selector和properties
package com.qimo.trace.annotation;import com.qimo.trace.OmsaTraceProperties;import com.qimo.trace.configuration.OmsaTraceConfigurationImportSelector;import java.lang.annotation.Documented;import java.lang.annotation.ElementType;import java.lang.annotation.Retention;import java.lang.annotation.RetentionPolicy;import java.lang.annotation.Target;import org.springframework.boot.context.properties.EnableConfigurationProperties;import org.springframework.context.annotation.Import;/** * @Description TODO * @Author 姚仲杰#80998699 * @Date 2021/6/21 0:20 */@Target(ElementType.TYPE)@Retention(RetentionPolicy.RUNTIME)@EnableConfigurationProperties(OmsaTraceProperties.class)@Import(OmsaTraceConfigurationImportSelector.class)@Documentedpublic @interface EnableOmsaTrace { String[] includePatterns() default { "/**/**"}; String[] excludePatterns() default { "/**/*.js", "/**/*.css", "/**/*.html"}; }
打包发布,然后建个相关demo项目,当然同时你还得具备skywalking服务端和agent,很简单直接从dockerhub拉取一个,以上包用的版本是8.2.0那我直接拉取一个8.2.0的服务端,直接使用docker-compose吧。
version: "3.1"services: oap: image: apache/skywalking-oap-server:8.2.0-es7 restart: always ports: - 11800:11800 - 12800:12800 oap_ui: image: apache/skywalking-ui:8.2.0 restart: always environment: SW_OAP_ADDRESS: "oap:12800" ports: - 10800:8080
再起个springboot-demo项目引入当前包,在启动类上注解个@EnableOmsaTrace 试试看
@SpringBootApplication@EnableOmsaTracepublic class OmsaDemoApplication { public static void main(String[] args) { SpringApplication.run(OmsaDemoApplication.class,args); }
当然还需要配置logback因为我们这里只做了logback,你如果要用其它日志框架需要将最上面的依赖包换层相关的框架依赖
logback-spring配置如下:随便摘抄了一份。${log_pattern} ${log_pattern} log/%d{yyyy-MM-dd}.%i.log 100MB
写个简单controller
package com.qimo.omsa.demo.trace;import org.apache.skywalking.apm.toolkit.trace.TraceContext;import org.slf4j.Logger;import org.slf4j.LoggerFactory;import org.springframework.web.bind.annotation.GetMapping;import org.springframework.web.bind.annotation.RestController;/** * @Description TODO * @Author 姚仲杰#80998699 * @Date 2021/6/21 1:18 */@RestControllerpublic class TraceTestController { Logger log= LoggerFactory.getLogger(TraceTestController.class); @GetMapping("/trace") public String trace(){ log.info(TraceContext.traceId()); return TraceContext.traceId(); }}
application.properties中配置上你的skywalking地址
server.port=7777logging.level.root=infoomsa.trace.skywalking-url=http://127.0.0.1:10800/trace?traceId=@{ traceId}
访问效果如下
复制链接直接访问转载地址:http://yxkfb.baihongyu.com/