写点什么

关于 takin-data,你想知道的都在这里(二)trace 日志篇

用户头像
数列科技
关注
发布于: 4 小时前

相信大家在使用 takin 的过程中都见到过压测过程中实时展示的请求流量明细和请求详情了吧,像这样:



还有这样:



这样的请求流量明细和调用链详情是怎么实现的呢,今天就带大家探究下。


在前面的启动命令篇(https://news.shulie.io/?p=3450),我们简单介绍了 surge-deploy 的启动命令,里面关于 IP 映射的章节相信大家都还有印象,我们会读取 IP 映射信息将我们的日志接收服务注册到 zk 上,供我们的 linkAgent 读取,并发送日志到上面。发送的是什么日志呢,就是我们今天要说的 trace 日志。


先来看一下日志的文件路径,在我们的应用接入 linkAgent 并成功启动后,在我们的/apps/logs_pradar(默认日志输出目录,可以通过 agent.properties 中 simulator.log.path 配置进行调整)目录下面将会看到以下内容:



这里面的 tank_demo 和 tank-gateway-demo 就是我们接入到 linkAgent 的应用,打开 tank-gateway-demo:



我们能看到以下几个日志文件,不知道大家有没有查看过里面的内容呢,其实我们的 trace 日志就保存在 pradar_trace.log.0 这个文件里。


说到这,需要给大家解释下 trace 日志的含义:我们的 LinkAgent 采用的是字节码增强的技术,当请求流经各个应用时,将会记录应用代码中的真实的调用关系,包含请求的上下游应用名称,接口名称,服务名称等等信息,其中最重要的就是一个全局的 traceId,这个 traceId 在请求第一次到达时生成,随后不断传递,一直到请求完成的最下游应用,即调用链的底部,这样生成的数据就是我们的 trace 日志。


接下来,我们来看下 pradar_trace.log.0 文件里面的内容,我们选取 demo 应用中的 user-center 应用:



相信大家初看这个文件,肯定不知从何看起,这里就要给大家介绍下我们的日志格式了:


traceId|startTime|agentId|invokeId|invokeType|appName|cost|middlewareName|serviceName|methodName|resultCode|request|response|flags|callbackMsg|#samplingInterval|@attributes|@localAttributes


日志的每个字段之间用竖线|进行分割,每一行日志则是用换行符(\r\n)进行分割。有了这个,相信大家再入手肯定不难了。我们以图片中最后一条为例,给大家解读下:



用一句通俗的话说,这条 trace 日志的含义就是,部署在 127.0.0.1 上,进程号为 33212 的 easy-demo-usercenter-1.0.0 应用在 1628712100533 这个时间收到了一条/user-center/user/shadow_data#POST 的请求,应用的容器为 tomcat,请求参数为空,响应码为 200,没有返回具体的响应信息。哈哈,这样一来大家是不是好理解了!


但是还有一些同学肯定更好学,想知道各个字段在不同中间件下的含义,没关系,这个我们也有!!!


下面就是关于我们的 trace 日志的各个字段解释:


traceId:关联一次请求相关的日志,全局唯一,在各个系统间传递,组成:IP 地址(8 位):ip 地址 16 进制压缩创建时间(13):在存储时用于分区顺序数(4):用于链路采样标志位(1):可选,用于调试和标记进程号(4):可选,单机多进程的应用使用


startTime:方法调用开始时间


agentId:一般为 ip+进程号


invokeId:标识日志埋点顺序和嵌套关系,也在各个系统间传递顺序编号:1、2、3…多级编号:0、0.1、0.2、0.2.1…


invokeType:web 的 server 端 TYPE_WEB_SERVER = 0 远程调用 TYPE_RPC = 1MQ 调用 TYPE_MQ = 3 数据库调用 TYPE_DB = 4 缓存调用 TYPE_CACHE = 5 搜索调用 TYPE_SEARCH = 6job 类型调用 TYPE_JOB = 7 文件系统调用 TYPE_FS = 8 本地方法调用 TYPE_LOCAL = 9 未知调用 TYPE_UNKNOW = -1


appName:应用名称


cost:方法耗时(ms)


middlewareName:中间件名称


serviceName:web 的 server 端:url, 不带参数,不带协议、域名和端口远程调用:类名 MQ 调用:topic/ueueq 数据库调用:库名缓存调用:库名搜索调用:索引名 job 类型调用:jobClassName / job 名称文件系统调用:服务地址本地方法调用:类名


methodName:web 的 server 端:http method,统一大写远程调用:方法名(参数列表)、如 test(String,int)、test()MQ 调用:group/group|tags/routingKey 数据库调用:表名缓存调用:方法 如 add/pop/spop/delete 等等搜索调用:操作的方法名 job 类型调用:jobType 文件系统调用:文件路径本地方法调用:方法名(参数列表)、如 test(String,int)、test()


resultCode:00(成功)/01(失败)/02(业务错误)/03(超时)/04(未知)/05(断言失败)


request:web 的 server 端:请求体内容缓存调用:key


response:web 的 server 端:响应体内容


flags:位标签,用~分割(第一位标记压测标、第二位标记 debug 流量、第 3 位标记是否是 trace 入口、第 4 位标记是否是 server、第 5 位标记是否是流量引擎日志)例:true~false~false~true~false


callbackMsg:web 的 server 端:响应码数据库调用:sql 缓存调用:redis 客户端名称(例:redis-redisson)


#samplingInterval:采样率例:#1


@attributes:包括 traceAppName(入口应用名称)、traceServiceName(入口服务名)、traceMethod(入口方法名称)、taskId(压测报告 ID)例:@easydemo~/get~POST~14


@localAttributes:包括 upAppName(上游应用名称)、remoteIp(主机 ip)、remotePort(主机端口)、requestSize(请求大小)、responseSize(响应大小)例:@easydemo~127.17.0.1~3306~0~0 那知道了 trace 日志的含义和组成后,我们回到开始的问题:请求详情和调用链是怎么实现的?相信有不少小伙伴也已经猜到了:linkAgent 会将我们的 trace 日志推送给 surge-deploy,由我们的大数据写入到 clickhouse 中,最后再从 clickhouse 中查询得到这些信息!


下面,再附上 clickhouse 的连接命令,小伙伴们也可以直接查询 clickhouse 来查询自己的请求数据:


  • 登录容器


docker exec -it ${containerid} bash


  • 登录 clikhouse


clickhouse-client -h 0.0.0.0 --password='rU4zGjA/'


  • 查询 t_trace_all 表


select * from t_trace_all limit 10;t_trace_all 的表结构,小伙伴们也可以看一下:



想要了解更多开源产品信息,扫码小树入群交流!



发布于: 4 小时前阅读数: 2
用户头像

数列科技

关注

还未添加个人签名 2020.03.03 加入

还未添加个人简介

评论

发布
暂无评论
关于takin-data,你想知道的都在这里(二)trace日志篇