├── .gitignore ├── LICENSE ├── NewVersion.md ├── README-cn.md ├── README.md ├── dtmcli-common ├── pom.xml └── src │ └── main │ └── java │ └── pub │ └── dtm │ └── client │ ├── constant │ ├── Constants.java │ └── ParamFieldConstants.java │ ├── enums │ └── TransTypeEnum.java │ ├── exception │ └── FailureException.java │ ├── interfaces │ ├── dtm │ │ └── DtmConsumer.java │ └── stub │ │ ├── IDtmServerStub.java │ │ └── IURIParser.java │ ├── log │ └── DtmFeignLogger.java │ ├── model │ ├── dtm │ │ └── TransBase.java │ ├── feign │ │ └── ServiceMessage.java │ ├── param │ │ ├── OperatorParam.java │ │ ├── SagaOperatorParam.java │ │ └── TccOperatorParam.java │ └── responses │ │ └── DtmResponse.java │ └── utils │ ├── FeignUtils.java │ ├── HttpUtils.java │ └── JsonUtils.java ├── dtmcli-core ├── pom.xml └── src │ └── main │ └── java │ └── pub │ └── dtm │ └── client │ ├── barrier │ ├── BarrierParam.java │ ├── BranchBarrier.java │ └── itfc │ │ ├── BarrierDBOperator.java │ │ ├── ConnectionCallback.java │ │ ├── ConnectionManager.java │ │ └── impl │ │ └── BarrierMysqlOperator.java │ ├── base │ └── BranchIdGenerator.java │ ├── saga │ └── Saga.java │ └── tcc │ └── Tcc.java ├── dtmcli-java ├── pom.xml └── src │ └── main │ └── java │ └── pub │ └── dtm │ └── client │ ├── DtmClient.java │ ├── properties │ └── DtmProperties.java │ ├── stub │ ├── DtmFeignClient.java │ └── URIParser.java │ └── utils │ └── NacosUtils.java ├── dtmcli-springcloud ├── pom.xml └── src │ └── main │ ├── java │ └── pub │ │ └── dtm │ │ └── client │ │ ├── DtmClient.java │ │ ├── configuration │ │ └── DtmConfiguration.java │ │ ├── properties │ │ └── DtmProperties.java │ │ └── stub │ │ ├── DtmFeignClient.java │ │ └── URIParser.java │ └── resources │ └── META-INF │ └── spring.factories ├── eureka-plugin ├── pom.xml └── src │ └── main │ ├── java │ └── pub │ │ └── dtm │ │ └── client │ │ └── configuration │ │ └── EurekaConfiguration.java │ └── resources │ └── META-INF │ └── spring.factories ├── nacos-plugin └── pom.xml ├── pic_ref ├── newversion.png └── oldversion.png └── pom.xml /.gitignore: -------------------------------------------------------------------------------- 1 | # Compiled class file 2 | *.class 3 | 4 | # Log file 5 | *.log 6 | 7 | # BlueJ files 8 | *.ctxt 9 | 10 | # Mobile Tools for Java (J2ME) 11 | .mtj.tmp/ 12 | 13 | # Package Files # 14 | *.jar 15 | *.war 16 | *.nar 17 | *.ear 18 | *.zip 19 | *.tar.gz 20 | *.rar 21 | 22 | # virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml 23 | hs_err_pid* 24 | 25 | .idea 26 | *.iml 27 | /*/target/ -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2022 dtm-labs 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /NewVersion.md: -------------------------------------------------------------------------------- 1 | # new version 2 | 新版本相比于旧版本Java client的的改造 3 | ## 旧版本客户端 4 | ![avatar](pic_ref/oldversion.png) 5 | ### 旧版本在设计上可以改进的一些地方 6 | 1.引入的类从引入路径看不出来自哪个jar包,比如exception.FailureException。在大型项目中可能会出现多个相同的类名,如果不明确包名可能会导致意义混乱,甚至引入冲突。 7 | 2.tcc等类直接依赖了dtmsvr信息,这样的依赖方式对后期的维护不友好,如果修改了DtmServerInfo的属性,那么后期需要修改所有支持的方式。应该做一个客户端这样的东西专门用来发送请求。 8 | 3.向dtmsvr传递参数时使用了map来传递,虽然这对用户是无感知的,但是客户在debug的时候使用map比较麻烦,感觉使用一个param对象比较好 9 | ## 新版本客户端 10 | ![avatar](pic_ref/newversion.png) 11 | ### 新版本中改进的地方 12 | 1.由于新版本需要同时支持http和feign两种交互方式,因此将请求dtmsvr相关的部分以及整个client的公共部分抽取出来形成了dtmcli-common模块,这样后续如果需要支持更多的交互方式只需要改动dtmcli-common中的代码,并在core新增代码 13 | 2.springcloud版本的client不在乎需要传入ipport这样的配置参数,一切通过feign+nacos/euraka集成起来处理。因此将java-client和spring-client分开处理了 14 | 3.对于一些非springcloud的项目我们也提供了java-client来处理,java-client支持像以前那样直接配置endpoint的方式,同时为了适配frontend服务,也支持通过配置nacos服务中心地址这样的方式来动态查找dtmsvr具体的地址。 15 | 4.优化了整个项目的包结构,让引入dtmcli-java的时候能够快速找到来自哪个包 16 | 17 | 18 | -------------------------------------------------------------------------------- /README-cn.md: -------------------------------------------------------------------------------- 1 | # dtmcli-java [![MIT][license-badge]](https://github.com/dtm-labs/dtmcli/blob/main/LICENSE) 2 | 3 | 简体中文 | [English](./README.md) 4 | 5 | `dtmcli-java` 是分布式事务管理器 [dtm](https://github.com/dtm-labs/dtm) 的Java客户端sdk 6 | 7 | ## DTM是什么 8 | 9 | DTM是一款变革性的分布式事务框架,提供了傻瓜式的使用方式,极大的降低了分布式事务的使用门槛,改变了“能不用分布式事务就不用”的行业现状,优雅的解决了服务间的数据一致性问题。 10 | 11 | ## 特性 12 | * 支持多种语言:支持Go、Java、PHP、C#、Python、Nodejs 各种语言的SDK 13 | * 支持多种事务模式:SAGA、TCC、XA 14 | * 支持消息最终一致性:二阶段消息,比本地消息表更优雅的方案 15 | * 支持多种数据库事务:Mysql、Redis、MongoDB、Postgres、TDSQL等 16 | * 支持多种存储引擎:Mysql(常用)、Redis(高性能)、MongoDB(规划中) 17 | * 支持多种微服务架构:[go-zero](https://github.com/zeromicro/go-zero)、go-kratos/kratos、polarismesh/polaris 18 | * 支持高可用,易水平扩展 19 | 20 | ## 使用方式 21 | 22 | ### 步骤一:确定你需要使用的版本 23 | 1. 您的项目是springcloud项目 24 | - 您的项目中springboot版本>=2.4.0,请选择dtmcli-springcloud相应的版本直接接入即可 25 | - 您的项目中的springboot版本<2.4.0,请选择dtmcli-java接入,dtmcli-java也提供了微服务相关的接口,请设置nacos服务中心的相关配置即可使用 26 | 2. 您的项目是普通项目/没有接入微服务的spring(boot)项目 27 | - 请选择dtmcli-java,并设置相应的配置即可 28 | 29 | | artifact| version | 适用版本 |备注| 30 | |:-----:|:----:|:----:|:----:| 31 | |dtmcli-springcloud| 2.1.4.1| 2.4.0 <= springboot version < 2.5.13| springboot 版本>=2.5.0,需要设置spring.cloud.compatibility-verifier.enabled=false| 32 | |dtmcli-springcloud| 2.1.4.2| 2.6.0 <= springboot version < 2.6.latest| | 33 | |dtmcli-java| 2.1.4| others| | 34 | 35 | ### 步骤二:添加依赖项 36 | 37 | Maven: 38 | 39 | ```bash 40 | 41 | io.github.dtm-labs 42 | dtmcli-springcloud 43 | ${dtmcli.version} 44 | 45 | ``` 46 | 47 | Gradle: 48 | 49 | ```bash 50 | dependencies { 51 | implementation 'io.github.dtm-labs:dtmcli-springcloud:${dtmcli.version}' 52 | } 53 | ``` 54 | 55 | ### 步骤三:设置dtmcli-java配置 56 | 如果您引入了dtmcli-java,则需要新建一个`dtm-conf.properties`配置文件 57 | - 情形一:您引入了nacos等服务中心组件的配置文件 58 | ``` 59 | serverAddr=127.0.0.1:8848 60 | username=nacos 61 | password=nacos 62 | namespace=c3dc917d-906a-429d-90a9-85012b41014e 63 | dtm.service.name=dtmService 64 | dtm.service.registryType=nacos 65 | ``` 66 | - 情形二:您直连dtmsvr 67 | ``` 68 | dtm.ipport=127.0.0.1:36789 69 | ``` 70 | ## 示例 71 | 72 | ```bash 73 | @RequestMapping("testTcc") 74 | public String testTcc() { 75 | //创建dtm clinet 76 | DtmClient dtmClient = new DtmClient(ipPort); 77 | //创建tcc事务 78 | try { 79 | dtmClient.tccGlobalTransaction(dtmClient.genGid(), TccTestController::tccTrans); 80 | } catch (Exception e) { 81 | log.error("tccGlobalTransaction error", e); 82 | return "fail"; 83 | } 84 | return "success"; 85 | } 86 | 87 | /** 88 | * 定义tcc事务函数,内部需要通过callBranch注册事务子分支 89 | * 90 | * @param tcc 91 | * @return 92 | * @see TransController 93 | */ 94 | public static void tccTrans(Tcc tcc) throws Exception { 95 | Response outResponse = tcc 96 | .callBranch("", svc + "/TransOutTry", svc + "/TransOutConfirm", svc + "/TransOutCancel"); 97 | log.info("outResponse:{}", outResponse); 98 | Response inResponse = tcc.callBranch("", svc + "/TransInTry", svc + "/TransInConfirm", svc + "/TransInCancel"); 99 | log.info("inResponse:{}", inResponse); 100 | } 101 | ``` 102 | 103 | 104 | ### 完整示例 105 | 106 | #### dtmcli-java使用示例 107 | [dtmcli-java-sample](https://github.com/dtm-labs/dtmcli-java-sample) 108 | [dtmcli-java-sample-use-configuration](https://github.com/horseLk/dtmcli-java-sample-with-conf) 109 | #### dtmcli-springcloud使用示例 110 | [dtmcli-java-spring-sample](https://github.com/dtm-labs/dtmcli-java-spring-sample) 111 | 112 | [license-badge]: https://img.shields.io/github/license/dtm-labs/dtmcli-java 113 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # dtmcli-java [![MIT][license-badge]](https://github.com/dtm-labs/dtmcli/blob/main/LICENSE) 2 | 3 | English | [简体中文](./README-cn.md) 4 | 5 | `dtmcli-java` is the Java client SDK for distributed transaction manager [dtm](https://github.com/dtm-labs/dtm) 6 | 7 | ## What is DTM 8 | 9 | DTM is a distributed transaction framework which provides cross-service eventual data consistency. It provides saga, tcc, xa, 2-phase message, outbox patterns for a variety of application scenarios. It also supports multiple languages and multiple store engine to form up a transaction as following: 10 | 11 | function-picture 12 | 13 | ## Features 14 | * Support for multiple languages: Go, Java, PHP, C#, Python, Nodejs SDKs 15 | * Support for multiple transaction patterns: SAGA, TCC, XA 16 | * Support for OutBox pattern: 2-phase messages, a more elegant solution than OutBox 17 | * Support for multiple database transactions: Mysql, Redis, MongoDB, Postgres, TDSQL, etc. 18 | * Support for multiple storage engines: Mysql (common), Redis (high performance), MongoDB (in planning) 19 | * Support for multiple microservices architectures: [go-zero](https://github.com/zeromicro/go-zero), go-kratos/kratos, polarismesh/polaris 20 | * Support for high availability and easy horizontal scaling 21 | 22 | ## Usage 23 | 24 | ### Step 1: Determine the version 25 | 1. Springcloud Projects 26 | - If the version of springboot >= 2.4.0, choose a corresponding version of dtmcli-springcloud. 27 | - If the version of springboot <> 2.4.0, use dtmcli-java, it provide the interfaces for micro-services, please set the configuration for nacos. 28 | 2. Not Springcloud Projects. 29 | - use dtmcli-java,and set your configurations. 30 | 31 | | artifact| version | dtmcli-java version |remark| 32 | |:-----:|:----:|:----:|:----:| 33 | |dtmcli-springcloud| 2.1.4.1| 2.4.0 <= springboot version < 2.5.13| for springboot >= 2.5.0,please set spring.cloud.compatibility-verifier.enabled=false| 34 | |dtmcli-springcloud| 2.1.4.2| 2.6.0 <= springboot version < 2.6.latest| | 35 | |dtmcli-java| 2.1.4| others| | 36 | 37 | ### Step 2: Add Dependencies 38 | 39 | Maven: 40 | 41 | ```bash 42 | 43 | io.github.dtm-labs 44 | dtmcli-springcloud 45 | ${dtmcli.version} 46 | 47 | ``` 48 | 49 | Gradle: 50 | 51 | ```bash 52 | dependencies { 53 | implementation 'io.github.dtm-labs:dtmcli-springcloud:${dtmcli.version}' 54 | } 55 | ``` 56 | 57 | ### Step 3:Configure dtmcli-java 58 | If you are using dtmcli-java,new a file named `dtm-conf.properties` 59 | - Case 1: Using naceos 60 | ``` 61 | serverAddr=127.0.0.1:8848 62 | username=nacos 63 | password=nacos 64 | namespace=c3dc917d-906a-429d-90a9-85012b41014e 65 | dtm.service.name=dtmService 66 | dtm.service.registryType=nacos 67 | ``` 68 | - Case 2: Connect to dtmsvr directly 69 | ``` 70 | dtm.ipport=127.0.0.1:36789 71 | ``` 72 | ## Sample 73 | 74 | ```bash 75 | @RequestMapping("testTcc") 76 | public String testTcc() { 77 | // new dtm clinet 78 | DtmClient dtmClient = new DtmClient(ipPort); 79 | //create TCC transaction 80 | try { 81 | dtmClient.tccGlobalTransaction(dtmClient.genGid(), TccTestController::tccTrans); 82 | } catch (Exception e) { 83 | log.error("tccGlobalTransaction error", e); 84 | return "fail"; 85 | } 86 | return "success"; 87 | } 88 | 89 | /** 90 | * define TCC sub-transactions by calling callBranch 91 | * 92 | * @param tcc 93 | * @return 94 | * @see TransController 95 | */ 96 | public static void tccTrans(Tcc tcc) throws Exception { 97 | Response outResponse = tcc 98 | .callBranch("", svc + "/TransOutTry", svc + "/TransOutConfirm", svc + "/TransOutCancel"); 99 | log.info("outResponse:{}", outResponse); 100 | Response inResponse = tcc.callBranch("", svc + "/TransInTry", svc + "/TransInConfirm", svc + "/TransInCancel"); 101 | log.info("inResponse:{}", inResponse); 102 | } 103 | ``` 104 | 105 | 106 | ### Complete Sample 107 | 108 | #### Sample for dtmcli-java 109 | [dtmcli-java-sample](https://github.com/dtm-labs/dtmcli-java-sample) 110 | [dtmcli-java-sample-use-configuration](https://github.com/horseLk/dtmcli-java-sample-with-conf) 111 | #### Sample for dtmcli-springcloud 112 | [dtmcli-java-spring-sample](https://github.com/dtm-labs/dtmcli-java-spring-sample) 113 | 114 | [license-badge]: https://img.shields.io/github/license/dtm-labs/dtmcli-java 115 | -------------------------------------------------------------------------------- /dtmcli-common/pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | dtmcli-java-parent 7 | io.github.dtm-labs 8 | 2.1.8 9 | 10 | 4.0.0 11 | 12 | dtmcli-common 13 | 2.1.8 14 | jar 15 | dtmcli-common 16 | 17 | 18 | UTF-8 19 | 1.8 20 | 1.8 21 | 22 | 23 | 24 | 25 | 26 | com.fasterxml.jackson.core 27 | jackson-databind 28 | 29 | 30 | 31 | org.projectlombok 32 | lombok 33 | 34 | 35 | 36 | io.github.openfeign 37 | feign-core 38 | 39 | 40 | 41 | org.apache.commons 42 | commons-lang3 43 | 44 | 45 | 46 | com.squareup.okhttp3 47 | okhttp 48 | 49 | 50 | 51 | com.alibaba.nacos 52 | nacos-client 53 | 54 | 55 | 56 | org.slf4j 57 | slf4j-api 58 | 59 | 60 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/constant/Constants.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.constant; 26 | 27 | /** 28 | * Constants 29 | * 30 | * @author horseLk 31 | */ 32 | public class Constants { 33 | public static final String MICRO_SERVICE_NAME_KEY = "dtm.service.name"; 34 | 35 | public static final String GET_METHOD = "GET "; 36 | 37 | public static final String POST_METHOD = "POST "; 38 | 39 | public static final String HTTP_PREFIX = "http://"; 40 | 41 | public static final String HTTPS_PREFIX = "https://"; 42 | 43 | public static final String PING_URL = "/api/ping"; 44 | 45 | private static final String BASE_URL = "/api/dtmsvr"; 46 | 47 | public static final String NEW_GID_URL = BASE_URL + "/newGid"; 48 | 49 | public static final String PREPARE_URL = BASE_URL + "/prepare"; 50 | 51 | public static final String SUBMIT_URL = BASE_URL + "/submit"; 52 | 53 | public static final String ABORT_URL = BASE_URL + "/abort"; 54 | 55 | public static final String REGISTER_BRANCH_URL = BASE_URL + "/registerBranch"; 56 | 57 | public static final String DEFAULT_STATUS = "prepared"; 58 | 59 | public static final String EMPTY_STRING = ""; 60 | 61 | public static final String SUCCESS_RESULT = "SUCCESS"; 62 | 63 | public static final String FAILURE_RESULT = "FAILURE"; 64 | 65 | public static final int RESP_ERR_CODE = 400; 66 | } 67 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/constant/ParamFieldConstants.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.constant; 26 | 27 | /** 28 | * Constants for dtm server parameter key 29 | * 30 | * @author horseLk 31 | */ 32 | public class ParamFieldConstants { 33 | public static final String GID = "gid"; 34 | 35 | public static final String TRANS_TYPE = "trans_type"; 36 | 37 | public static final String BRANCH_ID = "branch_id"; 38 | 39 | public static final String STATUS = "status"; 40 | 41 | public static final String DATA = "data"; 42 | 43 | public static final String TRY = "try"; 44 | 45 | public static final String CONFIRM = "confirm"; 46 | 47 | public static final String CANCEL = "cancel"; 48 | 49 | public static final String OP = "op"; 50 | 51 | public static final String CODE = "code"; 52 | 53 | public static final String MESSAGE = "message"; 54 | 55 | public static final String DTM_RESULT = "dtm_result"; 56 | 57 | public static final String ACTION = "action"; 58 | 59 | public static final String COMPENSATE = "compensate"; 60 | 61 | public static final String STEPS = "steps"; 62 | 63 | public static final String PAYLOADS = "payloads"; 64 | 65 | public static final String CUSTOM_DATA = "custom_data"; 66 | 67 | public static final String WAIT_RESULT = "wait_result"; 68 | 69 | public static final String TIMEOUT_TO_FAIL = "timeout_to_fail"; 70 | 71 | public static final String RETRY_INTERVAL = "retry_interval"; 72 | 73 | public static final String PASSTHROGH_HEADERS = "passthrough_headers"; 74 | 75 | public static final String BRANCH_HEADERS = "branch_headers"; 76 | } 77 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/enums/TransTypeEnum.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.enums; 26 | 27 | import java.util.HashMap; 28 | import java.util.Map; 29 | 30 | /** 31 | * Transtype enum 32 | * 33 | * @author horseLk 34 | */ 35 | public enum TransTypeEnum { 36 | /** 37 | * tcc 38 | */ 39 | TCC("tcc"), 40 | /** 41 | * xa 42 | */ 43 | XA("xa"), 44 | /** 45 | * msg 46 | */ 47 | MSG("msg"), 48 | /** 49 | * saga 50 | */ 51 | SAGA("saga") 52 | ; 53 | 54 | TransTypeEnum(String value) { 55 | this.value = value; 56 | } 57 | 58 | /** 59 | * Trans type string 60 | */ 61 | private final String value; 62 | 63 | public String getValue() { 64 | return this.value; 65 | } 66 | 67 | private static final Map EXIST = new HashMap<>(); 68 | 69 | static { 70 | for (TransTypeEnum transType : TransTypeEnum.values()) { 71 | EXIST.put(transType.value, transType); 72 | } 73 | } 74 | 75 | public static TransTypeEnum parseString(String value) { 76 | return EXIST.get(value); 77 | } 78 | } 79 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/exception/FailureException.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.exception; 26 | 27 | /** 28 | * dtm common exception 29 | * 30 | * @author horseLk 31 | */ 32 | public class FailureException extends Exception { 33 | public FailureException(String msg) { 34 | super(msg); 35 | } 36 | 37 | public FailureException(Throwable e) { 38 | super(e); 39 | } 40 | } 41 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/interfaces/dtm/DtmConsumer.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.interfaces.dtm; 26 | 27 | import pub.dtm.client.model.dtm.TransBase; 28 | 29 | /** 30 | * Functional Interface for Transtype to process busi request 31 | * 32 | * @param 33 | * @author horseLk 34 | */ 35 | @FunctionalInterface 36 | public interface DtmConsumer { 37 | void accept(T t) throws Exception; 38 | } 39 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/interfaces/stub/IDtmServerStub.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.interfaces.stub; 26 | 27 | import feign.Response; 28 | import pub.dtm.client.model.param.OperatorParam; 29 | import pub.dtm.client.model.responses.DtmResponse; 30 | 31 | import java.net.URI; 32 | import java.util.Map; 33 | 34 | /** 35 | * A stub interface for dtm svr, different client has different implements. 36 | * 37 | * @author horseLk 38 | */ 39 | public interface IDtmServerStub { 40 | /** 41 | * get stubType 42 | * @return type 43 | */ 44 | String stubType(); 45 | 46 | /** 47 | * get a new gid 48 | */ 49 | DtmResponse newGid(); 50 | 51 | /** 52 | * test connection 53 | */ 54 | DtmResponse ping(); 55 | 56 | /** 57 | * prepare 58 | * @param body prepare body 59 | */ 60 | DtmResponse prepare(OperatorParam body); 61 | 62 | /** 63 | * submit 64 | * @param body submit bosy 65 | */ 66 | DtmResponse submit(OperatorParam body); 67 | 68 | /** 69 | * abort 70 | * @param body abort body 71 | */ 72 | DtmResponse abort(OperatorParam body); 73 | 74 | /** 75 | * registerBranch 76 | * @param body registerBranch body 77 | */ 78 | DtmResponse registerBranch(OperatorParam body); 79 | 80 | /** 81 | * use feign send busi get request 82 | * @param host busi host 83 | * @param path busi path 84 | * @param queryMap querymao 85 | */ 86 | Response busiGet(URI host, String path, Map queryMap); 87 | 88 | /** 89 | * use feign send busi post request 90 | * @param host busi host 91 | * @param path busi path 92 | * @param queryMap query map 93 | * @param body request body 94 | */ 95 | Response busiPost(URI host, String path, Map queryMap, Object body); 96 | } 97 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/interfaces/stub/IURIParser.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.interfaces.stub; 26 | 27 | import pub.dtm.client.model.feign.ServiceMessage; 28 | 29 | /** 30 | * URI Parser interface 31 | * 32 | * @author horseLk 33 | */ 34 | public interface IURIParser { 35 | /** 36 | * according to serviceMessage and connection driver generate uri 37 | * @param serviceMessage service message 38 | * @param httpType true means http, false means microservice 39 | * @return uri 40 | * @throws Exception exception 41 | */ 42 | String generatorURI(ServiceMessage serviceMessage, boolean httpType) throws Exception; 43 | } 44 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/log/DtmFeignLogger.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.log; 26 | 27 | import org.slf4j.Logger; 28 | import org.slf4j.LoggerFactory; 29 | 30 | /** 31 | * Custom feign logger for print detail feign log 32 | * 33 | * @author horseLk 34 | */ 35 | public class DtmFeignLogger extends feign.Logger { 36 | private final Logger logger; 37 | 38 | public DtmFeignLogger() { 39 | this(feign.Logger.class); 40 | } 41 | 42 | public DtmFeignLogger(Class clazz) { 43 | this(LoggerFactory.getLogger(clazz)); 44 | } 45 | 46 | public DtmFeignLogger(String name) { 47 | this(LoggerFactory.getLogger(name)); 48 | } 49 | 50 | DtmFeignLogger(Logger logger) { 51 | this.logger = logger; 52 | } 53 | 54 | @Override 55 | protected void log(String configKey, String format, Object... args) { 56 | // Not using SLF4J's support for parameterized messages (even though it 57 | // would be more efficient) because it would 58 | // require the incoming message formats to be SLF4J-specific. 59 | if (logger.isInfoEnabled()) { 60 | logger.info(String.format(methodTag(configKey) + format, args)); 61 | } 62 | } 63 | } 64 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/model/dtm/TransBase.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.model.dtm; 26 | 27 | import pub.dtm.client.enums.TransTypeEnum; 28 | import lombok.AllArgsConstructor; 29 | import lombok.Data; 30 | import lombok.NoArgsConstructor; 31 | 32 | /** 33 | * base Class for different Trans type 34 | * 35 | * @author horseLk 36 | */ 37 | @Data 38 | @NoArgsConstructor 39 | @AllArgsConstructor 40 | public class TransBase { 41 | /** 42 | * global transaction id 43 | */ 44 | private String gid; 45 | 46 | /** 47 | * trans type 48 | */ 49 | private TransTypeEnum transTypeEnum; 50 | 51 | /** 52 | * is wait for result 53 | */ 54 | private boolean waitResult; 55 | } 56 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/model/feign/ServiceMessage.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.model.feign; 26 | 27 | import lombok.Data; 28 | import lombok.NoArgsConstructor; 29 | import org.apache.commons.lang3.StringUtils; 30 | 31 | import java.util.ArrayList; 32 | import java.util.List; 33 | 34 | /** 35 | * Service message for micro service 36 | * 37 | * @author horseLk 38 | */ 39 | @Data 40 | @NoArgsConstructor 41 | public class ServiceMessage { 42 | /** 43 | * service name 44 | */ 45 | private String serviceName; 46 | 47 | /** 48 | * group name 49 | */ 50 | private String groupName = "DEFAULT_GROUP"; 51 | 52 | /** 53 | * clusters 54 | */ 55 | private List cluster = new ArrayList<>(); 56 | 57 | /** 58 | * request path 59 | */ 60 | private String path; 61 | 62 | public ServiceMessage(String serviceName, String path){ 63 | this.serviceName = serviceName; 64 | this.path = path; 65 | } 66 | 67 | public ServiceMessage(String serviceName, String groupName, List cluster, String path) { 68 | this.serviceName = serviceName; 69 | this.groupName = groupName; 70 | this.cluster.addAll(cluster); 71 | this.path = path; 72 | } 73 | 74 | public String getPath() { 75 | if (StringUtils.startsWith(path, "/")) { 76 | return path; 77 | } 78 | return "/" + path; 79 | } 80 | 81 | @Override 82 | public String toString() { 83 | String _path = path; 84 | if (!StringUtils.startsWith(path, "/")) { 85 | _path = "/" + path; 86 | } 87 | return serviceName + _path + "?groupName=" + groupName; 88 | } 89 | } 90 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/model/param/OperatorParam.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.model.param; 26 | 27 | import com.fasterxml.jackson.annotation.JsonProperty; 28 | import com.fasterxml.jackson.annotation.JsonSubTypes; 29 | import com.fasterxml.jackson.annotation.JsonTypeInfo; 30 | import pub.dtm.client.constant.ParamFieldConstants; 31 | import pub.dtm.client.enums.TransTypeEnum; 32 | import lombok.AllArgsConstructor; 33 | import lombok.Data; 34 | import lombok.NoArgsConstructor; 35 | 36 | /** 37 | * Request Param for dtm svr 38 | * 39 | * @author horseLk 40 | */ 41 | @Data 42 | @NoArgsConstructor 43 | @AllArgsConstructor 44 | @JsonTypeInfo(use = JsonTypeInfo.Id.NAME, property = "subType") 45 | @JsonSubTypes({ 46 | @JsonSubTypes.Type(value = TccOperatorParam.class, name = "tcc"), 47 | @JsonSubTypes.Type(value = SagaOperatorParam.class, name = "saga") 48 | }) 49 | public class OperatorParam { 50 | /** 51 | * gid 52 | */ 53 | @JsonProperty(ParamFieldConstants.GID) 54 | private String gid; 55 | 56 | /** 57 | * trans type string value 58 | */ 59 | @JsonProperty(ParamFieldConstants.TRANS_TYPE) 60 | private String transType; 61 | 62 | /** 63 | * this attribute just for mark different sub class for encode/decode. 64 | */ 65 | @JsonProperty("subType") 66 | private String subType; 67 | 68 | public OperatorParam(String gid, TransTypeEnum transType) { 69 | this.gid = gid; 70 | this.transType = transType.getValue(); 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/model/param/SagaOperatorParam.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.model.param; 26 | 27 | import com.fasterxml.jackson.annotation.JsonProperty; 28 | import lombok.Data; 29 | import lombok.NoArgsConstructor; 30 | import pub.dtm.client.constant.ParamFieldConstants; 31 | import pub.dtm.client.enums.TransTypeEnum; 32 | 33 | import java.util.List; 34 | import java.util.Map; 35 | 36 | /** 37 | * Saga Operator Param 38 | * 39 | * @author horseLk 40 | */ 41 | @Data 42 | @NoArgsConstructor 43 | public class SagaOperatorParam extends OperatorParam { 44 | @JsonProperty(ParamFieldConstants.STEPS) 45 | private List> steps; 46 | 47 | @JsonProperty(ParamFieldConstants.PAYLOADS) 48 | private List payloads; 49 | 50 | @JsonProperty(ParamFieldConstants.CUSTOM_DATA) 51 | private String customData; 52 | 53 | @JsonProperty(ParamFieldConstants.WAIT_RESULT) 54 | private boolean waitResult; 55 | 56 | @JsonProperty(ParamFieldConstants.TIMEOUT_TO_FAIL) 57 | private long timeoutToFail; 58 | 59 | @JsonProperty(ParamFieldConstants.RETRY_INTERVAL) 60 | private long retryInterval; 61 | 62 | @JsonProperty(ParamFieldConstants.PASSTHROGH_HEADERS) 63 | private List passthroughHeaders; 64 | 65 | @JsonProperty(ParamFieldConstants.BRANCH_HEADERS) 66 | private Map branchHeaders; 67 | 68 | public SagaOperatorParam(String gid, TransTypeEnum transType, List> steps, 69 | List payloads, String customData, boolean waitResult, long timeoutToFail, 70 | long retryInterval, List passthroughHeaders, Map branchHeaders) { 71 | super(gid, transType); 72 | setSubType(transType.getValue()); 73 | this.steps = steps; 74 | this.payloads = payloads; 75 | this.customData = customData; 76 | this.waitResult = waitResult; 77 | this.timeoutToFail = timeoutToFail; 78 | this.retryInterval = retryInterval; 79 | this.passthroughHeaders = passthroughHeaders; 80 | this.branchHeaders = branchHeaders; 81 | } 82 | } 83 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/model/param/TccOperatorParam.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.model.param; 26 | 27 | import com.fasterxml.jackson.annotation.JsonProperty; 28 | import lombok.Data; 29 | import lombok.NoArgsConstructor; 30 | import pub.dtm.client.constant.ParamFieldConstants; 31 | import pub.dtm.client.enums.TransTypeEnum; 32 | 33 | /** 34 | * Tcc Operator Param 35 | * @author horseLk 36 | */ 37 | @Data 38 | @NoArgsConstructor 39 | public class TccOperatorParam extends OperatorParam { 40 | /** 41 | * branch id 42 | */ 43 | @JsonProperty(ParamFieldConstants.BRANCH_ID) 44 | private String branchId; 45 | 46 | /** 47 | * status 48 | */ 49 | @JsonProperty(ParamFieldConstants.STATUS) 50 | private String status; 51 | 52 | /** 53 | * data 54 | */ 55 | @JsonProperty(ParamFieldConstants.DATA) 56 | private String data; 57 | 58 | /** 59 | * branch confirm uri 60 | */ 61 | @JsonProperty(ParamFieldConstants.CONFIRM) 62 | private String confirm; 63 | 64 | /** 65 | * branch cancel uri 66 | */ 67 | @JsonProperty(ParamFieldConstants.CANCEL) 68 | private String cancel; 69 | 70 | 71 | public TccOperatorParam(String gid, TransTypeEnum transTypeEnum, String branchId, String status, String data, 72 | String confirm, String cancel) { 73 | super(gid, transTypeEnum); 74 | setSubType(transTypeEnum.getValue()); 75 | this.branchId = branchId; 76 | this.status = status; 77 | this.data = data; 78 | this.confirm = confirm; 79 | this.cancel = cancel; 80 | } 81 | } 82 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/model/responses/DtmResponse.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.model.responses; 26 | 27 | import com.fasterxml.jackson.annotation.JsonProperty; 28 | import lombok.AllArgsConstructor; 29 | import lombok.Data; 30 | import lombok.NoArgsConstructor; 31 | 32 | /** 33 | * Response from dtm svr 34 | * 35 | * @author horseLk 36 | */ 37 | @Data 38 | @AllArgsConstructor 39 | @NoArgsConstructor 40 | public class DtmResponse { 41 | /** 42 | * dtm_result 43 | */ 44 | @JsonProperty("dtm_result") 45 | private String dtmResult; 46 | 47 | /** 48 | * gid 49 | */ 50 | @JsonProperty("gid") 51 | private String gid; 52 | 53 | public static DtmResponse buildDtmResponse(String result) { 54 | return new DtmResponse(result, null); 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/utils/FeignUtils.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.utils; 26 | 27 | import pub.dtm.client.constant.Constants; 28 | import pub.dtm.client.exception.FailureException; 29 | import feign.Response; 30 | import pub.dtm.client.interfaces.stub.IURIParser; 31 | import pub.dtm.client.model.feign.ServiceMessage; 32 | import org.apache.commons.io.IOUtils; 33 | import org.apache.commons.lang3.StringUtils; 34 | import org.slf4j.Logger; 35 | import org.slf4j.LoggerFactory; 36 | import pub.dtm.client.model.responses.DtmResponse; 37 | 38 | import java.io.IOException; 39 | import java.io.InputStream; 40 | import java.nio.charset.StandardCharsets; 41 | 42 | /** 43 | * Feign Utils 44 | * 45 | * @author horseLk 46 | */ 47 | public class FeignUtils { 48 | /** 49 | * log 50 | */ 51 | private static final Logger log = LoggerFactory.getLogger(FeignUtils.class); 52 | 53 | /** 54 | * URIParser 55 | */ 56 | private static IURIParser uriParser; 57 | 58 | public static void setUriParser(IURIParser uriParser) { 59 | FeignUtils.uriParser = uriParser; 60 | } 61 | 62 | /** 63 | * Get gid from DtmResponse 64 | * @param base dtmResponse 65 | * @return gid 66 | * @throws Exception exception 67 | */ 68 | public static String parseGid(DtmResponse base) throws Exception { 69 | if (base == null || !Constants.SUCCESS_RESULT.equals(base.getDtmResult())) { 70 | throw new Exception("get new gid from dtm server fail."); 71 | } 72 | return base.getGid(); 73 | } 74 | 75 | /** 76 | * generate uri 77 | * @param serviceMessage service message 78 | * @param httpType true means http, false means micro service 79 | * @return uri 80 | * @throws Exception exception 81 | */ 82 | public static String generatorURI(ServiceMessage serviceMessage, boolean httpType) throws Exception { 83 | return uriParser.generatorURI(serviceMessage, httpType); 84 | } 85 | 86 | /** 87 | * check response 88 | * @param response feign response 89 | * @throws FailureException exception 90 | */ 91 | public static void checkResult(Response response) throws FailureException { 92 | checkResultWithReturn(response); 93 | } 94 | 95 | /** 96 | * check response and return result 97 | * @param response 98 | * @return 99 | * @throws FailureException 100 | */ 101 | public static String checkResultWithReturn(Response response) throws FailureException { 102 | if (response.status() >= Constants.RESP_ERR_CODE){ 103 | if (response.reason() != null) { 104 | throw new FailureException(response.reason()); 105 | } 106 | try { 107 | log.error("response code is {}, but unknown reason, response body is {}", response.status(), 108 | IOUtils.toString(response.body().asReader(StandardCharsets.UTF_8))); 109 | } finally { 110 | throw new FailureException("response code is " + response.status()); 111 | } 112 | } 113 | String result = ""; 114 | try { 115 | InputStream inputStream = response.body().asInputStream(); 116 | if (inputStream != null) { 117 | result = IOUtils.toString(inputStream, StandardCharsets.UTF_8); 118 | } 119 | } catch (IOException e) { 120 | throw new FailureException("response is null"); 121 | } 122 | if (StringUtils.isBlank(result)) { 123 | throw new FailureException("response is null"); 124 | } 125 | if (result.contains(Constants.FAILURE_RESULT)){ 126 | throw new FailureException("Service returned failed"); 127 | } 128 | return result; 129 | } 130 | } 131 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/utils/HttpUtils.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.utils; 26 | 27 | import pub.dtm.client.constant.Constants; 28 | import pub.dtm.client.exception.FailureException; 29 | import okhttp3.MediaType; 30 | import okhttp3.OkHttpClient; 31 | import okhttp3.Request; 32 | import okhttp3.RequestBody; 33 | import okhttp3.Response; 34 | import okhttp3.ResponseBody; 35 | import org.apache.commons.lang3.StringUtils; 36 | 37 | import java.io.IOException; 38 | import java.util.Map; 39 | import java.util.concurrent.TimeUnit; 40 | 41 | /** 42 | * Http utils 43 | * 44 | * @author horseLk 45 | */ 46 | public class HttpUtils { 47 | private static final OkHttpClient CLIENT = new OkHttpClient.Builder().connectTimeout(15, TimeUnit.SECONDS) 48 | .readTimeout(5, TimeUnit.SECONDS).writeTimeout(5, TimeUnit.SECONDS).build(); 49 | 50 | public static final MediaType MEDIA_TYPE = MediaType.get("application/json; charset=utf-8"); 51 | 52 | /** 53 | * send get request 54 | * @param url url 55 | * @return http response 56 | * @throws IOException exception 57 | */ 58 | public static Response get(String url) throws IOException { 59 | Request request = new Request.Builder().url(url).get().build(); 60 | return CLIENT.newCall(request).execute(); 61 | } 62 | 63 | /** 64 | * send post request 65 | * @param url url 66 | * @param json body json 67 | * @return http response 68 | * @throws IOException exception 69 | */ 70 | public static Response post(String url, String json) throws IOException { 71 | RequestBody body = RequestBody.create(MEDIA_TYPE, json); 72 | Request request = new Request.Builder().url(url).post(body).build(); 73 | return CLIENT.newCall(request).execute(); 74 | } 75 | 76 | /** 77 | * splice url with query map 78 | * @param url main url 79 | * @param params query map 80 | * @return string 81 | */ 82 | public static String splicingUrl(String url, Map params) { 83 | if (params == null || params.isEmpty()) { 84 | return url; 85 | } 86 | StringBuilder builder = new StringBuilder(url).append("?"); 87 | for (Map.Entry entry : params.entrySet()) { 88 | builder.append(entry.getKey()).append("=").append(entry.getValue()).append("&"); 89 | } 90 | return builder.deleteCharAt(builder.length() - 1).toString(); 91 | } 92 | 93 | 94 | /** 95 | * splice url without query map 96 | * @param ip ip 97 | * @param port port 98 | * @param path path 99 | * @return string 100 | */ 101 | public static String splicingUrl(String ip, int port, String path) { 102 | return Constants.HTTP_PREFIX + ip + ":" + String.valueOf(port) + path; 103 | } 104 | 105 | /** 106 | * check response 107 | * @param response http response 108 | * @throws Exception exception 109 | */ 110 | public static void checkResult(Response response) throws Exception { 111 | checkResultWithReturn(response); 112 | } 113 | 114 | /** 115 | * check response and return result 116 | * @param response 117 | * @return 118 | * @throws Exception 119 | */ 120 | public static String checkResultWithReturn(Response response) throws Exception { 121 | if (response.code() >= Constants.RESP_ERR_CODE){ 122 | throw new FailureException(response.message()); 123 | } 124 | ResponseBody body = response.body(); 125 | String result; 126 | if (body == null || StringUtils.isBlank(result = body.string())) { 127 | throw new FailureException("response is null"); 128 | } 129 | if (result.contains(Constants.FAILURE_RESULT)){ 130 | throw new FailureException("Service returned failed"); 131 | } 132 | return result; 133 | } 134 | } 135 | -------------------------------------------------------------------------------- /dtmcli-common/src/main/java/pub/dtm/client/utils/JsonUtils.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.utils; 26 | 27 | import com.fasterxml.jackson.core.JsonProcessingException; 28 | import com.fasterxml.jackson.databind.DeserializationFeature; 29 | import com.fasterxml.jackson.databind.ObjectMapper; 30 | 31 | import java.io.IOException; 32 | 33 | /** 34 | * Json Utils 35 | * 36 | * @author horseLk 37 | */ 38 | public class JsonUtils { 39 | private static final ObjectMapper objectMapper = 40 | new ObjectMapper().configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false); 41 | 42 | public static T parseJson(String json, Class clzz) throws JsonProcessingException { 43 | return objectMapper.readValue(json, clzz); 44 | } 45 | 46 | public static T parseJson(byte[] bytes, Class clzz) throws IOException { 47 | return objectMapper.readValue(bytes, clzz); 48 | } 49 | 50 | public static String toJson(Object object) throws JsonProcessingException { 51 | return objectMapper.writeValueAsString(object); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /dtmcli-core/pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | dtmcli-java-parent 7 | io.github.dtm-labs 8 | 2.1.8 9 | 10 | 4.0.0 11 | 12 | dtmcli-core 13 | 2.1.8 14 | jar 15 | dtmcli-core 16 | 17 | 18 | UTF-8 19 | 1.8 20 | 1.8 21 | 22 | 23 | 24 | 25 | io.github.dtm-labs 26 | dtmcli-common 27 | 2.1.5 28 | 29 | 30 | 31 | org.apache.commons 32 | commons-lang3 33 | 34 | 35 | 36 | org.slf4j 37 | slf4j-api 38 | 39 | 40 | 41 | 42 | -------------------------------------------------------------------------------- /dtmcli-core/src/main/java/pub/dtm/client/barrier/BarrierParam.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.barrier; 26 | 27 | import lombok.AllArgsConstructor; 28 | import lombok.Data; 29 | import lombok.NoArgsConstructor; 30 | 31 | /** 32 | * Branch barrier parameter 33 | * 34 | * @author horseLk 35 | */ 36 | @Data 37 | @NoArgsConstructor 38 | @AllArgsConstructor 39 | public class BarrierParam { 40 | /** 41 | * trans type 42 | */ 43 | private String trans_type[]; 44 | 45 | /** 46 | * gid 47 | */ 48 | private String gid[]; 49 | 50 | /** 51 | * branch id 52 | */ 53 | private String branch_id[]; 54 | 55 | /** 56 | * operator 57 | */ 58 | private String op[]; 59 | } 60 | -------------------------------------------------------------------------------- /dtmcli-core/src/main/java/pub/dtm/client/barrier/BranchBarrier.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.barrier; 26 | 27 | import pub.dtm.client.barrier.itfc.BarrierDBOperator; 28 | import pub.dtm.client.barrier.itfc.ConnectionManager; 29 | import pub.dtm.client.constant.ParamFieldConstants; 30 | import pub.dtm.client.enums.TransTypeEnum; 31 | import pub.dtm.client.exception.FailureException; 32 | import pub.dtm.client.interfaces.dtm.DtmConsumer; 33 | import lombok.Data; 34 | import lombok.NoArgsConstructor; 35 | import pub.dtm.client.model.dtm.TransBase; 36 | import org.apache.commons.lang3.ArrayUtils; 37 | import org.slf4j.Logger; 38 | import org.slf4j.LoggerFactory; 39 | import pub.dtm.client.utils.JsonUtils; 40 | 41 | import java.sql.Connection; 42 | import java.sql.PreparedStatement; 43 | import java.sql.SQLException; 44 | import java.util.Map; 45 | import java.util.Objects; 46 | 47 | /** 48 | * Branch barrier service 49 | * 50 | * @author horseLk 51 | */ 52 | @Data 53 | @NoArgsConstructor 54 | public class BranchBarrier extends TransBase { 55 | private static final Logger log = LoggerFactory.getLogger(BranchBarrier.class); 56 | 57 | /** 58 | * branch id 59 | */ 60 | private String branchId; 61 | 62 | /** 63 | * operator 64 | */ 65 | private String op; 66 | 67 | /** 68 | * barrier id 69 | */ 70 | private int barrierId; 71 | 72 | private ConnectionManager connectionManager; 73 | 74 | public BranchBarrier(Map paramsMap) throws Exception { 75 | this(paramsMap, null); 76 | } 77 | 78 | public BranchBarrier(Map paramsMap, ConnectionManager connectionManager) throws Exception { 79 | if (paramsMap == null || paramsMap.isEmpty()) { 80 | throw new FailureException("build BranchBarrier error, paramsMap can not be empty."); 81 | } 82 | BarrierParam barrierParam = JsonUtils.parseJson(JsonUtils.toJson(paramsMap), BarrierParam.class); 83 | if (ArrayUtils.isNotEmpty(barrierParam.getTrans_type())) { 84 | this.setTransTypeEnum(TransTypeEnum.parseString(barrierParam.getTrans_type()[0])); 85 | } 86 | if (ArrayUtils.isNotEmpty(barrierParam.getGid())) { 87 | this.setGid(barrierParam.getGid()[0]); 88 | } 89 | if (ArrayUtils.isNotEmpty(barrierParam.getBranch_id())) { 90 | this.branchId = barrierParam.getBranch_id()[0]; 91 | } 92 | if (ArrayUtils.isNotEmpty(barrierParam.getOp())) { 93 | this.op = barrierParam.getOp()[0]; 94 | } 95 | this.connectionManager = connectionManager; 96 | } 97 | 98 | /** 99 | * Busi can call method call() to open branch barrier 100 | * 101 | * @param connection data source connection 102 | * @param consumer consumer 103 | * @throws Exception exception 104 | */ 105 | public void call(Connection connection, DtmConsumer consumer) throws Exception { 106 | ++this.barrierId; 107 | connection.setAutoCommit(false); 108 | try { 109 | boolean result = insertBarrier(connection); 110 | if (result) { 111 | consumer.accept(this); 112 | connection.commit(); 113 | } 114 | } catch (Exception exception) { 115 | log.warn("barrier call error", exception); 116 | connection.rollback(); 117 | throw exception; 118 | } finally { 119 | connection.setAutoCommit(true); 120 | } 121 | } 122 | 123 | /** 124 | * Busi can call method call() to open branch barrier 125 | * 126 | * @param DBOperator db operator 127 | * @param consumer busi consumer 128 | * @throws Exception exception 129 | */ 130 | public void call(BarrierDBOperator DBOperator, DtmConsumer consumer) throws Exception { 131 | ++this.barrierId; 132 | try { 133 | boolean insertRes = DBOperator.insertBarrier(this.getTransTypeEnum().getValue(), this.getGid(), branchId, this.op, 134 | this.barrierId); 135 | if (insertRes) { 136 | consumer.accept(this); 137 | DBOperator.commit(); 138 | } 139 | } catch (Exception exception) { 140 | log.warn("barrier call error", exception); 141 | DBOperator.rollback(); 142 | throw new Exception(exception); 143 | } 144 | } 145 | 146 | // public void call(DtmConsumer consumer) throws Exception { 147 | // if (connectionManager == null) { 148 | // throw new IllegalStateException( 149 | // "Connection cannot be automatically created because ConnectionManager is not specified" 150 | // ); 151 | // } 152 | // connectionManager.execute(con -> { 153 | // call(con, consumer); 154 | // return null; 155 | // }); 156 | // } 157 | 158 | private boolean insertBarrier(Connection connection) throws SQLException { 159 | log.info("insert barrier {}", this); 160 | if (Objects.isNull(connection)) { 161 | return false; 162 | } 163 | PreparedStatement preparedStatement = null; 164 | try { 165 | String sql = "insert ignore into barrier(trans_type, gid, branch_id, op, barrier_id, reason) values(?,?,?,?,?,?)"; 166 | preparedStatement = connection.prepareStatement(sql); 167 | preparedStatement.setString(1, this.getTransTypeEnum().getValue()); 168 | preparedStatement.setString(2, this.getGid()); 169 | preparedStatement.setString(3, branchId); 170 | preparedStatement.setString(4, op); 171 | preparedStatement.setString(5, String.format("%02d", barrierId)); 172 | preparedStatement.setString(6, op); 173 | 174 | if (preparedStatement.executeUpdate() == 0) { 175 | return false; 176 | } 177 | if (ParamFieldConstants.CANCEL.equals(op)) { 178 | int opIndex = 4; 179 | preparedStatement.setString(opIndex, ParamFieldConstants.TRY); 180 | if (preparedStatement.executeUpdate() > 0) { 181 | return false; 182 | } 183 | } 184 | } finally { 185 | if (Objects.nonNull(preparedStatement)) { 186 | preparedStatement.close(); 187 | } 188 | } 189 | return true; 190 | } 191 | } 192 | -------------------------------------------------------------------------------- /dtmcli-core/src/main/java/pub/dtm/client/barrier/itfc/BarrierDBOperator.java: -------------------------------------------------------------------------------- 1 | package pub.dtm.client.barrier.itfc; 2 | 3 | /** 4 | * BarrierDBOperator is a interface to insert barrier, you can implements the interface according to your db. 5 | * 6 | * @author horseLk 7 | * @date 2022-09-28 22:02 8 | */ 9 | public interface BarrierDBOperator { 10 | /** 11 | * 12 | * @param transType Trans type 13 | * @param gid gid 14 | * @param branchId branch ID 15 | * @param op operator 16 | * @param barrierId barrier ID 17 | * @return Insert Success 18 | */ 19 | boolean insertBarrier(String transType, String gid, String branchId, String op, int barrierId) throws Exception; 20 | 21 | /** 22 | * commit transaction 23 | * @throws Exception 24 | */ 25 | void commit() throws Exception; 26 | 27 | /** 28 | * rollback transaction 29 | * @throws Exception 30 | */ 31 | void rollback() throws Exception; 32 | } 33 | -------------------------------------------------------------------------------- /dtmcli-core/src/main/java/pub/dtm/client/barrier/itfc/ConnectionCallback.java: -------------------------------------------------------------------------------- 1 | package pub.dtm.client.barrier.itfc; 2 | 3 | import java.sql.Connection; 4 | 5 | @FunctionalInterface 6 | public interface ConnectionCallback { 7 | 8 | R execute(Connection con) throws Exception; 9 | } 10 | -------------------------------------------------------------------------------- /dtmcli-core/src/main/java/pub/dtm/client/barrier/itfc/ConnectionManager.java: -------------------------------------------------------------------------------- 1 | package pub.dtm.client.barrier.itfc; 2 | 3 | import javax.sql.DataSource; 4 | import java.sql.Connection; 5 | 6 | /* 7 | * 1. If user want to use simple connection, uses this 8 | * 9 | * ``` 10 | * ConnectionManager.simpleConnectionManager(dataSource) 11 | * ``` 12 | * 13 | * 2. If user want to reuse the connection/transaction of spring, use this 14 | * 15 | * ``` 16 | * new ConnectionManager() { 17 | * @Override 18 | * public R execute(ConnectionCallback block) throws Exception { 19 | * Connection con = DataSourceUtils.getConnection(dataSource); 20 | * try { 21 | * return block.apply(con); 22 | * } finally { 23 | * DataSourceUtils.releaseConnection(con, dataSource); 24 | * } 25 | * } 26 | * } 27 | * ``` 28 | * 29 | * Please view 30 | * https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/jdbc/datasource/DataSourceUtils.html 31 | * to know more 32 | */ 33 | public interface ConnectionManager { 34 | 35 | R execute(ConnectionCallback block) throws Exception; 36 | 37 | static ConnectionManager simpleConnectionManager(DataSource dataSource) { 38 | return new ConnectionManager() { 39 | @Override 40 | public R execute(ConnectionCallback block) throws Exception { 41 | try (Connection con = dataSource.getConnection()) { 42 | return block.execute(con); 43 | } 44 | } 45 | }; 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /dtmcli-core/src/main/java/pub/dtm/client/barrier/itfc/impl/BarrierMysqlOperator.java: -------------------------------------------------------------------------------- 1 | package pub.dtm.client.barrier.itfc.impl; 2 | 3 | import pub.dtm.client.barrier.itfc.BarrierDBOperator; 4 | import pub.dtm.client.constant.ParamFieldConstants; 5 | 6 | import java.sql.Connection; 7 | import java.sql.PreparedStatement; 8 | import java.util.Objects; 9 | 10 | /** 11 | * BarrierDBOperator for MySQL 12 | * 13 | * @author horseLk 14 | * @date 2022-09-28 22:05 15 | */ 16 | public class BarrierMysqlOperator implements BarrierDBOperator { 17 | private Object connection; 18 | 19 | public BarrierMysqlOperator(Object connection) { 20 | this.connection = connection; 21 | } 22 | 23 | @Override 24 | public boolean insertBarrier(String transType, String gid, String branchId, String op, int barrierId) throws Exception { 25 | if (Objects.isNull(connection)) { 26 | return false; 27 | } 28 | Connection conn = (Connection)this.connection; 29 | conn.setAutoCommit(false); 30 | PreparedStatement preparedStatement = null; 31 | try { 32 | String sql = "insert ignore into barrier(trans_type, gid, branch_id, op, barrier_id, reason) values(?,?,?,?,?,?)"; 33 | preparedStatement = conn.prepareStatement(sql); 34 | preparedStatement.setString(1, transType); 35 | preparedStatement.setString(2, gid); 36 | preparedStatement.setString(3, branchId); 37 | preparedStatement.setString(4, op); 38 | preparedStatement.setString(5, String.format("%02d", barrierId)); 39 | preparedStatement.setString(6, op); 40 | 41 | if (preparedStatement.executeUpdate() == 0) { 42 | return false; 43 | } 44 | if (ParamFieldConstants.CANCEL.equals(op)) { 45 | int opIndex = 4; 46 | preparedStatement.setString(opIndex, ParamFieldConstants.TRY); 47 | if (preparedStatement.executeUpdate() > 0) { 48 | return false; 49 | } 50 | } 51 | } finally { 52 | if (Objects.nonNull(preparedStatement)) { 53 | preparedStatement.close(); 54 | } 55 | } 56 | return true; 57 | } 58 | 59 | @Override 60 | public void commit() throws Exception { 61 | if (Objects.isNull(connection)) { 62 | return; 63 | } 64 | Connection conn = (Connection)this.connection; 65 | conn.commit(); 66 | conn.setAutoCommit(true); 67 | } 68 | 69 | @Override 70 | public void rollback() throws Exception { 71 | if (Objects.isNull(connection)) { 72 | return; 73 | } 74 | Connection conn = (Connection)this.connection; 75 | conn.rollback(); 76 | conn.setAutoCommit(true); 77 | } 78 | } 79 | -------------------------------------------------------------------------------- /dtmcli-core/src/main/java/pub/dtm/client/base/BranchIdGenerator.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.base; 26 | 27 | /** 28 | * BranchIdGenerator for generate branch id 29 | * 30 | * @author horseLk 31 | */ 32 | public class BranchIdGenerator { 33 | private static final int MAX_BRANCH_ID = 99; 34 | 35 | private static final int LENGTH = 20; 36 | 37 | /** 38 | * branch id prefix 39 | */ 40 | private final String branchId; 41 | 42 | /** 43 | * last branch id 44 | */ 45 | private int subBranchId; 46 | 47 | public BranchIdGenerator(String branchId) { 48 | this.branchId = branchId; 49 | } 50 | 51 | /** 52 | * generate branch id 53 | * 54 | * @return branch id 55 | * @throws Exception exception 56 | */ 57 | public String genBranchId() throws Exception { 58 | if (this.subBranchId >= MAX_BRANCH_ID) { 59 | throw new Exception("branch id is larger than 99"); 60 | } 61 | if (this.branchId.length() >= LENGTH) { 62 | throw new Exception("total branch id is longer than 20"); 63 | } 64 | this.subBranchId++; 65 | return this.branchId + String.format("%02d", this.subBranchId); 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /dtmcli-core/src/main/java/pub/dtm/client/saga/Saga.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.saga; 26 | 27 | import lombok.Data; 28 | import lombok.NoArgsConstructor; 29 | import org.apache.commons.lang3.StringUtils; 30 | import org.slf4j.Logger; 31 | import org.slf4j.LoggerFactory; 32 | import pub.dtm.client.constant.ParamFieldConstants; 33 | import pub.dtm.client.enums.TransTypeEnum; 34 | import pub.dtm.client.exception.FailureException; 35 | import pub.dtm.client.interfaces.stub.IDtmServerStub; 36 | import pub.dtm.client.model.dtm.TransBase; 37 | import pub.dtm.client.model.feign.ServiceMessage; 38 | import pub.dtm.client.model.param.SagaOperatorParam; 39 | import pub.dtm.client.utils.FeignUtils; 40 | import pub.dtm.client.utils.JsonUtils; 41 | 42 | import java.util.ArrayList; 43 | import java.util.HashMap; 44 | import java.util.List; 45 | import java.util.Map; 46 | 47 | /** 48 | * Saga trans type service 49 | * 50 | * @author horseLk 51 | */ 52 | @Data 53 | @NoArgsConstructor 54 | public class Saga extends TransBase { 55 | private static final Logger log = LoggerFactory.getLogger(Saga.class); 56 | 57 | private static final String ORDERS = "orders"; 58 | 59 | private static final String CONCURRENT = "concurrent"; 60 | 61 | private IDtmServerStub dtmServerStub; 62 | 63 | private boolean concurrent; 64 | 65 | private Map> orders; 66 | 67 | private long timeoutToFail; 68 | 69 | private long retryInterval; 70 | 71 | private Map branchHeaders = new HashMap<>(); 72 | 73 | private List passthroughHeaders = new ArrayList<>(); 74 | 75 | private String customData; 76 | 77 | private List> steps = new ArrayList<>(); 78 | 79 | private List payloads = new ArrayList<>(); 80 | 81 | public Saga(String gid, IDtmServerStub dtmServerStub) { 82 | super(gid, TransTypeEnum.SAGA, false); 83 | this.concurrent = false; 84 | this.orders = new HashMap<>(); 85 | this.dtmServerStub = dtmServerStub; 86 | } 87 | 88 | public Saga add(ServiceMessage action, ServiceMessage compensate, Object postData) { 89 | Map step = new HashMap<>(); 90 | try { 91 | step.put(ParamFieldConstants.ACTION, FeignUtils.generatorURI(action, false)); 92 | step.put(ParamFieldConstants.COMPENSATE, FeignUtils.generatorURI(compensate, false)); 93 | this.payloads.add(JsonUtils.toJson(postData)); 94 | } catch (Exception e) { 95 | log.error("saga add branch error."); 96 | } 97 | this.steps.add(step); 98 | 99 | return this; 100 | } 101 | 102 | public Saga add(String action, String compensate, Object postData) { 103 | Map step = new HashMap<>(); 104 | step.put(ParamFieldConstants.ACTION, action); 105 | step.put(ParamFieldConstants.COMPENSATE, compensate); 106 | this.steps.add(step); 107 | try { 108 | this.payloads.add(JsonUtils.toJson(postData)); 109 | } catch (Exception e) { 110 | log.error("encode json error."); 111 | } 112 | return this; 113 | } 114 | 115 | public String submit() throws Exception { 116 | if (StringUtils.isEmpty(this.getGid())) { 117 | this.setGid(FeignUtils.parseGid(dtmServerStub.newGid())); 118 | } 119 | addConcurrentContext(); 120 | SagaOperatorParam operatorParam = new SagaOperatorParam(this.getGid(), TransTypeEnum.SAGA, this.getSteps(), 121 | this.getPayloads(), this.getCustomData(), this.isWaitResult(), this.getTimeoutToFail(), 122 | this.getRetryInterval(), this.getPassthroughHeaders(), this.getBranchHeaders()); 123 | 124 | try { 125 | dtmServerStub.submit(operatorParam); 126 | } catch (Exception e) { 127 | log.error("saga transaction submit failed, transaction gid is {}", this.getGid()); 128 | throw new FailureException(e); 129 | } 130 | return this.getGid(); 131 | } 132 | 133 | public Saga addBranchOrder(Integer branch, List preBranches) { 134 | orders.put(branch.toString(), preBranches); 135 | return this; 136 | } 137 | 138 | public Saga enableConcurrent() { 139 | concurrent = true; 140 | return this; 141 | } 142 | 143 | public Saga enableWaitResult() { 144 | this.setWaitResult(true); 145 | return this; 146 | } 147 | 148 | public Saga setTimeoutToFail(long timeoutToFail) { 149 | this.timeoutToFail = timeoutToFail; 150 | return this; 151 | } 152 | 153 | public Saga setRetryInterval(long retryInterval) { 154 | this.retryInterval = retryInterval; 155 | return this; 156 | } 157 | 158 | public Saga setBranchHeaders(Map branchHeaders) { 159 | this.branchHeaders = branchHeaders; 160 | return this; 161 | } 162 | 163 | public Saga setPassthroughHeaders(ArrayList passthroughHeaders) { 164 | this.passthroughHeaders = passthroughHeaders; 165 | return this; 166 | } 167 | 168 | private void addConcurrentContext() { 169 | if (concurrent) { 170 | HashMap data = new HashMap<>(); 171 | data.put(ORDERS, orders); 172 | data.put(CONCURRENT, true); 173 | try { 174 | this.customData = JsonUtils.toJson(data); 175 | } catch (Exception e) { 176 | log.error("encode json error."); 177 | } 178 | } 179 | } 180 | } 181 | -------------------------------------------------------------------------------- /dtmcli-core/src/main/java/pub/dtm/client/tcc/Tcc.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.tcc; 26 | 27 | import lombok.NoArgsConstructor; 28 | import pub.dtm.client.base.BranchIdGenerator; 29 | import pub.dtm.client.constant.Constants; 30 | import pub.dtm.client.constant.ParamFieldConstants; 31 | import pub.dtm.client.enums.TransTypeEnum; 32 | import pub.dtm.client.exception.FailureException; 33 | import pub.dtm.client.interfaces.stub.IDtmServerStub; 34 | import pub.dtm.client.interfaces.dtm.DtmConsumer; 35 | import pub.dtm.client.model.dtm.TransBase; 36 | import pub.dtm.client.model.feign.ServiceMessage; 37 | import okhttp3.Response; 38 | import org.apache.commons.lang3.StringUtils; 39 | import org.slf4j.Logger; 40 | import org.slf4j.LoggerFactory; 41 | import pub.dtm.client.model.param.OperatorParam; 42 | import pub.dtm.client.model.param.TccOperatorParam; 43 | import pub.dtm.client.model.responses.DtmResponse; 44 | import pub.dtm.client.utils.FeignUtils; 45 | import pub.dtm.client.utils.HttpUtils; 46 | import pub.dtm.client.utils.JsonUtils; 47 | 48 | import java.net.URI; 49 | import java.util.HashMap; 50 | import java.util.Map; 51 | 52 | /** 53 | * Tcc trans type service 54 | * 55 | * @author horseLk 56 | */ 57 | @NoArgsConstructor 58 | public class Tcc extends TransBase { 59 | private static final Logger log = LoggerFactory.getLogger(Tcc.class); 60 | 61 | private static final String OP = "try"; 62 | 63 | /** 64 | * branch id generator 65 | */ 66 | private BranchIdGenerator branchIdGenerator; 67 | 68 | /** 69 | * feign client 70 | */ 71 | private IDtmServerStub dtmServerStub; 72 | 73 | public Tcc(String gid, IDtmServerStub dtmServerStub) { 74 | super(gid, TransTypeEnum.TCC, false); 75 | this.branchIdGenerator = new BranchIdGenerator(Constants.EMPTY_STRING); 76 | this.dtmServerStub = dtmServerStub; 77 | } 78 | 79 | public void setDtmServerStub(IDtmServerStub dtmServerStub) { 80 | this.dtmServerStub = dtmServerStub; 81 | } 82 | 83 | /** 84 | * start a tcc distribute transaction 85 | * @param consumer consumer 86 | * @return gid 87 | * @throws Exception exception 88 | */ 89 | public String tccGlobalTransaction(DtmConsumer consumer) throws Exception { 90 | // if tcc's gid is empty, need to request a new gid from dtm svr 91 | if (StringUtils.isEmpty(this.getGid())) { 92 | this.setGid(FeignUtils.parseGid(dtmServerStub.newGid())); 93 | } 94 | log.info("the tcc transaction's gid is {}", this.getGid()); 95 | 96 | OperatorParam operatorParam = new OperatorParam(this.getGid(), TransTypeEnum.TCC); 97 | DtmResponse resp = dtmServerStub.prepare(operatorParam); 98 | log.info("prepare response: {}", resp); 99 | if (!Constants.SUCCESS_RESULT.equals(resp.getDtmResult())) { 100 | log.error("TCC transaction prepare fail. returned dtm_result is: {}, transaction gid: {}", resp.getDtmResult(), this.getGid()); 101 | throw new FailureException("TCC Transaction prepare fail"); 102 | } 103 | try { 104 | consumer.accept(this); 105 | dtmServerStub.submit(operatorParam); 106 | } catch (Exception e) { 107 | log.error("TCC transaction submit fail, start abort it. transaction gid: {}", this.getGid()); 108 | dtmServerStub.abort(operatorParam); 109 | throw new FailureException(e); 110 | } 111 | return this.getGid(); 112 | } 113 | 114 | /** 115 | * busi can call method callBranch() to set tcc transaction's branch. 116 | * the callBranch for micro service driver 117 | * @param body busi body 118 | * @param tryMessage service message of try operator 119 | * @param confirmMessage service message of confirm operator 120 | * @param cancelMessage service message of cancel operator 121 | * @return feign response 122 | * @throws Exception exception 123 | */ 124 | public feign.Response callBranch(Object body, ServiceMessage tryMessage, ServiceMessage confirmMessage, ServiceMessage cancelMessage) throws Exception { 125 | log.info("call method Tcc.callBranch, tryMessage: {}, confirmMessage: {}, cancelMessage: {}", 126 | JsonUtils.toJson(tryMessage), JsonUtils.toJson(confirmMessage), JsonUtils.toJson(cancelMessage)); 127 | String branchId = this.branchIdGenerator.genBranchId(); 128 | 129 | TccOperatorParam operatorParam = new TccOperatorParam(this.getGid(), TransTypeEnum.TCC, branchId, Constants.DEFAULT_STATUS, 130 | JsonUtils.toJson(body), FeignUtils.generatorURI(confirmMessage, false), FeignUtils.generatorURI(cancelMessage, false)); 131 | DtmResponse resp = dtmServerStub.registerBranch(operatorParam); 132 | if (!Constants.SUCCESS_RESULT.equals(resp.getDtmResult())) { 133 | log.error("TCC transaction register branch fail. transaction gid: {}", this.getGid()); 134 | throw new FailureException("TCC Transaction register branch fail"); 135 | } 136 | 137 | Map paramsMap = new HashMap<>(); 138 | paramsMap.put(ParamFieldConstants.GID, this.getGid()); 139 | paramsMap.put(ParamFieldConstants.TRANS_TYPE, TransTypeEnum.TCC.getValue()); 140 | paramsMap.put(ParamFieldConstants.BRANCH_ID, branchId); 141 | paramsMap.put(ParamFieldConstants.OP, OP); 142 | 143 | feign.Response response = dtmServerStub.busiPost(new URI(FeignUtils.generatorURI(tryMessage, true)), 144 | tryMessage.getPath(), paramsMap, body); 145 | log.info("busi post is: {}", response); 146 | FeignUtils.checkResult(response); 147 | return response; 148 | } 149 | 150 | /** 151 | * busi can call method callBranch() to set tcc transaction's branch. 152 | * the callBranch for http driver 153 | * @param body busi body 154 | * @param tryUrl http url of try operator 155 | * @param confirmUrl http url of confirm operator 156 | * @param cancelUrl http url of cancel operator 157 | * @return http response 158 | * @throws Exception exception 159 | */ 160 | public Response callBranch(Object body, String tryUrl, String confirmUrl, String cancelUrl) throws Exception { 161 | log.info("call method Tcc.callBranch, tryUrl: {}, confirmUrl: {}, cancelUrl: {}", tryUrl, confirmUrl, cancelUrl); 162 | String branchId = this.branchIdGenerator.genBranchId(); 163 | 164 | TccOperatorParam operatorParam = new TccOperatorParam(this.getGid(), TransTypeEnum.TCC, branchId, Constants.DEFAULT_STATUS, 165 | JsonUtils.toJson(body), confirmUrl, cancelUrl); 166 | DtmResponse resp = dtmServerStub.registerBranch(operatorParam); 167 | if (!Constants.SUCCESS_RESULT.equals(resp.getDtmResult())) { 168 | log.error("TCC transaction register branch fail. transaction gid: {}", this.getGid()); 169 | throw new FailureException("TCC Transaction register branch fail"); 170 | } 171 | 172 | Map paramsMap = new HashMap<>(); 173 | paramsMap.put(ParamFieldConstants.GID, this.getGid()); 174 | paramsMap.put(ParamFieldConstants.TRANS_TYPE, TransTypeEnum.TCC.getValue()); 175 | paramsMap.put(ParamFieldConstants.BRANCH_ID, branchId); 176 | paramsMap.put(ParamFieldConstants.OP, OP); 177 | Response tryResponse = HttpUtils.post(HttpUtils.splicingUrl(tryUrl, paramsMap), JsonUtils.toJson(body)); 178 | log.info("try response is: {}", tryResponse); 179 | HttpUtils.checkResult(tryResponse); 180 | return tryResponse; 181 | } 182 | } 183 | -------------------------------------------------------------------------------- /dtmcli-java/pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | dtmcli-java-parent 7 | io.github.dtm-labs 8 | 2.1.5 9 | 10 | 4.0.0 11 | 12 | dtmcli-java 13 | 2.1.8 14 | jar 15 | dtmcli-java 16 | 17 | 18 | UTF-8 19 | 1.8 20 | 1.8 21 | 22 | 23 | 24 | 25 | io.github.dtm-labs 26 | dtmcli-common 27 | 2.1.8 28 | 29 | 30 | 31 | io.github.dtm-labs 32 | dtmcli-core 33 | 2.1.8 34 | 35 | 36 | 37 | com.alibaba.nacos 38 | nacos-client 39 | 40 | 41 | 42 | io.github.openfeign 43 | feign-jackson 44 | 45 | 46 | 47 | 48 | -------------------------------------------------------------------------------- /dtmcli-java/src/main/java/pub/dtm/client/DtmClient.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client; 26 | 27 | import com.alibaba.nacos.api.naming.pojo.Instance; 28 | import feign.jackson.JacksonDecoder; 29 | import feign.jackson.JacksonEncoder; 30 | import pub.dtm.client.constant.Constants; 31 | import pub.dtm.client.stub.DtmFeignClient; 32 | import feign.Feign; 33 | import pub.dtm.client.stub.URIParser; 34 | import pub.dtm.client.interfaces.dtm.DtmConsumer; 35 | import pub.dtm.client.interfaces.stub.IDtmServerStub; 36 | import org.apache.commons.lang3.StringUtils; 37 | import org.slf4j.Logger; 38 | import org.slf4j.LoggerFactory; 39 | import pub.dtm.client.properties.DtmProperties; 40 | import pub.dtm.client.saga.Saga; 41 | import pub.dtm.client.tcc.Tcc; 42 | import pub.dtm.client.utils.NacosUtils; 43 | 44 | import java.util.ArrayList; 45 | import java.util.Arrays; 46 | import java.util.List; 47 | 48 | import static com.alibaba.nacos.api.common.Constants.DEFAULT_CLUSTER_NAME; 49 | import static com.alibaba.nacos.api.common.Constants.DEFAULT_GROUP; 50 | import static com.alibaba.nacos.api.naming.CommonParams.CLUSTER_NAME; 51 | import static com.alibaba.nacos.api.naming.CommonParams.GROUP_NAME; 52 | 53 | public class DtmClient { 54 | private static final Logger log = LoggerFactory.getLogger(DtmClient.class); 55 | 56 | private final IDtmServerStub dtmServerStub; 57 | 58 | public DtmClient() { 59 | // init URIParser 60 | new URIParser(); 61 | 62 | String endpoint = null; 63 | try { 64 | // redirect connect to dtm 65 | endpoint = DtmProperties.get("dtm.ipport"); 66 | // connect to dtm by nacos 67 | if (StringUtils.isEmpty(endpoint)) { 68 | Instance instance = NacosUtils.selectOneHealthyInstance(DtmProperties.get(Constants.MICRO_SERVICE_NAME_KEY), 69 | DtmProperties.getOrDefault(GROUP_NAME, DEFAULT_GROUP), genClusters(DtmProperties.get(CLUSTER_NAME))); 70 | endpoint = instance.toInetAddr(); 71 | } 72 | } catch (Exception e) { 73 | log.error("initial dtm client for java error.", e); 74 | System.exit(-1); 75 | } 76 | if (StringUtils.isEmpty(endpoint)) { 77 | log.error("can not resolve dtm server message from config file, you can use nacos or redirect configure to config it."); 78 | System.exit(-1); 79 | } 80 | IDtmServerStub feignClient = Feign 81 | .builder() 82 | .decoder(new JacksonDecoder()) 83 | .encoder(new JacksonEncoder()) 84 | // if you need read detail log of feign, please cancel the note. 85 | // .logLevel(feign.Logger.Level.FULL) 86 | // .logger(new DtmFeignLogger()) 87 | .target(DtmFeignClient.class, Constants.HTTP_PREFIX + endpoint); 88 | if (feignClient == null) { 89 | log.error("initial dtm client for java error, feign client can't be null."); 90 | System.exit(-1); 91 | } 92 | 93 | this.dtmServerStub = feignClient; 94 | } 95 | 96 | public DtmClient(String endpoint) { 97 | // init URIParser 98 | new URIParser(); 99 | 100 | if (StringUtils.isEmpty(endpoint)) { 101 | log.error("dtm server endpoint can not be empty."); 102 | System.exit(-1); 103 | } 104 | IDtmServerStub feignClient = Feign 105 | .builder() 106 | .decoder(new JacksonDecoder()) 107 | .encoder(new JacksonEncoder()) 108 | // if you need read detail log of feign, please cancel the note. 109 | // .logLevel(feign.Logger.Level.FULL) 110 | // .logger(new DtmFeignLogger()) 111 | .target(DtmFeignClient.class, Constants.HTTP_PREFIX + endpoint); 112 | 113 | if (feignClient == null) { 114 | log.error("initial dtm client for java error, feign client can't be null."); 115 | System.exit(-1); 116 | } 117 | 118 | this.dtmServerStub = feignClient; 119 | } 120 | 121 | public DtmClient(IDtmServerStub dtmServerStub) { 122 | this.dtmServerStub = dtmServerStub; 123 | } 124 | 125 | private List genClusters(String clusterStr) { 126 | if (StringUtils.isEmpty(clusterStr)) { 127 | List clusters = new ArrayList<>(); 128 | clusters.add(DEFAULT_CLUSTER_NAME); 129 | return clusters; 130 | } 131 | String[] split = StringUtils.split(clusterStr, ","); 132 | return Arrays.asList(split); 133 | } 134 | 135 | /** 136 | * start a tcc transaction without gid, client send a request to dtm svr for obtain a new gid. 137 | * @param function consumer 138 | * @return gid 139 | * @throws Exception exception 140 | */ 141 | public String tccGlobalTransaction(DtmConsumer function) throws Exception { 142 | Tcc tcc = new Tcc(null, dtmServerStub); 143 | return tcc.tccGlobalTransaction(function); 144 | } 145 | 146 | /** 147 | * start a tcc transaction with a custom gid. 148 | * @param gid gid 149 | * @param function consumer 150 | * @return gid 151 | * @throws Exception exception 152 | */ 153 | public String tccGlobalTransaction(String gid, DtmConsumer function) throws Exception { 154 | Tcc tcc = new Tcc(gid, dtmServerStub); 155 | return tcc.tccGlobalTransaction(function); 156 | } 157 | 158 | /** 159 | * start a saga transaction with custom gid 160 | * @param gid gid 161 | * @return Saga 162 | */ 163 | public Saga newSaga(String gid) { 164 | return new Saga(gid, dtmServerStub); 165 | } 166 | 167 | /** 168 | * start a saga transaction without gid, client send a request to dtm svr for obtain a new gid. 169 | * @return Saga 170 | */ 171 | public Saga newSaga() { 172 | return new Saga(null, dtmServerStub); 173 | } 174 | } 175 | -------------------------------------------------------------------------------- /dtmcli-java/src/main/java/pub/dtm/client/properties/DtmProperties.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.properties; 26 | 27 | import java.io.FileInputStream; 28 | import java.io.IOException; 29 | import java.util.Properties; 30 | 31 | 32 | /** 33 | * Load properties of dtm server 34 | * 35 | * @author horse 36 | */ 37 | public class DtmProperties { 38 | private static Properties dtmProperties; 39 | 40 | private static void loadNacosProperties() throws IOException { 41 | Properties properties = new Properties(); 42 | FileInputStream in = new FileInputStream(DtmProperties.class.getResource("/dtm-conf.properties").getPath()); 43 | properties.load(in); 44 | dtmProperties = properties; 45 | } 46 | 47 | public static String get(String key) throws IOException { 48 | if (dtmProperties == null) { 49 | loadNacosProperties(); 50 | } 51 | return dtmProperties.getProperty(key); 52 | } 53 | 54 | public static String getOrDefault(String key, String defaultValue) throws IOException { 55 | if (dtmProperties == null) { 56 | loadNacosProperties(); 57 | } 58 | return dtmProperties.getProperty(key, defaultValue); 59 | } 60 | 61 | public static Properties getNacosProperties() throws IOException { 62 | if (dtmProperties == null) { 63 | loadNacosProperties(); 64 | } 65 | return dtmProperties; 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /dtmcli-java/src/main/java/pub/dtm/client/stub/DtmFeignClient.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.stub; 26 | 27 | import feign.Headers; 28 | import feign.Param; 29 | import feign.QueryMap; 30 | import feign.RequestLine; 31 | import feign.Response; 32 | import pub.dtm.client.constant.Constants; 33 | import pub.dtm.client.interfaces.stub.IDtmServerStub; 34 | import pub.dtm.client.model.param.OperatorParam; 35 | import pub.dtm.client.model.responses.DtmResponse; 36 | 37 | import java.net.URI; 38 | import java.util.Map; 39 | 40 | /** 41 | * IDtmServerStub implements for open-feign 42 | * 43 | * @author horse 44 | */ 45 | @Headers("Content-Type: application/json") 46 | public interface DtmFeignClient extends IDtmServerStub { 47 | @Override 48 | default String stubType() { 49 | return "open-feign"; 50 | } 51 | 52 | @Override 53 | @RequestLine(Constants.GET_METHOD + Constants.NEW_GID_URL) 54 | DtmResponse newGid(); 55 | 56 | @Override 57 | @RequestLine(Constants.GET_METHOD + Constants.PING_URL) 58 | DtmResponse ping(); 59 | 60 | @Override 61 | @RequestLine(Constants.POST_METHOD + Constants.PREPARE_URL) 62 | DtmResponse prepare(OperatorParam body); 63 | 64 | @Override 65 | @RequestLine(Constants.POST_METHOD + Constants.SUBMIT_URL) 66 | DtmResponse submit(OperatorParam body); 67 | 68 | @Override 69 | @RequestLine(Constants.POST_METHOD + Constants.ABORT_URL) 70 | DtmResponse abort(OperatorParam body); 71 | 72 | @Override 73 | @RequestLine(Constants.POST_METHOD + Constants.REGISTER_BRANCH_URL) 74 | DtmResponse registerBranch(OperatorParam body); 75 | 76 | @Override 77 | @RequestLine(Constants.GET_METHOD + "{path}") 78 | Response busiGet(URI host, @Param("path") String path, @QueryMap Map queryMap); 79 | 80 | @Override 81 | @RequestLine(Constants.POST_METHOD + "{path}") 82 | Response busiPost(URI host, @Param("path") String path, @QueryMap Map queryMap, Object body); 83 | } 84 | -------------------------------------------------------------------------------- /dtmcli-java/src/main/java/pub/dtm/client/stub/URIParser.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.stub; 26 | 27 | import com.alibaba.nacos.api.naming.pojo.Instance; 28 | import pub.dtm.client.constant.Constants; 29 | import pub.dtm.client.interfaces.stub.IURIParser; 30 | import pub.dtm.client.model.feign.ServiceMessage; 31 | import pub.dtm.client.properties.DtmProperties; 32 | import pub.dtm.client.utils.FeignUtils; 33 | import pub.dtm.client.utils.NacosUtils; 34 | 35 | /** 36 | * Parse url to dtm server for java client. 37 | * 38 | * @author horse 39 | */ 40 | public class URIParser implements IURIParser { 41 | static { 42 | FeignUtils.setUriParser(new URIParser()); 43 | } 44 | 45 | @Override 46 | public String generatorURI(ServiceMessage serviceMessage, boolean httpType) throws Exception { 47 | if (httpType) { 48 | Instance instance = NacosUtils.selectOneHealthyInstance(serviceMessage.getServiceName(), 49 | serviceMessage.getGroupName(), serviceMessage.getCluster()); 50 | return Constants.HTTP_PREFIX + instance.toInetAddr(); 51 | } 52 | return DtmProperties.get("dtm.service.registryType") + "://" + serviceMessage.toString(); 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /dtmcli-java/src/main/java/pub/dtm/client/utils/NacosUtils.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.utils; 26 | 27 | import com.alibaba.nacos.api.naming.NamingFactory; 28 | import com.alibaba.nacos.api.naming.NamingService; 29 | import com.alibaba.nacos.api.naming.pojo.Instance; 30 | import pub.dtm.client.properties.DtmProperties; 31 | 32 | import java.util.List; 33 | 34 | /** 35 | * Nacos utils 36 | * 37 | * @author horse 38 | */ 39 | public class NacosUtils { 40 | private static NamingService namingService; 41 | 42 | public static void buildNamingService() throws Exception { 43 | NacosUtils.namingService = NamingFactory.createNamingService(DtmProperties.getNacosProperties()); 44 | } 45 | 46 | public static Instance selectOneHealthyInstance(String serviceName, String groupName, List cluster) throws Exception { 47 | if (namingService == null) { 48 | buildNamingService(); 49 | } 50 | return namingService.selectOneHealthyInstance(serviceName, groupName, cluster); 51 | } 52 | } 53 | -------------------------------------------------------------------------------- /dtmcli-springcloud/pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | dtmcli-java-parent 7 | io.github.dtm-labs 8 | 2.1.5 9 | 10 | 4.0.0 11 | 12 | dtmcli-springcloud 13 | 2.1.8.2 14 | jar 15 | dtmcli-springcloud 16 | 17 | 18 | UTF-8 19 | 1.8 20 | 1.8 21 | 22 | 2020.0.5 23 | 2.4.8 24 | 2021.1 25 | 26 | 27 | 28 | 29 | io.github.dtm-labs 30 | dtmcli-common 31 | 2.1.8 32 | 33 | 34 | 35 | io.github.dtm-labs 36 | dtmcli-core 37 | 2.1.8 38 | 39 | 40 | 41 | org.springframework.boot 42 | spring-boot-starter 43 | ${springboot.version} 44 | 45 | 46 | 47 | org.springframework.boot 48 | spring-boot-configuration-processor 49 | ${springboot.version} 50 | true 51 | 52 | 53 | 54 | org.springframework.cloud 55 | spring-cloud-starter-openfeign 56 | 57 | 58 | 59 | 60 | 61 | 62 | org.springframework.cloud 63 | spring-cloud-dependencies 64 | ${spring-cloud.version} 65 | pom 66 | import 67 | 68 | 69 | 70 | 71 | -------------------------------------------------------------------------------- /dtmcli-springcloud/src/main/java/pub/dtm/client/DtmClient.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client; 26 | 27 | import org.springframework.beans.factory.annotation.Autowired; 28 | import org.springframework.stereotype.Component; 29 | import pub.dtm.client.interfaces.stub.IDtmServerStub; 30 | import pub.dtm.client.interfaces.dtm.DtmConsumer; 31 | import pub.dtm.client.saga.Saga; 32 | import pub.dtm.client.tcc.Tcc; 33 | 34 | /** 35 | * dtm client for spring 36 | * 37 | * @author horseLk 38 | */ 39 | @Component 40 | public class DtmClient { 41 | @Autowired 42 | private IDtmServerStub dtmServerStub; 43 | 44 | /** 45 | * start a tcc transaction without gid, client send a request to dtm svr for obtain a new gid. 46 | * @return gid 47 | */ 48 | public String tccGlobalTransaction(DtmConsumer function) throws Exception { 49 | Tcc tcc = new Tcc(null, dtmServerStub); 50 | return tcc.tccGlobalTransaction(function); 51 | } 52 | 53 | /** 54 | * start a tcc transaction with custom gid 55 | * @param gid gid 56 | * @return gid 57 | */ 58 | public String tccGlobalTransaction(String gid, DtmConsumer function) throws Exception { 59 | Tcc tcc = new Tcc(gid, dtmServerStub); 60 | return tcc.tccGlobalTransaction(function); 61 | } 62 | 63 | /** 64 | * start a saga transaction with custom gid 65 | * @param gid gid 66 | * @return Saga 67 | */ 68 | public Saga newSaga(String gid) { 69 | return new Saga(gid, dtmServerStub); 70 | } 71 | 72 | /** 73 | * start a saga transaction without gid, client send a request to dtm svr for obtain a new gid. 74 | * @return Saga 75 | */ 76 | public Saga newSaga() { 77 | return new Saga(null, dtmServerStub); 78 | } 79 | } 80 | -------------------------------------------------------------------------------- /dtmcli-springcloud/src/main/java/pub/dtm/client/configuration/DtmConfiguration.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.configuration; 26 | 27 | import pub.dtm.client.stub.URIParser; 28 | import pub.dtm.client.properties.DtmProperties; 29 | import org.springframework.beans.factory.annotation.Autowired; 30 | import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean; 31 | import org.springframework.boot.context.properties.EnableConfigurationProperties; 32 | import org.springframework.cloud.openfeign.EnableFeignClients; 33 | import org.springframework.context.annotation.Bean; 34 | import org.springframework.context.annotation.ComponentScan; 35 | import org.springframework.context.annotation.Configuration; 36 | import org.springframework.stereotype.Component; 37 | 38 | /** 39 | * Dtm client configuration 40 | * 41 | * @author horse 42 | */ 43 | @Component 44 | @ComponentScan({"pub.dtm.client"}) 45 | @Configuration 46 | @EnableFeignClients("pub.dtm.client.stub") 47 | @EnableConfigurationProperties(DtmProperties.class) 48 | public class DtmConfiguration { 49 | @Autowired 50 | private DtmProperties dtmProperties; 51 | 52 | @Bean 53 | @ConditionalOnMissingBean(URIParser.class) 54 | public URIParser uriParser() { 55 | URIParser.setRegistryType(dtmProperties.getRegistryType()); 56 | return new URIParser(); 57 | } 58 | 59 | /** 60 | * if you need read detail log, please cancel note. 61 | */ 62 | // @Bean 63 | // Logger.Level feignLoggerLevel() { 64 | // return Logger.Level.FULL; 65 | // } 66 | // 67 | // @Bean 68 | // Logger feignLogger() { 69 | // return new DtmFeignLogger(); 70 | // } 71 | 72 | } 73 | -------------------------------------------------------------------------------- /dtmcli-springcloud/src/main/java/pub/dtm/client/properties/DtmProperties.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.properties; 26 | 27 | import lombok.Data; 28 | import org.springframework.boot.context.properties.ConfigurationProperties; 29 | 30 | /** 31 | * Load properties of dtm server 32 | * 33 | * @author horse 34 | */ 35 | @ConfigurationProperties(prefix = DtmProperties.PREFIX) 36 | @Data 37 | public class DtmProperties { 38 | public static final String PREFIX = "dtm.service"; 39 | 40 | private String registryType; 41 | 42 | private String name; 43 | 44 | } 45 | -------------------------------------------------------------------------------- /dtmcli-springcloud/src/main/java/pub/dtm/client/stub/DtmFeignClient.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.stub; 26 | 27 | import feign.Response; 28 | import org.springframework.cloud.openfeign.FeignClient; 29 | import org.springframework.cloud.openfeign.SpringQueryMap; 30 | import org.springframework.http.MediaType; 31 | import org.springframework.web.bind.annotation.GetMapping; 32 | import org.springframework.web.bind.annotation.PathVariable; 33 | import org.springframework.web.bind.annotation.PostMapping; 34 | import org.springframework.web.bind.annotation.RequestBody; 35 | import pub.dtm.client.constant.Constants; 36 | import pub.dtm.client.interfaces.stub.IDtmServerStub; 37 | import pub.dtm.client.model.param.OperatorParam; 38 | import pub.dtm.client.model.responses.DtmResponse; 39 | 40 | import java.net.URI; 41 | import java.util.Map; 42 | 43 | /** 44 | * IdtmServerStub implements for feign-spring 45 | * 46 | * @author horseLk 47 | */ 48 | @FeignClient(value = "${dtm.service.name}") 49 | public interface DtmFeignClient extends IDtmServerStub { 50 | @Override 51 | default String stubType() { 52 | return "feign-spring"; 53 | } 54 | 55 | @Override 56 | @GetMapping(Constants.NEW_GID_URL) 57 | DtmResponse newGid(); 58 | 59 | @Override 60 | @GetMapping(Constants.PING_URL) 61 | DtmResponse ping(); 62 | 63 | @Override 64 | @PostMapping(Constants.PREPARE_URL) 65 | DtmResponse prepare(@RequestBody OperatorParam body); 66 | 67 | @Override 68 | @PostMapping(Constants.SUBMIT_URL) 69 | DtmResponse submit(@RequestBody OperatorParam body); 70 | 71 | @Override 72 | @PostMapping(Constants.ABORT_URL) 73 | DtmResponse abort(@RequestBody OperatorParam body); 74 | 75 | @Override 76 | @PostMapping(Constants.REGISTER_BRANCH_URL) 77 | DtmResponse registerBranch(@RequestBody OperatorParam body); 78 | 79 | @Override 80 | @GetMapping(value = "{path}", consumes = MediaType.APPLICATION_JSON_VALUE, produces = MediaType.APPLICATION_JSON_VALUE) 81 | Response busiGet(URI host, @PathVariable("path") String path, @SpringQueryMap Map queryMap); 82 | 83 | @Override 84 | @PostMapping(value = "{path}", consumes = MediaType.APPLICATION_JSON_VALUE, produces = MediaType.APPLICATION_JSON_VALUE) 85 | Response busiPost(URI host, @PathVariable("path") String path, @SpringQueryMap Map queryMap, @RequestBody Object body); 86 | } 87 | -------------------------------------------------------------------------------- /dtmcli-springcloud/src/main/java/pub/dtm/client/stub/URIParser.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.stub; 26 | 27 | import pub.dtm.client.constant.Constants; 28 | import pub.dtm.client.interfaces.stub.IURIParser; 29 | import pub.dtm.client.model.feign.ServiceMessage; 30 | import pub.dtm.client.utils.FeignUtils; 31 | 32 | /** 33 | * Parse url to dtm server for spring cloud client. 34 | * 35 | * @author horse 36 | */ 37 | public class URIParser implements IURIParser { 38 | static { 39 | FeignUtils.setUriParser(new URIParser()); 40 | } 41 | 42 | private static String registryType; 43 | 44 | public static void setRegistryType(String registryType) { 45 | URIParser.registryType = registryType; 46 | } 47 | 48 | @Override 49 | public String generatorURI(ServiceMessage serviceMessage, boolean httpType) throws Exception { 50 | if (httpType) { 51 | return Constants.HTTP_PREFIX + serviceMessage.getServiceName(); 52 | } 53 | return registryType + "://" + serviceMessage.toString(); 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /dtmcli-springcloud/src/main/resources/META-INF/spring.factories: -------------------------------------------------------------------------------- 1 | org.springframework.boot.autoconfigure.EnableAutoConfiguration=pub.dtm.client.configuration.DtmConfiguration -------------------------------------------------------------------------------- /eureka-plugin/pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | dtmcli-java-parent 7 | io.github.dtm-labs 8 | 2.1.5 9 | 10 | 4.0.0 11 | 12 | eureka-plugin 13 | 2.1.8.2 14 | jar 15 | eureka-plugin 16 | 17 | 18 | UTF-8 19 | 1.8 20 | 1.8 21 | 22 | 2020.0.5 23 | 2.4.8 24 | 25 | 26 | 27 | 28 | org.springframework.boot 29 | spring-boot-starter 30 | ${springboot.version} 31 | 32 | 33 | 34 | org.springframework.boot 35 | spring-boot-configuration-processor 36 | ${springboot.version} 37 | true 38 | 39 | 40 | 41 | 42 | org.springframework.cloud 43 | spring-cloud-starter-netflix-eureka-client 44 | 45 | 46 | 47 | 48 | 49 | 50 | org.springframework.cloud 51 | spring-cloud-dependencies 52 | ${spring-cloud.version} 53 | pom 54 | import 55 | 56 | 57 | 58 | -------------------------------------------------------------------------------- /eureka-plugin/src/main/java/pub/dtm/client/configuration/EurekaConfiguration.java: -------------------------------------------------------------------------------- 1 | /* 2 | * MIT License 3 | * 4 | * Copyright (c) 2022 dtm-labs 5 | * 6 | * Permission is hereby granted, free of charge, to any person obtaining a copy 7 | * of this software and associated documentation files (the "Software"), to deal 8 | * in the Software without restriction, including without limitation the rights 9 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | * copies of the Software, and to permit persons to whom the Software is 11 | * furnished to do so, subject to the following conditions: 12 | * 13 | * The above copyright notice and this permission notice shall be included in all 14 | * copies or substantial portions of the Software. 15 | * 16 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 | * SOFTWARE. 23 | */ 24 | 25 | package pub.dtm.client.configuration; 26 | 27 | import org.springframework.cloud.netflix.eureka.EnableEurekaClient; 28 | 29 | /** 30 | * Eureka configuration 31 | * 32 | * @author horseLk 33 | */ 34 | @EnableEurekaClient 35 | public class EurekaConfiguration { 36 | } 37 | -------------------------------------------------------------------------------- /eureka-plugin/src/main/resources/META-INF/spring.factories: -------------------------------------------------------------------------------- 1 | org.springframework.boot.autoconfigure.EnableAutoConfiguration=pub.dtm.client.configuration.EurekaConfiguration -------------------------------------------------------------------------------- /nacos-plugin/pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | dtmcli-java-parent 7 | io.github.dtm-labs 8 | 2.1.5 9 | 10 | 4.0.0 11 | 12 | nacos-plugin 13 | 2.1.8.2 14 | jar 15 | nacos-plugin 16 | 17 | 18 | UTF-8 19 | 1.8 20 | 1.8 21 | 22 | 2020.0.5 23 | 2021.1 24 | 25 | 26 | 27 | 28 | com.alibaba.cloud 29 | spring-cloud-starter-alibaba-nacos-discovery 30 | 31 | 32 | 33 | org.springframework.cloud 34 | spring-cloud-starter-netflix-ribbon 35 | 36 | 37 | com.netflix.ribbon 38 | ribbon 39 | 40 | 41 | 42 | 43 | 44 | org.springframework.cloud 45 | spring-cloud-loadbalancer 46 | 47 | 48 | 49 | 50 | 51 | 52 | org.springframework.cloud 53 | spring-cloud-dependencies 54 | ${spring-cloud.version} 55 | pom 56 | import 57 | 58 | 59 | 60 | com.alibaba.cloud 61 | spring-cloud-alibaba-dependencies 62 | ${alibaba-cloud.version} 63 | pom 64 | import 65 | 66 | 67 | 68 | -------------------------------------------------------------------------------- /pic_ref/newversion.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dtm-labs/dtmcli-java/a6e2670ec0abda5ae7b117003b0451431dd62e03/pic_ref/newversion.png -------------------------------------------------------------------------------- /pic_ref/oldversion.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dtm-labs/dtmcli-java/a6e2670ec0abda5ae7b117003b0451431dd62e03/pic_ref/oldversion.png -------------------------------------------------------------------------------- /pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 4.0.0 6 | 7 | io.github.dtm-labs 8 | dtmcli-java-parent 9 | 2.1.8 10 | pom 11 | 12 | dtmcli-java-parent 13 | The java client for dtm 14 | https://github.com/dtm-labs/dtmcli-java 15 | 16 | 17 | dtmcli-common 18 | dtmcli-core 19 | dtmcli-springcloud 20 | dtmcli-java 21 | nacos-plugin 22 | eureka-plugin 23 | 24 | 25 | 26 | 1.8 27 | 1.8 28 | 1.8 29 | UTF-8 30 | 4.12 31 | 2.12.2 32 | 33 | 1.18.20 34 | 11.8 35 | 3.12.0 36 | 3.14.9 37 | 1.4.2 38 | 1.7.30 39 | 40 | 41 | 42 | 43 | 44 | junit 45 | junit 46 | ${junit.version} 47 | test 48 | 49 | 50 | 51 | com.fasterxml.jackson.core 52 | jackson-databind 53 | ${jackson.version} 54 | 55 | 56 | 57 | org.projectlombok 58 | lombok 59 | ${lombok.version} 60 | 61 | 62 | 63 | io.github.openfeign 64 | feign-core 65 | ${feign.version} 66 | 67 | 68 | 69 | io.github.openfeign 70 | feign-jackson 71 | ${feign.version} 72 | 73 | 74 | 75 | org.apache.commons 76 | commons-lang3 77 | ${commons-lang3.version} 78 | 79 | 80 | 81 | com.squareup.okhttp3 82 | okhttp 83 | ${okhttp.version} 84 | 85 | 86 | 87 | com.alibaba.nacos 88 | nacos-client 89 | ${nacos.version} 90 | 91 | 92 | 93 | org.slf4j 94 | slf4j-api 95 | ${slf4j.version} 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | MIT 104 | https://spdx.org/licenses/MIT.html 105 | 106 | 107 | 108 | https://github.com/dtm-labs/dtmcli-java.git 109 | https://github.com/dtm-labs/dtmcli-java 110 | 111 | 112 | 113 | horseLk 114 | horsekiao@gmail.com 115 | 116 | Developer 117 | 118 | +8 119 | 120 | 121 | 122 | 123 | 124 | release 125 | 126 | 127 | 128 | src/main/java 129 | 130 | **/*.properties 131 | **/*.sample 132 | 133 | 134 | 135 | dtmcli-common/src/main/java 136 | 137 | **/*.properties 138 | **/*.sample 139 | 140 | 141 | 142 | dtmcli-core/src/main/java 143 | 144 | **/*.properties 145 | **/*.sample 146 | 147 | 148 | 149 | dtmcli-java/src/main/java 150 | 151 | **/*.properties 152 | **/*.sample 153 | 154 | 155 | dtmcli-spring/src/main/java 156 | 157 | **/*.properties 158 | **/*.sa 159 | 160 | 161 | 162 | 163 | 164 | 165 | org.apache.maven.plugins 166 | maven-source-plugin 167 | 2.2.1 168 | 169 | ${project.build.sourceEncoding} 170 | 171 | 172 | 173 | package 174 | 175 | jar-no-fork 176 | 177 | 178 | 179 | 180 | 181 | 182 | org.apache.maven.plugins 183 | maven-javadoc-plugin 184 | 2.9.1 185 | 186 | private 187 | true 188 | UTF-8 189 | UTF-8 190 | UTF-8 191 | -Xdoclint:none 192 | /Library/Java/JavaVirtualMachines/jdk1.8.0_261.jdk/Contents/Home/bin/javadoc 193 | 194 | 195 | 196 | 197 | package 198 | 199 | jar 200 | 201 | 202 | 203 | 204 | 205 | 206 | org.apache.maven.plugins 207 | maven-gpg-plugin 208 | 1.6 209 | 210 | 211 | verify 212 | 213 | sign 214 | 215 | 216 | 217 | 218 | 219 | 220 | org.apache.maven.plugins 221 | maven-compiler-plugin 222 | 3.0 223 | 224 | 1.8 225 | 1.8 226 | true 227 | true 228 | UTF-8 229 | false 230 | ${project.build.sourceEncoding} 231 | 232 | 233 | 234 | 235 | org.apache.maven.plugins 236 | maven-release-plugin 237 | 2.5.1 238 | 239 | 240 | 241 | 242 | 243 | ossrh 244 | ossrh 245 | https://s01.oss.sonatype.org/content/repositories/snapshots/ 246 | 247 | 248 | ossrh 249 | ossrh 250 | https://s01.oss.sonatype.org/service/local/staging/deploy/maven2/ 251 | 252 | 253 | 254 | 255 | 256 | 257 | 258 | 259 | 260 | 261 | 262 | 263 | 264 | 265 | 266 | 267 | 268 | 269 | 270 | 271 | 272 | 273 | 274 | 275 | 276 | 277 | --------------------------------------------------------------------------------