服务工具平台原创
金蝶云社区-lzpeng723
lzpeng723
5人赞赏了该文章 1425次浏览 未经作者许可,禁止转载编辑于2023年07月13日 08:02:07

常见问题

  • 业务出错,怀疑上游接口问题,但是线上又没有打印接口返回数据

  • 业务出错,怀疑代码业务逻辑有问题,需要代码逻辑环节输出相应参数定位

  • 线上有业务数据异常,需要直接数据库操作修复

  • 上游接口偶尔异常,但是由于没有日志,没有证据

  • 需要对上游接口做各种场景测试

  • 想要执行线上某段业务代码逻辑

解决办法

对于只能在线上环境(生产环境)定位的问题:

  • 新增相应的info日志,然后打包、上线,查看日志。

  • 新增调试代码逻辑,然后打包、上线,再次调用得到需要的结果。

可以在预发环境(测试环境)重现或者定位的问题:

  • 新增相应debug日志,然后打包,发布到测试环境,查看日志。

  • 新增对应代码逻辑,然后打包、发布到测试环境,再次调用得到需要的结果。

无论怎么处理,最终都需要重新打包、发布,甚至是上线。整个过程不复杂,但是很繁琐。那么有没有一种方法可以不打包,不上线,不发布,不重启就能够在线上直接执行某段代码,或者打印相应的日志呢?

原理介绍—类加载查看

获取类所在位置:

使用类加载器的 getResource()方法。 使用类的getProtectionDomain().getCodeSource(). getLocation()方法。

找到类所在位置后进行反编译:

使用FernFlower反编译。 使用jd-core 反编译。

原理介绍—代码执行器

原理介绍—代码执行器(Java)

  • 先在 IDE 中编写 Java 源码,源码中可以引用任意线上 JVM 里已经加载的类。

  • 通过 JavaCompiler 对源码进行编译,并将当前线程上下文类加载器设置为编译时的父类加载器

  • 编译完成后会得到一个自定义类加载器,从其中得到 Class 类,并实例化。

  • 通过反射调用实例的方法。

  • 将运行结果返回给前端和苍穹系统

原理介绍—代码执行器(js)

  • 先编写 js 脚本(Rhino, Nashorn,KScript),脚本中可以引用任意线上已部署的类。

  • 将 java 对象注入到脚本中。

  • 调用 js 引擎执行脚本。

  • 将运行结果返回给前端和苍穹系统。

具体实现

服务工具平台-类加载查看

服务工具平台-代码执行器

使用的苍穹特性

微服务开发与调用

大任务异步处理

应用迁移

源码地址

https://www.github.com/lzpeng723/servicetools

应用使用到开源 jar 包对应的 maven 仓库:

https://mvnrepository.com/artifact/cn.hutool/hutool-all/5.8.20

https://mvnrepository.com/artifact/org.jd/jd-core/1.1.3

https://mvnrepository.com/artifact/com.github.adedayo.intellij.sdk/java-decompiler-engine/142.1

导入应用

从 MC 或 开发平台导入 sys_lzp_servicetools.zip

将 jar 包部署到服务器对应位置:

sys_lzp_servicetools.zip\jar\common.zip(第三方开源 jar 包) sys_lzp_servicetools.zip\jar\servicetools.zip (苍穹插件)

若 sql 未执行成功可自行执行一下 sql :

sys_lzp_servicetools.zip\dm\sys-lzp_service_helper-dm.zip\datamodel\1.5.0\main\lzp_service_helper\preinsdata\servicetools.sql(本应用初始化数据------扩展开发库下执行)

sys_lzp_servicetools.zip\dm\sys-lzp_service_helper-dm.zip\datamodel\1.5.0\main\lzp_service_helper\preinsdata\permission.sql(本应用表单权限-------系统库下执行)


赞 5