Skip to content
[email protected] edited this page Oct 6, 2015 · 9 revisions

GREYS-PROTOCOL

介绍

GREYS-PROTOCOL(以下简称GP协议)定义了一套用于GREYS软件C/S模型的通讯协议,利用这套协议客户端和服务端能正常的完成交互,从达到操作GREYS的目的。

感谢

本协议在设计过程中得到了以下网友的支持

协议约定

  • ###请求报文标准结构###

    字段说明 字段长度
    协议版本 2 Byte
    请求序列 4 Byte
    请求类型 2 Byte
    长度 4 Byte
    数据 n Byte
  • ###应答报文标准结构###

    字段说明 字段长度
    请求序列 4 Byte
    应答序列 4 Byte
    返回码 4 Byte
    长度 4 Byte
    数据 n Byte
  • ###协议交互流程###

      +--------+                        +--------+
      | Client |                        | Server |
      +--------+                        +--------+ 
           |                                 |
           |                                 |
           + > > > > > > > > > > > > > > > > +
           |    [REQ.send_id=1]              |
           |    [REQ.exec_type='monitor']    |
           |                                 |
           |                                 |
           |                                 |
           + < < < < < < < < < < < < < < < < +
           |    [RSP.send_id=1]              |
           |    [RSP.resp_id=1]              |
           |    [RSP.resp_type=/CONTINUE/]   |
           |    [RSP.resp_data=/DATA/]       |
           |                                 |
           |                                 |
           |                                 |
           + > > > > > > > > > > > > > > > > +
           |    [REQ.send_id=2]              |
           |    [REQ.exec_type='version']    |
           |                                 |
           |                                 |
           |                                 |     
           + < < < < < < < < < < < < < < < < +
           |    [RSP.send_id=1]              |
           |    [RSP.resp_id=2]              |
           |    [RSP.resp_type=/CONTINUE/]   |
           |    [RSP.resp_data=/DATA/]       |
           |                                 |
           |                                 |
           |                                 |
           + < < < < < < < < < < < < < < < < +
           |    [RSP.send_id=1]              |
           |    [RSP.resp_id=3]              |
           |    [RSP.resp_type=/END/]        |
           |    [RSP.resp_data=/DATA/]       |
           |                                 |
           |                                 |
           |                                 |
           + < < < < < < < < < < < < < < < < +
           |    [RSP.send_id=2]              |
           |    [RSP.resp_id=4]              |
           |    [RSP.resp_type=/END/]        |
           |    [RSP.resp_data=/DATA/]       |
           |                                 |
           |                                 |
           |                                 |
           -                                 -
    
  • ###协议版本###

    GP协议要求能做到向下版本的兼容,表达当前请求的协议版本号。

  • ###关键字段解释###

    • 请求序列

      GP协议采用多路复用的方式来完成协议通讯,所以使用应答报文.请求序列==请求报文.请求序列来完成请求报文和应答报文的关联。

      GP协议对请求序列有以下的约定

      • 请求序列由请求端发起,服务端在应答该请求的时候必须将该对应请求的序列ID返回
      • 请求序列在协议中定义为INT(4B),允许溢出成负数
    • 应答序列

      GREYS命令中有很多异步命令,比如watch/tt/monitor,当客户端请求发出后,后续的数据推送将由服务端发送多个应答报文来完成。

      GP协议对应答序列有以下的约定

      • 应答序列由服务端发起
      • 应答序列在协议中定义为INT(4B),允许溢出成负数
    • 请求类型

      服务端根据不同的请求类型,从而决定执行操作和返回对应的响应报文。

  • ###请求类型###

    类型值 类型说明
    0x01 心跳
    0x02 获取服务端版本
    0x03 监控方法调用
    0x04 重置增强类
    0x05 搜索已加载类
    0x06 搜索已经加载类方法
  • ###返回码###

    标记应答协议的状态。

    返回码 成功 结束 码值说明
    0x00 Y Y 全部成功
    0x01 Y N 部分成功,有后续应答
    0x10 N Y 发生未知错误
    0x11 N Y 请求协议版本不支持
    0x12 N Y 请求类型不支持

协议内容

心跳

心跳协议主要用于维持服务端的会话链接,如果客户端没有在指定的时间发起心跳包,则服务端有权主动断开客户端当前链接,同时中止当前链接上所关联的所有任务。

  • 请求

    心跳请求无需数据内容

    {}
  • 应答

    心跳应答无需数据内容

    {}

