【Seata】_02 Docker部署Seata1.4.0集成Nacos2.2.0

生命周期

TC(Transaction Coordinator):事务协调者
维护全局和分支事务状态,驱动全局事务提交或回滚
TM(Transaction Manager): 事务管理器
定义全局事务的范围,开始全局事务、提交或回滚全局事务
RM(Resource Manager):资源管理器
管理分支事务处理的资源,与TC交谈注册分支事务和报告分支事务状态,并驱动分支事务提交或回滚
其中,TC为单独部署的Server,TM和RM为嵌入到应用中的Client
在这里插入图片描述
1.TM请求TC开启一个全局事务。TC会生成一个XID作为该全局事务的编号。XID会在微服务的调用链路中传播,保证将多个微服务的子事务关联在一起,
2.RM请求TC将本地事务注册为全局事务的分支事务,通过全局事务的 XID进行关联。
3.TM请求 TC告诉 XID 对应的全局事务是进行提交还是回滚
4.TC动RM们将 XID对应的自己的本地事务进行提交还是回滚

第一阶段

第一阶段

第二阶段成功

在这里插入图片描述

第二阶段回滚

分布式事务操作失败,TM向TC发送回滚请求,RM 收到协调器TC发来的回滚请求,通过 XID 和 Branch ID 找到相应的回滚日志记录,通过回滚记录生成反向的更新SQL井执行,以完成分支的回滚
在这里插入图片描述

Seata使用

Seata Server搭建(docker)

有三种持久化模式:

  1. file:(默认)单机模式,全局事务会话信息内存中读写并持久化本地文件root.data,性能较高
  2. db(5.7+,包含):高可用模式,全局事务会话信息通过db共享,相应性能差些
  3. redisT Seata-Server 1.3及以上版本支持,性能较高,存在事务信息委失风险,请提前配置适合当前场景的redis持久化配置
    我要搭建一个db模式并且集成Nacos的注册和配置功能,这样在集群中可以进行负载和统一配置,Nacos搭建略……
  4. 先启动一个容器拷贝点文件
docker run --name seata-server -p 8091:8091 -d  seataio/seata-server:1.3.0
docker cp seata-server:/seata-server E:/docker/volumes

拷贝完就可以把这个容器删了,目录结构如下
在这里插入图片描述

  1. 修改E:\docker\volumes\seata-server\resources下的file.conf
## transaction log store, only used in seata-server
store {
  ## store mode: file、db、redis
  mode = "db"

  ## database store property
  db {
    ## the implement of javax.sql.DataSource, such as DruidDataSource(druid)/BasicDataSource(dbcp)/HikariDataSource(hikari) etc.
    datasource = "druid"
    ## mysql/oracle/postgresql/h2/oceanbase etc.
    dbType = "mysql"
    driverClassName = "com.mysql.jdbc.Driver"
    url = "jdbc:mysql://192.168.2.115:3306/seata"
    user = "root"
    password = "1"
    minConn = 5
    maxConn = 100
    globalTable = "global_table"
    branchTable = "branch_table"
    lockTable = "lock_table"
    queryLimit = 100
    maxWait = 5000
  }
}

mode 修改为 db,下面的配置修改为自己的数据库,注意我的mysql装在宿主机上所以写的是内网IP,因为要让容器访问到。
这里是将Seata的数据持久化到数据库用于多个Seata节点共享数据,多余的配置我都删除了
3. 创建数据库seata并初始化表结构,给出一份sql脚本:

-- the table to store GlobalSession data
drop table if exists `global_table`;
create table `global_table`
(
    `xid`                       varchar(128) not null,
    `transaction_id`            bigint,
    `status`                    tinyint      not null,
    `application_id`            varchar(32),
    `transaction_service_group` varchar(32),
    `transaction_name`          varchar(128),
    `timeout`                   int,
    `begin_time`                bigint,
    `application_data`          varchar(2000),
    `gmt_create`                datetime,
    `gmt_modified`              datetime,
    primary key (`xid`),
    key `idx_gmt_modified_status` (`gmt_modified`, `status`),
    key `idx_transaction_id` (`transaction_id`)
);

-- the table to store BranchSession data
drop table if exists `branch_table`;
create table `branch_table`
(
    `branch_id`         bigint       not null,
    `xid`               varchar(128) not null,
    `transaction_id`    bigint,
    `resource_group_id` varchar(32),
    `resource_id`       varchar(256),
    `lock_key`          varchar(128),
    `branch_type`       varchar(8),
    `status`            tinyint,
    `client_id`         varchar(64),
    `application_data`  varchar(2000),
    `gmt_create`        datetime,
    `gmt_modified`      datetime,
    primary key (`branch_id`),
    key `idx_xid` (`xid`)
);

