迁移行以导入到现有数据库,负责更改ID等

St.*_*son 7 mysql data-migration mysqldump

这样做的目的是将一些行从一个环境复制到另一个环境而不覆盖现有行.

样本数据库:

INSERT INTO `school` (school_id,name) VALUES (15,'Middle');
INSERT INTO `class` (class_id,school_id,name) VALUES (12,15,'Sample');
Run Code Online (Sandbox Code Playgroud)

我们的想法是school_idclass_id有自动递增,并class有一个外键链接回school.但我想转储只是这些行并把它们插入到已经有其他数据库school_id的15.

它可能是这样的东西:

INSERT INTO `school` (name) VALUES ('Middle');
INSERT INTO `class` (school_id,name) VALUES (LAST_INSERT_ID(),'Sample');
Run Code Online (Sandbox Code Playgroud)

但那只是为了这个简单的例子.想象一下,如果我有50个班级,每个班级有25名学生,每个学生/班级组合有几百个等级.如果LAST_INSERT_ID()不将其存储在一系列变量中,您可以看到它可能无法工作.

做这种操作的适当工具是什么?可以mysqldump做任何聪明的事吗?

Dev*_*art 4

你可以这样做:

  • school_id在目标表中查找 MAX school-

    SELECT MAX(school_id) INTO @max_school_id FROM school;

  • 更改school_id源表中的所有值 ( school, class) - 添加school_id上一点的 MAX -

    UPDATE school SET school_id = school_id + @max_school_id + 1;

向外键添加操作可能非常有用ON UPDATE CASCADE,它将有助于school_id自动更改子表,例如 -

ALTER TABLE class
  DROP FOREIGN KEY FK_name;
ALTER TABLE class
  ADD CONSTRAINT FK_name FOREIGN KEY (school_id)
    REFERENCES school(school_id) ON UPDATE CASCADE;
Run Code Online (Sandbox Code Playgroud)
  • 转储并导入。

解释和例子:

创建源表:

CREATE TABLE school(
  school_id INT PRIMARY KEY AUTO_INCREMENT,
  name VARCHAR(20)
);

INSERT INTO school (school_id, name) VALUES
  (1, 'Middle1'),
  (2, 'Middle2'),
  (3, 'Middle3'),
  (15, 'Middle');

CREATE TABLE class(
  class_id INT(11) NOT NULL,
  school_id INT(11) DEFAULT NULL,
  name VARCHAR(20) DEFAULT NULL,
  PRIMARY KEY (class_id),
  CONSTRAINT FK_class_school_school_id FOREIGN KEY (school_id)
  REFERENCES school (school_id) ON DELETE RESTRICT ON UPDATE CASCADE
)
ENGINE = INNODB;

INSERT INTO class (class_id, school_id, name) VALUES (11, 1, 'Sample1');
INSERT INTO class (class_id, school_id, name) VALUES (12, 15, 'Sample');
Run Code Online (Sandbox Code Playgroud)

创建目标表:

CREATE TABLE school(
  school_id INT PRIMARY KEY AUTO_INCREMENT,
  name VARCHAR(20)
);

INSERT INTO school (school_id, name) VALUES
  (1, 'Top'),
  (2, 'Middle'),
  (3, 'Bottom'),
  (15, 'Top');

CREATE TABLE class(
  class_id INT(11) NOT NULL,
  school_id INT(11) DEFAULT NULL,
  name VARCHAR(20) DEFAULT NULL,
  PRIMARY KEY (class_id),
  CONSTRAINT FK_class_school_school_id FOREIGN KEY (school_id)
  REFERENCES school (school_id) ON DELETE RESTRICT ON UPDATE CASCADE
)
ENGINE = INNODB;

INSERT INTO class (class_id, school_id, name) VALUES (10, 2, 'Sample2');
INSERT INTO class (class_id, school_id, name) VALUES (12, 15, 'Sample');
Run Code Online (Sandbox Code Playgroud)

更新源表,增加 id 值: 我们应该更新所有唯一值,在我们的例子中,我们必须class_idclass表和school_id表中进行更新school

查找class_idTARGETclass表的最大值

SELECT MAX(class_id) + 1000 FROM class; -- This will return => 1012
Run Code Online (Sandbox Code Playgroud)

增加所有 SOURCEclass_idclass_id + 1012

UPDATE class SET class_id = class_id + 1012;
Run Code Online (Sandbox Code Playgroud)

查找school_idTARGETschool表的最大值

SELECT max(school_id) + 1000 FROM school; -- This will return =>1015
Run Code Online (Sandbox Code Playgroud)

增加所有 SOURCEschool_idschool_id + 1015

UPDATE school SET school_id = school_id + 1015;
Run Code Online (Sandbox Code Playgroud)

就这些。我们可以转储源表:

INSERT INTO school VALUES
  (1016, 'Middle1'),
  (1017, 'Middle2'),
  (1018, 'Middle3'),
  (1030, 'Middle');

INSERT INTO class VALUES
  (1023, 1016, 'Sample1'),
  (1024, 1030, 'Sample');
Run Code Online (Sandbox Code Playgroud)

现在我们可以轻松地针对目标数据库运行此脚本。