获取服务端版本

返回当前服务端软件版本。

对应version命令

  • 请求

    版本请求无请求数据内容

    {}
  • 应答

    版本应答返回当前服务器版本

    {
        "version": "1.8.0.0"
    }

监控方法调用

对应monitor命令

  • 请求

    {
        "class-pattern":"com.taobao.*",
        "method-pattern":"query*",
        "cycle":"120",
        "is-regex":"false"
    }
  • 应答

    {
        "affect":
        {
            "class-count":"100",
            "method-count":"50"
        },
        "items":
        [
            {
                "timestamp":"1443108198994",
                "class":"org.apache.commons.lang3.StringUtils",
                "method":"isNotBlank",
                "total":"100",
                "success":"90",
                "fail":"10",
                "rt":"500",
                "fail-rate":"0.1"
            }
        ]
    }

重置增强类

对应reset命令

  • 请求

    {
        "class-pattern":"com.taobao.*",
        "is-regex":"false"
    }
  • 应答

    {
        "affect":
        {
            "row-count":"100"
        }
    }

搜索已加载类

对应sc命令

  • 请求

    {
        "class-pattern":"com.alibaba.AgentTest",
        "is-regex":"false",
        "is-display-fields":"true",
        "is-display-detail":"true"
    }
  • 应答

    {
        "items":
        [
            {
                "classname":"com.alibaba.AgentTest",
                "detail":
                {
                    "code-source":"/Users/vlinux/temp/agent-test/target/",
                    "is-interface":"false",
                    "is-annotation":"false",
                    "is-enum":"false",
                    "is-anonymous-class":"false",
                    "is-array":"false",
                    "is-local-class":"false",
                    "is-member-class":"false",
                    "is-primitive":"false",
                    "is-synthetic":"false",
                    "modifier":"1",
                    "annotations":
                    [
                        "com.github.ompc.greys.core.command.annotation.Cmd"
                    ],
                    "interfaces":
                    [
                        "com.github.ompc.greys.core.command.Command"
                    ],
                    "super-class":"java.lang.Object",
                    "class-loader":
                    [
                        "com.github.ompc.greys.agent.GreysClassLoader@7d64a7f2",
                        "sun.misc.Launcher$AppClassLoader@58644d46",
                        "sun.misc.Launcher$ExtClassLoader@7ea987ac"
                    ]
                },
                "fields":
                [
                    {
                        "modifier":"5",
                        "type":"java.lang.String",
                        "name":"DEFAULT_PROMPT",
                        "value":"ga?>"
                    },
                    {
                        "modifier":"5",
                        "type":"java.lang.String",
                        "name":"ABORT_MSG",
                        "value":"Press Ctrl+D to abort."
                    },
                    {
                        "modifier":"5",
                        "type":"java.lang.String",
                        "name":"SPY_CLASSNAME",
                        "value":"com.github.ompc.greys.agent.Spy"
                    }
                ]
            },
        ]
    }

搜索已经加载类方法

对应sm命令

  • 请求

    {
        "class-pattern":"com.github.ompc.greys.core.util.GaStringUtils",
        "method-pattern":"*",
        "is-regex":"false",
        "is-display-fields":"true",
        "is-display-detail":"true"
    }
  • 应答

    {
        "items":
        [
            {
                "classname":"com.github.ompc.greys.core.util.GaStringUtils",
                "methods":
                [
                    {
                        "method-name":"tranModifier",
                        "modifier":"5",
                        "annotation":[],
                        "exception":[],
                        "parameters":
                        [
                            "int"
                        ],
                        "return":"java.lang.String"
                    },
                    {
                        "method-name":"getLogo",
                        "modifier":"5",
                        "annotation":[],
                        "exception":
                        [
                            "java.io.IOException"
                        ],
                        "parameters":[],
                        "return":"java.lang.String"
                    }
                ]
            }
        ]
    }

会话状态

返回服务端所有会话状态

对应session命令

  • 请求

    {}
  • 应答

    {
        "pid":"79321",
        "items":
        [
            {
                "session-id":"1",
                "duration":"300000",
                "charset":"utf-8",
                "client-address":"127.0.0.1:64702",
                "server-address":"127.0.0.1:3658"
            }
        ]
    }

方法调用堆栈