-- the table to store lock data
drop table if exists `lock_table`;
create table `lock_table`
(
    `row_key`        varchar(128) not null,
    `xid`            varchar(96),
    `transaction_id` long,
    `branch_id`      long,
    `resource_id`    varchar(256),
    `table_name`     varchar(32),
    `pk`             varchar(36),
    `gmt_create`     datetime,
    `gmt_modified`   datetime,
    primary key (`row_key`)
);

  1. 修改E:\docker\volumes\seata\resources下的registry.conf
registry {
  type = "nacos"
  loadBalance = "RandomLoadBalance"
  loadBalanceVirtualNodes = 10

  nacos {
    application = "seata-server"
    serverAddr = "192.168.2.115:8848"
    group = "SEATA_GROUP"
    namespace = "seata-server"
    cluster = "default"
    username = "nacos"
    password = "nacos"
  }
}

config {
  type = "nacos"

  nacos {
    serverAddr = "192.168.2.115:8848"
    namespace = "seata-server"
    group = "SEATA_GROUP"
    username = "nacos"
    password = "nacos"
  }
}

type改成nacos,下面的配置改对,这里注意我的nacos也是在本地所以也写的宿主机的IP,namespace写Nacos的namespace,我是自己创建了个,不写的话默认是public
现在seata就能注册进Nacos并且能使用配置中心了

  1. 将本地配置推送到Nacos
    这步比较容易出错,需要将本地的一些配置推送到Nacos中
    在registry.conf同级目录下新建:config.txt,这个文件可以在seata源码中找到,我是删除了一些不相关的配置
    config.txt
transport.type=TCP
transport.server=NIO
transport.heartbeat=true
transport.enableClientBatchSendRequest=false
transport.threadFactory.bossThreadPrefix=NettyBoss
transport.threadFactory.workerThreadPrefix=NettyServerNIOWorker
transport.threadFactory.serverExecutorThreadPrefix=NettyServerBizHandler
transport.threadFactory.shareBossWorker=false
transport.threadFactory.clientSelectorThreadPrefix=NettyClientSelector
transport.threadFactory.clientSelectorThreadSize=1
transport.threadFactory.clientWorkerThreadPrefix=NettyClientWorkerThread
transport.threadFactory.bossThreadSize=1
transport.threadFactory.workerThreadSize=default
transport.shutdown.wait=3
service.vgroupMapping.my_test_tx_group=default
service.default.grouplist=127.0.0.1:8091
service.enableDegrade=false
service.disableGlobalTransaction=false
client.rm.asyncCommitBufferLimit=10000
client.rm.lock.retryInterval=10
client.rm.lock.retryTimes=30
client.rm.lock.retryPolicyBranchRollbackOnConflict=true
client.rm.reportRetryCount=5
client.rm.tableMetaCheckEnable=false
client.rm.sqlParserType=druid
client.rm.reportSuccessEnable=false
client.rm.sagaBranchRegisterEnable=false
client.tm.commitRetryCount=5
client.tm.rollbackRetryCount=5
client.tm.defaultGlobalTransactionTimeout=60000
client.tm.degradeCheck=false
client.tm.degradeCheckAllowTimes=10
client.tm.degradeCheckPeriod=2000
store.mode=db
store.file.dir=file_store/data
store.file.maxBranchSessionSize=16384
store.file.maxGlobalSessionSize=512
store.file.fileWriteBufferCacheSize=16384
store.file.flushDiskMode=async
store.file.sessionReloadReadSize=100
store.db.datasource=druid
store.db.dbType=mysql
store.db.driverClassName=com.mysql.jdbc.Driver
store.db.url=jdbc:mysql://127.0.0.1:3306/seata?useUnicode=true
store.db.user=root
store.db.password=1
store.db.minConn=5
store.db.maxConn=30
store.db.globalTable=global_table
store.db.branchTable=branch_table
store.db.queryLimit=100
store.db.lockTable=lock_table
store.db.maxWait=5000
store.redis.host=127.0.0.1
store.redis.port=6379
store.redis.maxConn=10
store.redis.minConn=1
store.redis.database=0
store.redis.password=null
store.redis.queryLimit=100
server.recovery.committingRetryPeriod=1000
server.recovery.asynCommittingRetryPeriod=1000
server.recovery.rollbackingRetryPeriod=1000
server.recovery.timeoutRetryPeriod=1000
server.maxCommitRetryTimeout=-1
server.maxRollbackRetryTimeout=-1
server.rollbackRetryTimeoutUnlockEnable=false
client.undo.dataValidation=true
client.undo.logSerialization=jackson
client.undo.onlyCareUpdateColumns=true
server.undo.logSaveDays=7
server.undo.logDeletePeriod=86400000
client.undo.logTable=undo_log
log.exceptionRate=100
transport.serialization=seata
transport.compressor=none
metrics.enabled=false
metrics.registryType=compact
metrics.exporterList=prometheus
metrics.exporterPrometheusPort=9898

