Копирование данных реляционной таблицы - PullRequest
5 голосов
/ 14 июля 2010

Надеюсь, я не слишком задумчив в этом вопросе, я просто хочу убедиться, что то, что я спрашиваю, совершенно ясно (я думаю, что это довольно запутанно:).

У меня есть база данных с кучей таблиц со всеми моими ограничениями внешнего ключа. Иногда отношения состоят из нескольких таблиц, и в некоторых случаях дочерний элемент связан с несколькими родительскими таблицами. Я хочу вставить копию одной из моих строк таблицы «верхнего уровня» и всех данных дочерней таблицы, которые с ней связаны (сохраняя реляционную целостность). То есть моя новая строка верхнего уровня получает свой новый первичный ключ (через auto_increment), а все новые дочерние строки получают свои собственные первичные ключи (снова через auto_increment), а вся информация внешнего ключа таблиц относится аналогично Данные, которые я скопировал (только теперь с вновь созданными первичными ключами). Так что теперь у меня будет копия реляционных данных, которые были независимо изменяемыми от оригинала.

Чтобы сделать мой пример более конкретным, я тщательно подготовил аналогичный, но более простой пример. Давайте определим следующие таблицы:

альтернативный текст http://www.freeimagehosting.net/uploads/ef22070a89.png

Все зеленые поля id являются первичными ключами auto_update, а желтоватые - это индексированные столбцы с ограничениями внешнего ключа. Допустим, в базе данных изначально есть следующие данные:

job_types
+----+----------+
| id | jobcode  |
+----+----------+
|  1 | DEADBEEF |
|  3 | FEEDFACE |
+----+----------+

managers
+----+---------------+-------------+
| id | name          | job_type_id |
+----+---------------+-------------+
|  1 | John          |           1 |
|  3 | Michael Scott |           3 |
+----+---------------+-------------+

departments
+----+------+------------+
| id | name | manager_id |
+----+------+------------+
|  1 | H32  |          1 |
|  2 | X11  |          3 |
+----+------+------------+

employees
+----+-------------+---------------+------------+-------------+
| id | name        | department_id | manager_id | job_type_id |
+----+-------------+---------------+------------+-------------+
|  1 | Billy Bob   |             1 |          1 |           1 |
|  2 | Sandra Lee  |             1 |          1 |           3 |
|  3 | Buddy Holly |             2 |          3 |           1 |
+----+-------------+---------------+------------+-------------+

Теперь скажите, что я хочу сделать, это сделать реляционную копию отдела H32 (id = 1).

Что я должен закончить, это что-то вроде следующего (очевидно, фактические значения первичных ключей не важны, ссылочная целостность это).

job_types
+----+----------+
| id | jobcode  |
+----+----------+
|  1 | DEADBEEF |
|  3 | FEEDFACE |
|  4 | DEADBEEF |
|  5 | FEEDFACE |
+----+----------+

managers
+----+---------------+-------------+
| id | name          | job_type_id |
+----+---------------+-------------+
|  1 | John          |           1 |
|  3 | Michael Scott |           3 |
|  4 | John          |           4 |
+----+---------------+-------------+

departments
+----+------+------------+
| id | name | manager_id |
+----+------+------------+
|  1 | H32  |          1 |
|  2 | X11  |          3 |
|  3 | H32  |          4 |
+----+------+------------+

employees
+----+-------------+---------------+------------+-------------+
| id | name        | department_id | manager_id | job_type_id |
+----+-------------+---------------+------------+-------------+
|  1 | Billy Bob   |             1 |          1 |           1 |
|  2 | Sandra Lee  |             1 |          1 |           3 |
|  3 | Buddy Holly |             2 |          3 |           1 |
|  4 | Billy Bob   |             3 |          4 |           4 |
|  5 | Sandra Lee  |             3 |          4 |           5 |
+----+-------------+---------------+------------+-------------+

Какой наиболее эффективный способ реализовать этот тип операции копирования? Для чего я стою, я работаю с MySQL, используя движок таблиц InnoDB, в контексте Grails. Я с нетерпением жду возможности услышать некоторые хорошие идеи о том, как вы делаете что-то вроде этого «правильного пути».

- С уважением, Вик

Я разместил MySQLDump примера инициализации на PasteBin.

EDIT Что бы это ни стоило, я разместил гораздо более простой / широкий вопрос здесь , и я получил в целом положительные ответы, предполагая, что я не "просто делаю это неправильно" ...

1 Ответ

1 голос
/ 16 ноября 2010

Я сделал то же самое, используя INSERT INTO ... SELECT синтаксис. (C api также имеет MYSQL_OPTION_MULTI_STATEMENTS_ON, который вы можете использовать для запуска нескольких операторов. Или вы можете использовать процедуру).

Это наиболее эффективно, поскольку вам не нужно перемещать данные между клиентом и сервером. Скопированное значение было шаблоном для создания нового объекта. Я не понимаю, почему вы делаете это с этой конкретной моделью данных.

...