返回指定方法调用堆栈

  • 请求

    {
        "class-pattern":"com.github.ompc.greys.core.util.GaStringUtils",
        "method-pattern":"*",
        "condition-express":"true",
        "is-regex":"false",
        "limit":"-1"
    }
  • 应答

    {
        "thread-name":"main",
        "thread-id":"0x1",
        "is-daemon":"false",
        "priority":"5",
        "items":
        [
            {
                "classname":"com.alibaba.AgentTest",
                "method-name":"print",
                "filename":"AgentTest.java",
                "line-number":"-1"
            },
            {
                "classname":"sun.reflect.NativeConstructorAccessorImpl",
                "method-name":"newInstance0",
                "filename":"NativeConstructorAccessorImpl.java",
                "line-number":"-2"
            },
            {
                "classname":"sun.reflect.NativeConstructorAccessorImpl",
                "method-name":"newInstance",
                "filename":"NativeConstructorAccessorImpl.java",
                "line-number":"62"
            },
            {
                "classname":"sun.reflect.DelegatingConstructorAccessorImpl",
                "method-name":"newInstance",
                "filename":"DelegatingConstructorAccessorImpl.java",
                "line-number":"45"
            },
            {
                "classname":"java.lang.reflect.Constructor",
                "method-name":"newInstance",
                "filename":"Constructor.java",
                "line-number":"408"
            },
            {
                "classname":"java.lang.Class",
                "method-name":"newInstance",
                "filename":"Class.java",
                "line-number":"438"
            },
            {
                "classname":"com.alibaba.AgentTest",
                "method-name":"main",
                "filename":"AgentTest.java",
                "line-number":"122"
            }
        ]
    }

命令调用记录:搜索调用记录

对应tt -ltt -s命令

  • 请求

    {
        "condition-express":"true"
    }
  • 应答

    {
        "items":
        [
            {
                "index":"1000",
                "timestamp":"2015-09-27 10:17:25",
                "cost":"1",
                "is-return":"true",
                "is-exception":"false",
                "object":"0x4b1210ee",
                "classname":"com.alibaba.AgentTest",
                "method-name":"print"
            },
            {
                "index":"1001",
                "timestamp":"2015-09-27 10:17:26",
                "cost":"2",
                "is-return":"true",
                "is-exception":"false",
                "object":"0x4b1210ee",
                "classname":"com.alibaba.AgentTest",
                "method-name":"print"
            }
        ]
    }

命令调用记录:调用记录详情

对应tt -i命令

  • 请求

    {
        "index":"1003",
        "expend":
        {
            "level":"1",
            "format":"json"
        }
    }
  • 应答

    {
        "index":"1003",
        "timestamp":"2015-09-27 22:22:56",
        "cost":"1",
        "object":"0x4b1210ee",
        "classname":"com.alibaba.AgentTest",
        "method-name":"printAddress",
        "is-return":"false",
        "is-exception":"true",
        "parameters":
        [
            '{"addressId":20808,"addressName":"ADDRESS","avg":2.0}',
            "null"
        ],
        "exception":'{"detailMessage":"test","stackTrace":[{"declaringClass":"com.alibaba.AgentTest","methodName":"printAddress","fileName":"AgentTest.java","lineNumber":86},{"declaringClass":"com.alibaba.AgentTest","methodName":"\u003cinit\u003e","fileName":"AgentTest.java","lineNumber":68},{"declaringClass":"sun.reflect.NativeConstructorAccessorImpl","methodName":"newInstance0","fileName":"NativeConstructorAccessorImpl.java","lineNumber":-2},{"declaringClass":"sun.reflect.NativeConstructorAccessorImpl","methodName":"newInstance","fileName":"NativeConstructorAccessorImpl.java","lineNumber":62},{"declaringClass":"sun.reflect.DelegatingConstructorAccessorImpl","methodName":"newInstance","fileName":"DelegatingConstructorAccessorImpl.java","lineNumber":45},{"declaringClass":"java.lang.reflect.Constructor","methodName":"newInstance","fileName":"Constructor.java","lineNumber":408},{"declaringClass":"java.lang.Class","methodName":"newInstance","fileName":"Class.java","lineNumber":438},{"declaringClass":"com.alibaba.AgentTest","methodName":"main","fileName":"AgentTest.java","lineNumber":122}],"suppressedExceptions":[]}'
    }