Skip to content

Commit

Permalink
feature: add at-sample/at-api e2e test (#684)
Browse files Browse the repository at this point in the history
  • Loading branch information
xjlgod authored Sep 6, 2024
1 parent 8bd5db5 commit c9a6d84
Show file tree
Hide file tree
Showing 29 changed files with 632 additions and 80 deletions.
1 change: 1 addition & 0 deletions at-sample/at-api/e2e-files/rollback.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"res": "rollback"}
56 changes: 56 additions & 0 deletions at-sample/at-api/e2e-files/sqlsh/all.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
--
-- Licensed to the Apache Software Foundation (ASF) under one or more
-- contributor license agreements. See the NOTICE file distributed with
-- this work for additional information regarding copyright ownership.
-- The ASF licenses this file to You under the Apache License, Version 2.0
-- (the "License"); you may not use this file except in compliance with
-- the License. You may obtain a copy of the License at
--
-- http://www.apache.org/licenses/LICENSE-2.0
--
-- Unless required by applicable law or agreed to in writing, software
-- distributed under the License is distributed on an "AS IS" BASIS,
-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-- See the License for the specific language governing permissions and
-- limitations under the License.
--

CREATE TABLE `account_tbl`
(
`id` int(11) NOT NULL AUTO_INCREMENT,
`user_id` varchar(255) DEFAULT NULL,
`money` int(11) DEFAULT '0',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8;

CREATE TABLE `stock_tbl`
(
`id` int(11) NOT NULL AUTO_INCREMENT,
`commodity_code` varchar(255) DEFAULT NULL,
`count` int(11) DEFAULT '0',
PRIMARY KEY (`id`),
UNIQUE KEY `commodity_code` (`commodity_code`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8;

CREATE TABLE `order_tbl`
(
`id` int(11) NOT NULL AUTO_INCREMENT,
`user_id` varchar(255) DEFAULT NULL,
`commodity_code` varchar(255) DEFAULT NULL,
`count` int(11) DEFAULT '0',
`money` int(11) DEFAULT '0',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8;

CREATE TABLE IF NOT EXISTS `undo_log`
(
`branch_id` BIGINT NOT NULL COMMENT 'branch transaction id',
`xid` VARCHAR(128) NOT NULL COMMENT 'global transaction id',
`context` VARCHAR(128) NOT NULL COMMENT 'undo_log context,such as serialization',
`rollback_info` LONGBLOB NOT NULL COMMENT 'rollback info',
`log_status` INT(11) NOT NULL COMMENT '0:normal status,1:defense status',
`log_created` DATETIME(6) NOT NULL COMMENT 'create datetime',
`log_modified` DATETIME(6) NOT NULL COMMENT 'modify datetime',
UNIQUE KEY `ux_undo_log` (`xid`, `branch_id`)
) ENGINE = InnoDB AUTO_INCREMENT = 1 DEFAULT CHARSET = utf8mb4 COMMENT ='AT transaction mode undo table';
ALTER TABLE `undo_log` ADD INDEX `ix_log_created` (`log_created`);
126 changes: 126 additions & 0 deletions at-sample/at-api/e2e-replace/file.conf
Original file line number Diff line number Diff line change
@@ -0,0 +1,126 @@
#
# Licensed to the Apache Software Foundation (ASF) under one or more
# contributor license agreements. See the NOTICE file distributed with
# this work for additional information regarding copyright ownership.
# The ASF licenses this file to You under the Apache License, Version 2.0
# (the "License"); you may not use this file except in compliance with
# the License. You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#

transport {
# tcp, unix-domain-socket
type = "TCP"
#NIO, NATIVE
server = "NIO"
#enable heartbeat
heartbeat = true
# the tm client batch send request enable
enableTmClientBatchSendRequest = false
# the rm client batch send request enable
enableRmClientBatchSendRequest = true
# the rm client rpc request timeout
rpcRmRequestTimeout = 2000
# the tm client rpc request timeout
rpcTmRequestTimeout = 30000
# the rm client rpc request timeout
rpcRmRequestTimeout = 15000
#thread factory for netty
threadFactory {
bossThreadPrefix = "NettyBoss"
workerThreadPrefix = "NettyServerNIOWorker"
serverExecutorThread-prefix = "NettyServerBizHandler"
shareBossWorker = false
clientSelectorThreadPrefix = "NettyClientSelector"
clientSelectorThreadSize = 1
clientWorkerThreadPrefix = "NettyClientWorkerThread"
# netty boss thread size
bossThreadSize = 1
#auto default pin or 8
workerThreadSize = "default"
}
shutdown {
# when destroy server, wait seconds
wait = 3
}
serialization = "seata"
compressor = "none"
}
service {
#transaction service group mapping
vgroupMapping.my_test_tx_group = "default"
#only support when registry.type=file, please don't set multiple addresses
default.grouplist = "seata:8091"
#degrade, current not support
enableDegrade = false
#disable seata
disableGlobalTransaction = false
}

client {
rm {
asyncCommitBufferLimit = 10000
lock {
retryInterval = 10
retryTimes = 30
retryPolicyBranchRollbackOnConflict = true
}
reportRetryCount = 5
tableMetaCheckEnable = false
tableMetaCheckerInterval = 60000
reportSuccessEnable = false
sagaBranchRegisterEnable = false
sagaJsonParser = "fastjson"
sagaRetryPersistModeUpdate = false
sagaCompensatePersistModeUpdate = false
tccActionInterceptorOrder = -2147482648 #Ordered.HIGHEST_PRECEDENCE + 1000
sqlParserType = "druid"
branchExecutionTimeoutXA = 60000
connectionTwoPhaseHoldTimeoutXA = 10000
}
tm {
commitRetryCount = 5
rollbackRetryCount = 5
defaultGlobalTransactionTimeout = 60000
degradeCheck = false
degradeCheckPeriod = 2000
degradeCheckAllowTimes = 10
interceptorOrder = -2147482648 #Ordered.HIGHEST_PRECEDENCE + 1000
}
undo {
dataValidation = true
onlyCareUpdateColumns = true
logSerialization = "jackson"
logTable = "undo_log"
compress {
enable = true
# allow zip, gzip, deflater, lz4, bzip2, zstd default is zip
type = zip
# if rollback info size > threshold, then will be compress
# allow k m g t
threshold = 64k
}
}
loadBalance {
type = "XID"
virtualNodes = 10
}
}
log {
exceptionRate = 100
}
tcc {
fence {
# tcc fence log table name
logTableName = tcc_fence_log
# tcc fence log clean period
cleanPeriod = 1h
}
}
24 changes: 24 additions & 0 deletions at-sample/at-api/e2e-replace/jdbc.properties
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
jdbc.account.url=jdbc:mysql://127.0.0.1:3306/seata?useSSL=false&serverTimezone=UTC
jdbc.account.username=root
jdbc.account.password=123456
jdbc.account.driver=com.mysql.cj.jdbc.Driver
# stock db config
jdbc.stock.url=jdbc:mysql://127.0.0.1:3306/seata?useSSL=false&serverTimezone=UTC
jdbc.stock.username=root
jdbc.stock.password=123456
jdbc.stock.driver=com.mysql.cj.jdbc.Driver
# order db config
jdbc.order.url=jdbc:mysql://127.0.0.1:3306/seata?useSSL=false&serverTimezone=UTC
jdbc.order.username=root
jdbc.order.password=123456
jdbc.order.driver=com.mysql.cj.jdbc.Driver

e2e.jdbc.account.url: jdbc:mysql://mysqlAddress:3306/seata?useSSL=false&serverTimezone=UTC
e2e.jdbc.account.username: user
e2e.jdbc.account.password: 123456
e2e.jdbc.stock.url: jdbc:mysql://mysqlAddress:3306/seata?useSSL=false&serverTimezone=UTC
e2e.jdbc.stock.username: user
e2e.jdbc.stock.password: 123456
e2e.jdbc.order.url: jdbc:mysql://mysqlAddress:3306/seata?useSSL=false&serverTimezone=UTC
e2e.jdbc.order.username: user
e2e.jdbc.order.password: 123456
26 changes: 26 additions & 0 deletions at-sample/at-api/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -76,4 +76,30 @@
<version>8.0.28</version>
</dependency>
</dependencies>

<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-shade-plugin</artifactId>
<version>3.2.4</version>
<executions>
<execution>
<phase>package</phase>
<goals>
<goal>shade</goal>
</goals>
<configuration>
<createDependencyReducedPom>false</createDependencyReducedPom>
<transformers>
<transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
<mainClass>org.apache.seata.api.BusinessService</mainClass>
</transformer>
</transformers>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
58 changes: 58 additions & 0 deletions at-sample/at-api/seata-e2e.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
e2e:
scene_name: at-api
# retry config
retry:
max: 5
interval: 10s
total_timeout: 10m
# services in docker-compose
modules:
# provider service
providers:
- name: at-api
docker_service:
hostname: at-api
restart: on-failure
container_name: test
depends_on:
mysql:
condition: service_healthy
environment:
E2E_ENV: open
# infrastructure services
infrastructures:
- name: mysql
docker_service:
hostname: mysqlAddress
image: mysql:5.7
volumes:
- ./e2e-files/sqlsh:/docker-entrypoint-initdb.d
restart: always
environment:
MYSQL_ROOT_PASSWORD: 123456
MYSQL_DATABASE: seata
MYSQL_USER: user
MYSQL_PASSWORD: 123456
healthcheck:
test: '[ "CMD", "mysqladmin" ,"ping", "-h", "localhost" ]'
interval: 5s
timeout: 10s
retries: 10
- name: seata-server
docker_service:
hostname: seata
image: seataio/seata-server:2.0.0
environment:
SEATA_PORT: 8091
STORE_MODE: file
replace:
- source: e2e-replace/jdbc.properties
dest: src/main/resources/jdbc.properties
- source: e2e-replace/file.conf
dest: src/main/resources/file.conf

# cases to verify
cases:
- name: normal test rollback
invoke: 'docker exec test cat result.yaml'
verify: './e2e-files/rollback.yaml'
Original file line number Diff line number Diff line change
Expand Up @@ -28,8 +28,12 @@
import org.apache.seata.api.service.impl.StorageServiceImpl;
import org.springframework.util.ReflectionUtils;

import java.io.IOException;
import java.lang.reflect.Method;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.sql.SQLException;
import java.util.Map;
import java.util.concurrent.TimeUnit;

/**
Expand All @@ -52,6 +56,8 @@ public static void main(String[] args) throws SQLException, TransactionException
// init tm client and rm client, only once
String applicationId = "api";
String txServiceGroup = "my_test_tx_group";
String outPutRes = "";
boolean isInE2ETest = isInE2ETest();
TMClient.init(applicationId, txServiceGroup);
RMClient.init(applicationId, txServiceGroup);

Expand Down Expand Up @@ -106,16 +112,40 @@ public static void main(String[] args) throws SQLException, TransactionException
//if data negative rollback else commit
if (needCommit) {
tx.commit();
outPutRes = "{\"res\": \"commit\"}";
} else {
System.out.println("rollback trx, cause: data negative, xid is " + tx.getXid());
tx.rollback();
outPutRes = "{\"res\": \"rollback\"}";
}
} catch (Exception exx) {
System.out.println("rollback trx, cause: " + exx.getMessage() + " , xid is " + tx.getXid());
tx.rollback();
if (isInE2ETest) {
writeE2EResFile(exx.getMessage());
}
throw exx;
}
TimeUnit.SECONDS.sleep(10);
if (isInE2ETest) {
writeE2EResFile(outPutRes);
}
TimeUnit.SECONDS.sleep(100);

}

private static void writeE2EResFile(String outPutRes) throws InterruptedException {
try {
Files.write(Paths.get("result.yaml"), outPutRes.getBytes());
} catch (IOException e) {
throw new RuntimeException(e);
}
System.out.println(outPutRes);
TimeUnit.MINUTES.sleep(2);
}

public static boolean isInE2ETest() {
Map<String, String> envs = System.getenv();
String env = envs.getOrDefault("E2E_ENV", "");
return "open".equals(env);
}
}
Loading

0 comments on commit c9a6d84

Please sign in to comment.