需要修改
store.mode
store.db.url
store.db.user
store.db.password
注意:service.vgroupMapping这个配置,.后面的my_test_tx_group是可以自定义的,这个配置意思是作为事务分组来标明机房组,比如实际生产中会做异地多活,这个值作为不同区域机房组。可以将同一个机房的多个实例配置成一个组。
service.vgroupMapping.my_test_tx_group的值必须与registry.conf文件中的cluster值一样

目录下新建一个sh文件夹并且新建一个文件:nacos-config.sh,需要执行这个脚本将Seata初始化配置推送到Nacos,给出脚本内容,别改动:

while getopts ":h:p:g:t:u:w:" opt
do
  case $opt in
  h)
    host=$OPTARG
    ;;
  p)
    port=$OPTARG
    ;;
  g)
    group=$OPTARG
    ;;
  t)
    tenant=$OPTARG
    ;;
  u)
    username=$OPTARG
    ;;
  w)
    password=$OPTARG
    ;;
  ?)
    echo " USAGE OPTION: $0 [-h host] [-p port] [-g group] [-t tenant] [-u username] [-w password] "
    exit 1
    ;;
  esac
done

if [[ -z ${host} ]]; then
    host=localhost
fi
if [[ -z ${port} ]]; then
    port=8848
fi
if [[ -z ${group} ]]; then
    group="SEATA_GROUP"
fi
if [[ -z ${tenant} ]]; then
    tenant=""
fi
if [[ -z ${username} ]]; then
    username=""
fi
if [[ -z ${password} ]]; then
    password=""
fi

nacosAddr=$host:$port
contentType="content-type:application/json;charset=UTF-8"

echo "set nacosAddr=$nacosAddr"
echo "set group=$group"

failCount=0
tempLog=$(mktemp -u)
function addConfig() {
  curl -X POST -H "${contentType}" "http://$nacosAddr/nacos/v1/cs/configs?dataId=$1&group=$group&content=$2&tenant=$tenant&username=$username&password=$password" >"${tempLog}" 2>/dev/null
  if [[ -z $(cat "${tempLog}") ]]; then
    echo " Please check the cluster status. "
    exit 1
  fi
  if [[ $(cat "${tempLog}") =~ "true" ]]; then
    echo "Set $1=$2 successfully "
  else
    echo "Set $1=$2 failure "
    (( failCount++ ))
  fi
}

count=0
for line in $(cat $(dirname "$PWD")/config.txt | sed s/[[:space:]]//g); do
  (( count++ ))
	key=${line%%=*}
    value=${line#*=}
	addConfig "${key}" "${value}"
done

echo "========================================================================="
echo " Complete initialization parameters,  total-count:$count ,  failure-count:$failCount "
echo "========================================================================="

if [[ ${failCount} -eq 0 ]]; then
	echo " Init nacos config finished, please start seata-server. "
else
	echo " init nacos config fail. "
fi

在windows下怎么执行sh脚本呢?在脚本同级目录下右键 - Git Bash Here (需要安装Git,相信大家都有),输入命令

 sh nacos-config.sh -h localhost -p 8848 -g SEATA_GROUP -t seata-server -u nacos -w nacos 

就能推送上去

=========================================================================
 Complete initialization parameters,  total-count:80 ,  failure-count:0
=========================================================================
 Init nacos config finished, please start seata-server.

在这里插入图片描述
这里有个问题,如果下载的官方的config.txt没有进行改动时,官方配置有一些key值是空,这些配置会导入失败,目测应该不影响功能

启动Seate

docker run -d --name seata-server -p 8091:8091 -v E:/docker/volumes/seata:/seata-server seataio/seata-server:1.3.0

查看容器日志:

2023-02-17 23:49:35 2023-02-17 15:49:35.289  INFO --- [           main] io.seata.server.Server                   : The server is running in container.
2023-02-17 23:49:35 2023-02-17 15:49:35.564  INFO --- [           main] io.seata.config.FileConfiguration        : The configuration file used is registry.conf
2023-02-17 23:49:39 2023-02-17 15:49:39.343  INFO --- [           main] com.alibaba.druid.pool.DruidDataSource   : {dataSource-1} inited
2023-02-17 23:49:40 2023-02-17 15:49:40.436  INFO --- [           main] i.s.core.rpc.netty.NettyServerBootstrap  : Server started, listen port: 8091

服务已经注册进来了
在这里插入图片描述

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值