如何使得dm同步过来的表的字符集和校验排序规则是utf8和utf8_general_ci

为提高效率,提问时请提供以下信息,问题描述清晰可优先响应。

  • 【TiDB 版本】:v4.0.6
  • 【问题描述】:通过dm集群全量同步上游MySQL的数据,但是在下游的tidb集群上show create table xxx的时候发现表的校验规则COLLATE为utf8_bin,请问如何提前设置,进而保证在dm全量同步过来的时候,下游tidb的表的校验规格是utf8_general_ci。
    dump出来的建表语句:
    [root@mvxl12301 dumped_data.dm-mideazy-prod]# cat midea_mss.sys_tenant-schema.sql
    CREATE TABLE sys_tenant (
    id varchar(36) NOT NULL,
    create_date datetime(6) DEFAULT NULL,
    create_user varchar(255) DEFAULT NULL,
    is_locked varchar(255) DEFAULT NULL,
    lock_date datetime(6) DEFAULT NULL,
    lock_key varchar(36) DEFAULT NULL,
    lock_user varchar(255) DEFAULT NULL,
    md5 varchar(255) DEFAULT NULL,
    tenant_id varchar(36) DEFAULT NULL,
    update_date datetime(6) DEFAULT NULL,
    update_user varchar(255) DEFAULT NULL,
    version int(11) DEFAULT NULL,
    company_address varchar(255) DEFAULT NULL,
    company_email_domain varchar(255) DEFAULT NULL,
    company_name varchar(255) NOT NULL,
    company_telephone varchar(255) DEFAULT NULL,
    company_web_site varchar(255) DEFAULT NULL,
    industry varchar(255) DEFAULT NULL,
    legal_representative varchar(255) DEFAULT NULL,
    organization_code varchar(255) DEFAULT NULL,
    reg_number varchar(255) DEFAULT NULL,
    tax_reg_number varchar(255) DEFAULT NULL,
    uniform_credit_code varchar(255) DEFAULT NULL,
    PRIMARY KEY (id),
    UNIQUE KEY UKp880bnaaw1r7b8difpf0fwohk (company_name),
    KEY i_Tenant_companyName (company_name)
    ) ENGINE=InnoDB DEFAULT CHARSET=utf8 ROW_FORMAT=DYNAMIC;

tidb的表结构:
MySQL [midea_mss]> show create table sys_tenant\G
*************************** 1. row ***************************
Table: sys_tenant
Create Table: CREATE TABLE sys_tenant (
id varchar(36) NOT NULL,
create_date datetime(6) DEFAULT NULL,
create_user varchar(255) DEFAULT NULL,
is_locked varchar(255) DEFAULT NULL,
lock_date datetime(6) DEFAULT NULL,
lock_key varchar(36) DEFAULT NULL,
lock_user varchar(255) DEFAULT NULL,
md5 varchar(255) DEFAULT NULL,
tenant_id varchar(36) DEFAULT NULL,
update_date datetime(6) DEFAULT NULL,
update_user varchar(255) DEFAULT NULL,
version int(11) DEFAULT NULL,
company_address varchar(255) DEFAULT NULL,
company_email_domain varchar(255) DEFAULT NULL,
company_name varchar(255) NOT NULL,
company_telephone varchar(255) DEFAULT NULL,
company_web_site varchar(255) DEFAULT NULL,
industry varchar(255) DEFAULT NULL,
legal_representative varchar(255) DEFAULT NULL,
organization_code varchar(255) DEFAULT NULL,
reg_number varchar(255) DEFAULT NULL,
tax_reg_number varchar(255) DEFAULT NULL,
uniform_credit_code varchar(255) DEFAULT NULL,
PRIMARY KEY (id),
UNIQUE KEY UKp880bnaaw1r7b8difpf0fwohk (company_name),
KEY i_Tenant_companyName (company_name)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin
1 row in set (0.00 sec)

db级别的建库语句:
MySQL [midea_mss]> show create database midea_mss;
±----------±-------------------------------------------------------------------------------------------+
| Database | Create Database |
±----------±-------------------------------------------------------------------------------------------+
| midea_mss | CREATE DATABASE midea_mss /*!40100 DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci */ |
±----------±-------------------------------------------------------------------------------------------+
1 row in set (0.00 sec)

若提问为性能优化、故障排查类问题,请下载脚本运行。终端输出的打印结果,请务必全选并复制粘贴上传。

SHOW COLLATION;

看下是否支持

https://docs.pingcap.com/zh/tidb/stable/character-set-and-collation

首先在集群部署初始化时,就要开启新的排序框架配置,目前还不支持部署后再开启

然后可以指定某个 db 下的默认 collation,比如 alter database xxx collate utf8mb4_general_ci(目前还没有全局参数设置默认的 collation)

还可以指定 connection 上的默认 collation,通过 set names utf8mb4 collate utf8mb4_general_ci 设置(通过 show variables like ‘%collation%’ 查看当前的设置),这个是决定一个字面量的默认 collation 是什么,比如 select ‘a’ = ‘A’ 是否相等

1 个赞

集群在部署初始化的时候已经开启新的排序框架配置的了。
业务库也指定了默认的字符集和排序规则。


但是通过DM,从阿里云自建的只读MySQL同步全量的数据过来后,表级的校验规格仍然是默认的utf8_bin。。而非utf8_general_ci。可以看问题描述里面dm全量同步dump出来的建表语句和下游tidb生成的表的建表语句,是有差别的。

image

@Hacker_Nsl2Vb7f
您好,麻烦用 curl http://{TiDBIP}:10080/ddl/history 查下创建 sys_tenant 这个表的 query。


我在dm集群在全量同步的时候,处于dump过程中,直接去修改了create database的sql文件,加上了collate uft8_general_ci这个配置,但是通过查询curl http://{TiDBIP}:10080/ddl/history 发现是没有这个额外加的配置项的

从创建表的 query 来看,显式指定了 charset,但是没有指定 collation。这时候会使用 charset 对应的 default collation(utf8_bin),而不是 database 的。这一点与 MySQL 的行为是一致的。所以如果想修改同步过来的表的 collation,需要更改 create table 语句,显式指定 collation。

如果表不是特别多的话,可以直接先提前在 TiDB 中建好表,然后再开始使用 DM dump + load 数据。这样当表已经存在时,DM 会忽略这个 already exists 错误。