数据库迁移:MySQL->PostgreSQL注意问题汇总(基于项目并不完整)

因为项目原因,需要把原来MySQL数据库上的数据全部迁移到PostgreSQL。两者都是很优秀的开源数据库,但在国内,MySQL要比PostgreSQL普及,看资料PostgreSQL在处理高并发和数据类型支持上要好于MySQL,这也是我们项目进行数据库迁移的主要原因。

在迁移过程中,我主要遇到了一下几个问题:

1 部分数据类别不通用

在项目中遇到了主要以下几种数据类别需要转换(前面为MySQL数据类别,后面为PostgreSQL,数据类别括号中的n表示具体数字):

bigint(n)->bigint;

double->double precision或者float8;

datetime->timestamp;

项目中用到的差不多就这些,其余的用到再查。

2.命名规则和大小写

在MySQL中,有关数据库,表名和字段的命名,会采用“··”符号(即键盘上Esc键下面的印有~符号的键)而这在PostgreSQL中是不允许的,PostgreSQL中要么使用双引号包起来,要么直接不加任何标记。

MySQL创建表sys_user:

CREATE TABLE `sys_user` (
  `USER_ID` varchar(100) NOT NULL,
  `USERNAME` varchar(255) DEFAULT NULL,
  `PASSWORD` varchar(255) DEFAULT NULL,
  `NAME` varchar(255) DEFAULT NULL,
  `RIGHTS` varchar(255) DEFAULT NULL,
  `ROLE_ID` varchar(100) DEFAULT NULL,
  `LAST_LOGIN` varchar(255) DEFAULT NULL,
  `IP` varchar(100) DEFAULT NULL,
  `EMAIL` varchar(32) DEFAULT NULL,
  `NUMBER` varchar(100) DEFAULT NULL,
  `PHONE` varchar(32) DEFAULT NULL,
  PRIMARY KEY (`USER_ID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
用PostgreSQL创建表sys_user:
CREATE TABLE sys_user (
  USER_ID varchar(100) NOT NULL,
  USERNAME varchar(255) DEFAULT NULL,
  PASSWORD varchar(255) DEFAULT NULL,
  NAME varchar(255) DEFAULT NULL,
  RIGHTS varchar(255) DEFAULT NULL,
  ROLE_ID varchar(100) DEFAULT NULL,
  LAST_LOGIN varchar(255) DEFAULT NULL,
  IP varchar(100) DEFAULT NULL,
  EMAIL varchar(32) DEFAULT NULL,
  PHONE varchar(32) DEFAULT NULL,
  PRIMARY KEY (USER_ID)
);

在这里还有特别重要的一点需要注意,在PostgreSQL中,如果表名,字段名不加双引号,则建表的时候都会被默认转换为小写,如果想在命名中包括大写必须用双引号包起来。

3.实现表中某字段的自增

在MySQL中实现该功能很简单,如下面脚本所示:
CREATE TABLE `sys_file` (
  `id` bigint(20) NOT NULL AUTO_INCREMENT,
  `filename` varchar(1000) NOT NULL,
  `renames` varchar(1000) NOT NULL,
  `path` varchar(10000) NOT NULL,
  `userid` varchar(200) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=170 DEFAULT CHARSET=utf8;

在上面MySQL脚本中,表sys_file中id字段就实现了自增,即有新的数据插入时id会自动增加,可以看到在MySQL中有关键字AUTO_INCREMENT即可实现。
在PostgreSQL中的实现:

CREATE SEQUENCE sys_file_id_seq INCREMENT BY 1 MINVALUE 1 NO MAXVALUE START WITH 170;
CREATE TABLE sys_file (
  id bigint NOT NULL DEFAULT NEXTVAL('sys_file_id_seq'),
  filename varchar(1000) NOT NULL,
  renames varchar(1000) NOT NULL,
  path varchar(10000) NOT NULL,
  userid varchar(200) NOT NULL,
  PRIMARY KEY (id)
);

从脚本可以看到在PostgreSQL中实现自增还需要生成一个sequence再调用它才能实现。在生成sequence语句中,后面有几个参数,从左到右依次表示:该序列的步长,允许最小值,允许最大值(在上面代码中为NO MAXVALUE即没定义最大值),起始值。

4.时间戳的更新

在MySQL实现如下代码所示:
CREATE TABLE `sys_file` (
  `id` bigint(20) NOT NULL AUTO_INCREMENT,
  `filename` varchar(1000) NOT NULL,
  `renames` varchar(1000) NOT NULL,
  `path` varchar(10000) NOT NULL,
  `createtime` timestamp NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
  `userid` varchar(200) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=170 DEFAULT CHARSET=utf8;
如上述代码中新增的createtime字段,就实现了时间戳的自动更新(ON UPDATE CURRENT_TIMESTAMP),在PostgreSQL中的实现较为复杂:
 
   
CREATE TABLE sys_file (
  id bigint NOT NULL DEFAULT NEXTVAL('sys_file_id_seq'),
  filename varchar(1000) NOT NULL,
  renames varchar(1000) NOT NULL,
  path varchar(10000) NOT NULL,
  createtime timestamp,
  userid varchar(200) NOT NULL,
  PRIMARY KEY (id)
);

CREATE OR REPLACE FUNCTION update_timestamp_sys_file()
RETURNS TRIGGER AS $$
BEGIN
   NEW.createtime = now(); 
   RETURN NEW;
END;
$$ language 'plpgsql';

CREATE TRIGGER update_sys_file_createtime BEFORE UPDATE
    ON sys_file FOR EACH ROW EXECUTE PROCEDURE 
    update_timestamp_sys_file();
如上述代码所示,在PostgreSQL中实现该功能,首先需要创建函数(CREATE OR REPLACE FUNCTION update_timestamp_sys_file()),然后创建触发器(CREATE TRIGGER)。
 
   

5. 注解的实现

MySQL:
CREATE TABLE `sys_link` (
  `stiename` varchar(100) DEFAULT NULL COMMENT '友情链接网站名称',
  `sitecontent` varchar(200) DEFAULT NULL COMMENT '友情链接网站内容',
  `type` char(2) DEFAULT '0' COMMENT '类型  0为文字连接,1为图片连接',
  `stieurl` varchar(200) DEFAULT NULL COMMENT '图片连接地址',
  `addtime` varchar(50) DEFAULT NULL COMMENT '添加时间',
  `uptime` varchar(50) DEFAULT NULL COMMENT '修改时间',
  `status` char(2) DEFAULT '0' COMMENT '状态  0为未启用,1为启用',
  `sequence` int(10) DEFAULT NULL COMMENT '排序',
  `tourl` varchar(255) DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8;
如上述代码所示,在MySQL实现注解只需在字段后面加上‘COMMENT’即可,在PostgreSQL中实现如下所示:
 
   
CREATE TABLE sys_link (
  sitename varchar(100) DEFAULT NULL,
  sitecontent varchar(200) DEFAULT NULL,
  type char(2) DEFAULT '0',
  siteurl varchar(200) DEFAULT NULL,
  addtime varchar(50) DEFAULT NULL,
  uptime varchar(50) DEFAULT NULL,
  status char(2) DEFAULT '0',
  sequence int DEFAULT NULL,
  tourl varchar(255) DEFAULT NULL,
  PRIMARY KEY (id)
);
COMMENT ON COLUMN sys_link.id IS '友情链接ID';
COMMENT ON COLUMN sys_link.sitename IS '友情链接网站名称';
COMMENT ON COLUMN sys_link.sitecontent IS '友情链接网站内容';
COMMENT ON COLUMN sys_link.type IS '类型  0为文字连接,1为图片连接';
COMMENT ON COLUMN sys_link.siteurl IS '图片连接地址';
COMMENT ON COLUMN sys_link.addtime IS  '添加时间';
COMMENT ON COLUMN sys_link.uptime IS '修改时间';
COMMENT ON COLUMN sys_link.status IS '状态  0为未启用,1为启用';
COMMENT ON COLUMN sys_link.sequence IS '排序';

你可能感兴趣的:(Database)