文件最后提交记录最后更新时间
1 个月前
1 个月前
1 个月前
1 个月前
1 个月前
1 个月前
1 个月前
1 个月前
1 个月前
1 个月前
README

DieselCompatibility2openGauss

背景

Diesel 是 Rust 生态中最流行的 ORM 框架,提供类型安全的查询构造和编译时 SQL 验证。本项目验证 Diesel 通过 MySQL 协议连接 openGauss B 兼容模式数据库的兼容性。

openGauss 通过 dolphin 插件提供 MySQL 协议支持,允许 MySQL 客户端(如 Diesel + mysql crate)通过 3306 端口连接 B 兼容模式数据库,无需修改应用代码即可从 MySQL 迁移到 openGauss。

项目说明

本目录包含 Diesel ORM 与 openGauss 的兼容性测试代码,覆盖:

  • 连接与认证:握手、版本查询、mysql_native_password 认证
  • CRUD 操作:INSERT/SELECT/UPDATE/DELETE、批量操作、LAST_INSERT_ID
  • 事务管理:手动事务、自动事务、隔离级别、多语句批处理
  • 类型映射:整数、字符串、日期时间、JSON、BLOB、DECIMAL 等
  • 查询构造:过滤、排序、分页、聚合、JOIN、子查询
  • 预处理语句:PREPARE/EXECUTE/CLOSE、参数绑定、长数据发送
  • 数据迁移:diesel_migrations 工具支持
  • 连接池与并发:r2d2 连接池、多线程并发

测试结果

Master 全量矩阵:80 例,80 PASS / 0 FAIL。

模块 覆盖范围 用例数 通过 备注
T1 连接与认证 握手/version/native auth/@@autocommit 4 4
T2 CRUD insert 单/批/select by id/update/delete/LAST_INSERT_ID 7 7
T3 事务 手动 BEGIN/COMMIT/ROLLBACK、conn.transaction()、SET autocommit、隔离、多语句 batch_execute 7 7
T4 类型映射 int/bigint/smallint、varchar/text、bool、float/double、date/time/ts、nullable、numeric 7 7
T5 查询构造 eq/ne/gt/lt/ge/le、null、like/between/in、order、limit/offset、count、聚合、group/having、inner join、distinct、选列 11 11
T6 预处理 PREPARE/EXECUTE、复用、CLOSE、复用异参、100KB TEXT prepared bind round-trip 5 5
T7 约定与运维 search_path 约定、DDL via MySQL 2 2
T8 迁移/CLI diesel migration run、print-schema、embed_migrations!、revert 4 4
T9 JOIN/子查询 LEFT/RIGHT/CROSS/FULL JOIN、subquery-WHERE/FROM、EXISTS、ANY/ALL 8 8 支持 FULL JOIN(超越 MySQL)
T10 类型深挖 JSON 列、日期函数、ENUM、BLOB、DECIMAL、LONGTEXT 200KB 6 6
T11 upsert/嵌套 ON DUPLICATE KEY、SAVEPOINT、嵌套 conn.transaction() 3 3
T12 池/并发/隔离/错误 r2d2 池、并发 insert、跨连接可见性、错误映射 4 4
T13 协议层 MySQL 多 payload 大包 1 1
T14 typed DSL typed LEFT JOIN、typed 子查询 IN、AsChangeset、QueryableByName、associations、for_update、typed Json 7 7
T-Meta 元数据(metadata) information_schema 类型名、diesel print-schema 类型映射、nvarchar2 类型名映射 4 4

T-Meta-5:nvarchar2 的 MySQL 协议数据类型码是 VAR_STRING(字符串)。dolphin 将其元数据中的类型名映射为 varchar,使类型名与数据类型码一致,MySQL ORM(Diesel)可正常识别。

亮点发现:dolphin 插件基于 openGauss 内核支持 FULL OUTER JOIN(MySQL 原生不支持此语法),测试验证 Diesel 可通过 MySQL 协议使用该语法(T9.4)。

完整测试报告见 doc/测试报告.md。

环境要求

openGauss(master) 与 dolphin 从源码编译,Rust 与 diesel_cli 在容器内安装。各组件版本如下,端到端部署步骤见下文「快速开始(从零编译部署)」。

组件 版本
openGauss 7.0.0 (master)
dolphin 插件 master
Rust 1.88.0
Diesel CLI 2.3.12
Diesel 2.3.12,features: mysql, chrono, r2d2, serde_json
libmysqlclient 8.0.44
数据库配置 B 兼容模式 (DBCOMPATIBILITY='B'),用户认证 mysql_native_password

容器基础环境(openEuler 22.03 + 构建工具 + libmysqlclient)见 docker/README.md。

快速开始(从零编译部署)

以下均在容器 opengauss-dev(openEuler 22.03)内执行,从源码编译 openGauss(master) 与 dolphin,起 B 兼容库并跑通测试。

步骤 1:准备源码与第三方库

mkdir -p /work && cd /work
git clone https://gitcode.com/opengauss/openGauss-server.git /work/src/openGauss-server
# 将 openGauss-third_party_binarylibs_openEuler_2203_x86_64.tar.gz 放入 /work
tar -xzf openGauss-third_party_binarylibs_openEuler_2203_x86_64.tar.gz -C /work   # 得到 /work/binarylibs

步骤 2:编译 openGauss server

cd /work/src/openGauss-server
./build.sh -m release -3rd /work/binarylibs --cmake
# 产物:/work/src/openGauss-server/mppdb_temp_install/

步骤 3:编译并安装 dolphin

