本文档适用于单表形式的数据迁移。
表导出导入建议
表的操作顺序:
在进行MySQL向Hubble的数据迁移时,需要关注以下几点:
MySQL和Hubble数据类型不完全一致,需要进行数据类型转换。
MySQL和Hubble的语法也有所不同,需要进行语法转换。
在进行数据导入时,需要注意数据的完整性和一致性。
在导入数据之前,最好先备份原有数据,以防数据丢失。
推荐用dbeaver工具
insert
语句)例如:导出的文件命名为emp.sql
进行表结构修改:主要进行数据类型映射
数据类型映射
MySQL数据类型 | Hubble数据类型 |
---|---|
CHAR(n) | CHAR(n) |
CLOB | STRING |
DATE | DATE |
FLOAT(n) | DECIMAL(n) |
DECIMAL(m,n) | DECIMAL(m,n) |
DOUBLE | DECIMAL(m,n) |
JSON | JSON |
BLOB | BYTES |
VARCHAR(n) | VARCHAR(n) |
int(n) | int |
bigint64 | int64 |
bigint | INT8 |
TINYINT | INT |
SMALLINT | INT |
MEDIUMINT | INT |
TIMESTAMP(p) | TIMESTAMP |
TIME | TIME |
date | date |
datetime | datetime |
BOOLEAN | BOOL |
ENUM | ENUM |
默认情况下Hubble创建的数据库名与mysql当中一致,本示例mysql中的库名为guar
create database if not exists guar;
use guar;
create table guar.emp (
id int NOT NULL ,
name varchar(255) ,
sex varchar(255) ,
age int ,
zzms varchar(255) ,
eid int ,
PRIMARY KEY (id)
)
将文件(emp.sql)放置到可访问的位置(与certs同级别目录),如:/var/lib/hubble
下
hubble sql --certs-dir=/var/lib/hubble/certs --host=hubble01:15432 < emp.sql
mysql | hubble |
---|---|
ifnull() | coalesce() |
str1+str2 | str1 |
date_format | cast() 字符串转日期 |
date_format | experimental_strftime() 日期转字符串 |
FROM_UNIXTIME | 1668338530::timestamp(时间戳转日期) |
UNIX_TIMESTAMP | extract(epoch from cast('2022-11-13 11:22:10' as timestamp))::int(日期转时间戳) |
substring() | substring() |
replace() | replace() |
trim() | trim() |
ltrim() | ltrim() |
rtrim() | rtrim() |
lower() | lower() |
upper() | upper() |
now() | now() |
curdate() | current_date() |
date_add() | now() + interval '1 day' |
datediff() | age() |
sysdate() | now() |
用Hubble的序列替换Mysql的自增字段
Mysql中形式:
CREATE TABLE test_col (
id INT(8) NOT null auto_increment primary key,
name VARCHAR(100) NOT null,
age int(1)
);
Hubble中形式:
create sequence userid_seq;
create table test_col(
id int PRIMARY KEY DEFAULT nextval('userid_seq'),
name string,
age int
);
bit类型或者在mysql的迁移脚本中处理为bool
,或者处理为int64
。 这里有个注意的点,即使处理为bool
,insert
语句中也不可以处理为true
或者false
。 需要处理为0和1,0来代表false
,1来代表true
。另外sql中注意对bit的语句的where
条件='f'
或者='t'
,需要改为='0'
和='1'
。
find_in_set()
函数问题find_in_set()
(查询字段(strlist) 中是否包含(str)的结果)在Hubble中需要用string_to_array()
和ANY()
这两个函数来代替,也可以用string_to_array()
和和array_position()
来代替
MySQL中支持隐式类型转换,但是Hubble需要强转语法是 : 字段::数据类型,例如:id::varchar
,项目中常遇见的时间戳转日期
select 1668338530::timestamp;
MySQL中分页配置是pagehelper.helperDialect=mysql
,在Hubble中用的话需要先把这个配置注释掉,在加上pagehelper.auto-dialect=true和pagehelper.auto-runtime-dialect=true
这两个配置
''
单引号转,Hubble是加""
双引号转。order
字段为关键字的mysql用单引号形式:
CREATE TABLE test_col (
id INT(8) NOT NULL,
name VARCHAR(100) NOT NULL,
`order` INT(8) NOT NULL,
PRIMARY KEY (`id`)
);
order
字段为关键字的Hubble用双引号形式:
CREATE TABLE test_col (
id INT8 NOT NULL,
name VARCHAR(100) NOT NULL,
"order" INT8 NOT NULL,
PRIMARY KEY (id)
);
database()
函数要用Hubble中current_database()
函数来代替。mysql:select database()
等同于Hubble:select current_database()
split failed while applying backpressure to Put
错误split failed while applying backpressure to Put
错误引起的原因是Hubble使用了MVCC,而如果单表中数据频繁更新,导致键值过大就会进行拆分,单个键值拆分时会导致这个错误发生。常用的解决方法可以是修改表的gc ttl(默认是24小时),alter table test_a CONFIGURE ZONE using gc.ttlseconds = 1800
;将表的ttl时间改为1800秒,这存在的问题是会导致数据库回滚时,恢复时只能恢复1800秒之内的。另外一种方式是在配置中加大分片的大小。还有一种是将频繁更新的字段作为单独的表列族来使用,这样会减少更新时mvcc值的大小。