SpringBoot+seata+mybatis+feign使用說明

Seata-Server部署

  1. 下載啟動包

    wget https://github.com/seata/seata/releases/download/v1.0.0/seata-server-1.0.0.tar.gz
    
  2. 建立數(shù)據(jù)庫seata-server

  3. 創(chuàng)建相關(guān)表

    CREATE TABLE `branch_table` (
        `branch_id` bigint(20) NOT NULL,
        `xid` varchar(128) NOT NULL,
        `transaction_id` bigint(20) DEFAULT NULL,
        `resource_group_id` varchar(32) DEFAULT NULL,
        `resource_id` varchar(256) DEFAULT NULL,
        `branch_type` varchar(8) DEFAULT NULL,
        `status` tinyint(4) DEFAULT NULL,
        `client_id` varchar(64) DEFAULT NULL,
        `application_data` varchar(2000) DEFAULT NULL,
        `gmt_create` datetime DEFAULT NULL,
        `gmt_modified` datetime DEFAULT NULL,
        PRIMARY KEY (`branch_id`),
        KEY `idx_xid` (`xid`)
    ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
    
    CREATE TABLE `global_table` (
        `xid` varchar(128) NOT NULL,
        `transaction_id` bigint(20) DEFAULT NULL,
        `status` tinyint(4) NOT NULL,
        `application_id` varchar(32) DEFAULT NULL,
        `transaction_service_group` varchar(32) DEFAULT NULL,
        `transaction_name` varchar(128) DEFAULT NULL,
        `timeout` int(11) DEFAULT NULL,
        `begin_time` bigint(20) DEFAULT NULL,
        `application_data` varchar(2000) DEFAULT NULL,
        `gmt_create` datetime DEFAULT NULL,
        `gmt_modified` datetime DEFAULT NULL,
        PRIMARY KEY (`xid`),
        KEY `idx_gmt_modified_status` (`gmt_modified`,`status`),
        KEY `idx_transaction_id` (`transaction_id`)
    ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
    
    CREATE TABLE `lock_table` (
        `row_key` varchar(128) NOT NULL,
        `xid` varchar(96) DEFAULT NULL,
        `transaction_id` bigint(20) DEFAULT NULL,
        `branch_id` bigint(20) NOT NULL,
        `resource_id` varchar(256) DEFAULT NULL,
        `table_name` varchar(32) DEFAULT NULL,
        `pk` varchar(36) DEFAULT NULL,
        `gmt_create` datetime DEFAULT NULL,
        `gmt_modified` datetime DEFAULT NULL,
        PRIMARY KEY (`row_key`),
        KEY `idx_branch_id` (`branch_id`)
    ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
    
    CREATE TABLE `undo_log` (
        `id` bigint(20) NOT NULL AUTO_INCREMENT,
        `branch_id` bigint(20) NOT NULL,
        `xid` varchar(100) NOT NULL,
        `context` varchar(128) NOT NULL,
        `rollback_info` longblob NOT NULL,
        `log_status` int(11) NOT NULL,
        `log_created` datetime NOT NULL,
        `log_modified` datetime NOT NULL,
        PRIMARY KEY (`id`),
        UNIQUE KEY `ux_undo_log` (`xid`,`branch_id`)
    ) ENGINE=InnoDB DEFAULT CHARSET=utf8;
    
  4. 修改file.conf配置文件

    1. cd <seata-server directory>/conf/
    2. vim file.conf
    3. 定義tx-service-group:
        將vgroup_mapping.my_test_tx_group = "default" 修改為-> vgroup_mapping.my_test_tx_group = "seata-server"
    4. 修改store.mode="db"
    5. 修改db.datasource="druid"
    6. 修改數(shù)據(jù)庫連接的信息
    
  5. 修改registry.conf配置文件

    1. 修改registry.type="eureka"
    2. 修改eureka.serviceUrl為自己eureka地址
    3. 修改eureka.applicaton="seata-server"
    4. 修改config.type="apollo"
    5. 修改config.apollo.app.id="seata-server"
    6. 修改config.apollo.apollo.meta為apollo對應(yīng)地址
    
  6. 啟動

    1. cd <seata-server directory>/bin/
    2. ./seata-server.sh -p 8091 -n 1
    
  7. 啟動參數(shù)詳解

    -h: 注冊到注冊中心的ip
    -p: Server rpc 監(jiān)聽端口
    -m: 全局事務(wù)會話信息存儲模式袱蜡,file令蛉、db,優(yōu)先讀取啟動參數(shù)
    -n: Server node筹裕,多個Server時编兄,需區(qū)分各自節(jié)點(diǎn)渠羞,用于生成不同區(qū)間的transactionId契吉,以免沖突
    -e: 多環(huán)境配置參考 http://seata.io/en-us/docs/ops/multi-configuration-isolation.html
    

Seata客戶端使用

注:seata的配置較多漠其,但是1.0.0版本里面Apollo配置源碼只支持使用application的namespace贫悄。

  1. 在pom中增加依賴
    <dependency>
        <groupId>com.alibaba.cloud</groupId>
        <artifactId>spring-cloud-alibaba-seata</artifactId>
        <exclusions>
            <exclusion>
                <artifactId>seata-all</artifactId>
                <groupId>io.seata</groupId>
            </exclusion>
        </exclusions>
    </dependency>
    <dependency>
        <groupId>io.seata</groupId>
        <artifactId>seata-all</artifactId>
        <version>1.0.0</version>
    </dependency>
  1. 將DataSource用seata包內(nèi)的DataSourceProxy代理
    @Primary
    @Bean("dataSource")
    public DataSourceProxy dataSourceProxy(DataSource druidDataSource) {
        return new DataSourceProxy(druidDataSource);
    }
    
  2. SqlSessionFactory使用代理后的DataSource
    @Bean(name = "sqlSessionFactory")
    public SqlSessionFactory sqlSessionFactoryBean(DataSourceProxy dataSourceProxy) {
        SqlSessionFactoryBean bean = new SqlSessionFactoryBean();
        bean.setDataSource(dataSourceProxy);
        bean.setTypeAliasesPackage("com.test.entity");
    
        // 分頁插件
        PageHelper pageHelper = new PageHelper();
        Properties properties = new Properties();
        properties.setProperty("reasonable", "true");
        // properties.setProperty("supportMethodsArguments", "true");
        properties.setProperty("returnPageInfo", "check");
        properties.setProperty("params", "count=countSql");
        pageHelper.setProperties(properties);
        MybatisBaseUpdateInterceptor mybatisBaseUpdateInterceptor = new MybatisBaseUpdateInterceptor();
        MybatisBaseSelectInterceptor mybatisBaseSelectInterceptor = new MybatisBaseSelectInterceptor();
        // 添加插件
        bean.setPlugins(new Interceptor[]{pageHelper, mybatisBaseUpdateInterceptor, mybatisBaseSelectInterceptor});
    
        // 添加XML目錄
        ResourcePatternResolver resolver = new PathMatchingResourcePatternResolver();
        try {
            bean.setMapperLocations(resolver.getResources("classpath*:mapper/*.xml"));
            // 設(shè)置過濾_
            org.apache.ibatis.session.Configuration configuration = new org.apache.ibatis.session.Configuration();
            configuration.setMapUnderscoreToCamelCase(true);
            bean.setConfiguration(configuration);
    
            return bean.getObject();
        } catch (Exception e) {
            e.printStackTrace();
            throw new RuntimeException(e);
        }
    }
    
  3. application.properties增加配置
    spring.cloud.alibaba.seata.tx-service-group=my_test_tx_group
    config.type = apollo
    registry.type = eureka
    #seata-server注冊的注冊中心地址瑞驱,必填,不填會報(bào)錯
    registry.eureka.serviceUrl = http://xxx.xxx.xxx.xxx:8000/eureka
    
  4. 數(shù)據(jù)庫創(chuàng)建undo_log表
    CREATE TABLE `undo_log` (
        `id` bigint(20) NOT NULL AUTO_INCREMENT,
        `branch_id` bigint(20) NOT NULL,
        `xid` varchar(100) NOT NULL,
        `context` varchar(128) NOT NULL,
        `rollback_info` longblob NOT NULL,
        `log_status` int(11) NOT NULL,
        `log_created` datetime NOT NULL,
        `log_modified` datetime NOT NULL,
        PRIMARY KEY (`id`),
        UNIQUE KEY `ux_undo_log` (`xid`,`branch_id`)
    ) ENGINE=InnoDB AUTO_INCREMENT=32 DEFAULT CHARSET=utf8;
    
  5. apollo增加配置
    #======================seata配置=====================
    transport.type = TCP
    transport.server = NIO
    transport.heartbeat = true
    transport.enable-client-batch-send-request = true
    #thread factory for netty
    transport.thread-factory.boss-thread-prefix = NettyBoss
    transport.thread-factory.worker-thread-prefix = NettyServerNIOWorker
    transport.thread-factory.server-executor-thread-prefix = NettyServerBizHandler
    transport.thread-factory.share-boss-worker = false
    transport.thread-factory.client-selector-thread-prefix = NettyClientSelector
    transport.thread-factory.client-selector-thread-size = 1
    transport.thread-factory.client-worker-thread-prefix = NettyClientWorkerThread
    # netty boss thread size,will not be used for UDT
    transport.thread-factory.boss-thread-size = 1
    #auto default pin or 8
    transport.thread-factory.worker-thread-size = 8
    transport.shutdown.wait = 3
    transport.serialization = seata
    transport.compressor = none
    #transaction service group mapping
    service.vgroup_mapping.my_test_tx_group = seata-server
    service.enableDegrade = false
    #disable seata
    service.disableGlobalTransaction = false
    client.rm.async.commit.buffer.limit = 10000
    client.rm.lock.retry.internal = 10
    client.rm.lock.retry.times = 30
    client.rm.lock.retry.policy.branch-rollback-on-conflict = true
    client.rm.report.retry.count = 5
    client.rm.table.meta.check.enable = false
    client.rm.report.success.enable = true
    client.tm.commit.retry.count = 5
    client.tm.rollback.retry.count = 5
    client.undo.data.validation = true
    client.undo.log.serialization = jackson
    client.undo.log.table = undo_log
    client.log.exceptionRate = 100
    # auto proxy the DataSource bean
    client.support.spring.datasource.autoproxy = false
    #===================================================
    
  6. 在需要使用分布式事務(wù)的方法上@GlobalTransactional注解即可窄坦,且只有拋出異常才可回滾
  7. 調(diào)用示例
    @RestController
    @RequestMapping("/capi/test")
    public class TestController {
    
        @Autowired
        private Server1Api server1Api;
        @Autowired
        private Server2Api server2Api;
    
        @PostMapping()
        @GlobalTransactional
        public Result create(){
            Result test1 = server1Api.test();
    
            Result test = server2Api.test();
            if(!"00".equals(test.getRespCode())){
                throw new RuntimeException("xxxxxx");
            }
            return Result.ok();
        }
    
    }
    
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末唤反,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子鸭津,更是在濱河造成了極大的恐慌彤侍,老刑警劉巖,帶你破解...
    沈念sama閱讀 216,402評論 6 499
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件逆趋,死亡現(xiàn)場離奇詭異盏阶,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)闻书,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,377評論 3 392
  • 文/潘曉璐 我一進(jìn)店門名斟,熙熙樓的掌柜王于貴愁眉苦臉地迎上來脑慧,“玉大人,你說我怎么就攤上這事砰盐∶铺唬” “怎么了?”我有些...
    開封第一講書人閱讀 162,483評論 0 353
  • 文/不壞的土叔 我叫張陵楞卡,是天一觀的道長霜运。 經(jīng)常有香客問我脾歇,道長蒋腮,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,165評論 1 292
  • 正文 為了忘掉前任藕各,我火速辦了婚禮池摧,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘激况。我一直安慰自己作彤,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,176評論 6 388
  • 文/花漫 我一把揭開白布乌逐。 她就那樣靜靜地躺著竭讳,像睡著了一般。 火紅的嫁衣襯著肌膚如雪浙踢。 梳的紋絲不亂的頭發(fā)上绢慢,一...
    開封第一講書人閱讀 51,146評論 1 297
  • 那天,我揣著相機(jī)與錄音洛波,去河邊找鬼胰舆。 笑死,一個胖子當(dāng)著我的面吹牛蹬挤,可吹牛的內(nèi)容都是我干的缚窿。 我是一名探鬼主播,決...
    沈念sama閱讀 40,032評論 3 417
  • 文/蒼蘭香墨 我猛地睜開眼焰扳,長吁一口氣:“原來是場噩夢啊……” “哼倦零!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起吨悍,我...
    開封第一講書人閱讀 38,896評論 0 274
  • 序言:老撾萬榮一對情侶失蹤光绕,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后畜份,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體诞帐,經(jīng)...
    沈念sama閱讀 45,311評論 1 310
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,536評論 2 332
  • 正文 我和宋清朗相戀三年爆雹,在試婚紗的時候發(fā)現(xiàn)自己被綠了停蕉。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片愕鼓。...
    茶點(diǎn)故事閱讀 39,696評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖慧起,靈堂內(nèi)的尸體忽然破棺而出菇晃,到底是詐尸還是另有隱情,我是刑警寧澤蚓挤,帶...
    沈念sama閱讀 35,413評論 5 343
  • 正文 年R本政府宣布磺送,位于F島的核電站,受9級特大地震影響灿意,放射性物質(zhì)發(fā)生泄漏估灿。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,008評論 3 325
  • 文/蒙蒙 一缤剧、第九天 我趴在偏房一處隱蔽的房頂上張望馅袁。 院中可真熱鬧,春花似錦荒辕、人聲如沸汗销。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,659評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽弛针。三九已至,卻和暖如春李皇,著一層夾襖步出監(jiān)牢的瞬間削茁,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,815評論 1 269
  • 我被黑心中介騙來泰國打工疙赠, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留付材,地道東北人。 一個月前我還...
    沈念sama閱讀 47,698評論 2 368
  • 正文 我出身青樓圃阳,卻偏偏與公主長得像厌衔,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子捍岳,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,592評論 2 353