export GAUSSHOME=/work/src/openGauss-server/mppdb_temp_install
export PATH=$GAUSSHOME/bin:$PATH
export CC=/work/binarylibs/buildtools/gcc10.3/gcc/bin/gcc
export CXX=/work/binarylibs/buildtools/gcc10.3/gcc/bin/g++
export THIRD_BIN_PATH=/work/binarylibs
export PREFIX_HOME=$GAUSSHOME
export DEBUG_TYPE=release
export LD_LIBRARY_PATH=$GAUSSHOME/lib:$GAUSSHOME/lib/postgresql:/work/binarylibs/kernel/dependency/openssl/comm/lib:/work/binarylibs/kernel/dependency/onnxruntime/comm/lib:/work/binarylibs/buildtools/gcc10.3/gcc/lib64:/work/binarylibs/buildtools/gcc10.3/isl/lib:/work/binarylibs/buildtools/gcc10.3/mpc/lib:/work/binarylibs/buildtools/gcc10.3/mpfr/lib:/work/binarylibs/buildtools/gcc10.3/gmp/lib

cd /work/src/openGauss-server/contrib/dolphin
# cmake.sh 的 CMAKE_OPT 需与 server 一致:
# -DENABLE_OPENEULER_MAJOR=ON -DENABLE_OPENSSL3=ON -DENABLE_READLINE=ON -DHAVE_LIBXML2=OFF -DENABLE_HTAP=on
./cmake.sh x86_64 off on on
# dolphin.so 装到 $GAUSSHOME/lib/postgresql/

步骤 4:配置环境脚本

cat > /work/env_gauss.sh <<'EOF'
export GAUSSHOME=/work/src/openGauss-server/mppdb_temp_install
export PGDATA=/work/dolphin-master-data
export PATH=$GAUSSHOME/bin:$PATH
export LD_LIBRARY_PATH=$GAUSSHOME/lib:$GAUSSHOME/lib/postgresql:/work/binarylibs/kernel/dependency/openssl/comm/lib:/work/binarylibs/kernel/dependency/onnxruntime/comm/lib:/work/binarylibs/kernel/dependency/libcgroup/comm/lib:/work/binarylibs/kernel/dependency/kerberos/comm/lib:/work/binarylibs/kernel/dependency/libcurl/comm/lib:/work/binarylibs/buildtools/gcc10.3/gcc/lib64:$LD_LIBRARY_PATH
EOF
source /work/env_gauss.sh

步骤 5:初始化 B 兼容库并启动

gs_initdb -D $PGDATA -U opengauss --nodename=opengauss --dbcompatibility=B -E UTF8 --locale=C
cat >> $PGDATA/postgresql.conf <<'EOF'
shared_preload_libraries = 'dolphin'
enable_dolphin_proto = on
dolphin_server_port = 3306
dolphin.nulls_minimal_policy = on
EOF
gs_ctl start -D $PGDATA -l $PGDATA/gaussdb.log

步骤 6:创建库、用户并执行初始化脚本

# MySQL 协议实际落在默认库 postgres,连接串里的 diesel_test 作为 schema 名;
# schema 与表必须建在 postgres 下。
gsql -h 127.0.0.1 -p 5432 -U opengauss -d postgres <<'EOF'
CREATE USER diesel_user WITH PASSWORD 'Diesel_test123';
SELECT set_native_password('diesel_user', 'Diesel_test123', 'Diesel_test123');
ALTER USER diesel_user WITH SYSADMIN;
EOF

# 初始化 schema 与测试表(openGauss 原生协议,超级用户执行)
gsql -h 127.0.0.1 -p 5432 -U opengauss -d postgres -f sql/init.sql

步骤 7:验证 MySQL 协议

mysql -h 127.0.0.1 -P 3306 -u diesel_user -pDiesel_test123 -e "select version();"

步骤 8:安装 Rust 工具链并运行测试

yum install -y mysql-devel
curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y
source /root/.cargo/env
cargo install diesel_cli --version 2.3.12 --locked

export PATH="/root/.cargo/bin:$PATH"
export MYSQLCLIENT_LIB_DIR=/usr/lib64 MYSQLCLIENT_INCLUDE_DIR=/usr/include/mysql
cd /work/diesel-compat
cat > .env <<'EOF'
DATABASE_URL=mysql://diesel_user:Diesel_test123@127.0.0.1:3306/diesel_test
EOF
cargo run --release
# 最终汇总:PASS: 80  FAIL: 0

保存测试日志:

cargo run --release 2>&1 | tee logs/full-test-run.log

每次测试可先执行 DROP SCHEMA IF EXISTS diesel_test CASCADE 再重跑 sql/init.sql,之后直接 cargo run --release,无需其它前置状态。

目录结构

├── Cargo.toml              # Rust 项目配置
├── diesel.toml             # Diesel 配置
├── .env.example            # 连接串模板
├── README.md               # 本文档
├── docker/
│   ├── Dockerfile          # 容器构建文件
│   └── README.md           # 容器环境与 openGauss+dolphin 获取说明
├── doc/
│   └── 测试报告.md          # 详细测试报告
├── sql/
│   └── init.sql            # 数据库初始化脚本
├── migrations/             # Diesel 数据迁移
│   └── .../up.sql, down.sql
├── src/
│   ├── main.rs             # 测试入口
│   ├── common.rs           # 连接/工具函数
│   ├── schema.rs           # Diesel table! 宏
│   ├── models.rs           # 模型
│   └── cases/              # 各测试模块
└── logs/                   # 测试日志(gitignored)

参考资料

贡献者

测试代码与文档由 Rourou2285 (snowmantin@foxmail.com) 编写。

许可

本项目遵循 openGauss 许可协议。