MySQL - дублирующее значение родительского столбца при вставке - PullRequest
1 голос
/ 07 марта 2019

Допустим, у меня есть три таблицы:

категории

| column | data_type   |
|--------|-------------|
| id     | int(10)     |
| code   | int(5)      |
| name   | varchar(50) |

депозиты

| column | data_type   |
|--------|-------------|
| id     | int(10)     |
| code   | int(5)      |
| name   | varchar(50) |

товар

| column        | data_type   |
|---------------|-------------|
| id            | int(10)     |
| category_id   | int(10)     |
| deposit_id    | int(10)     |
| category_code | int(5)      |
| deposit_code  | int(5)      |
| name          | varchar(50) |

Столбцы {parent}_id являются ограничениями внешнего ключа. {parent}_code - это обычные столбцы, которые должны совпадать в записях родительской таблицы.

Итак, по некоторым причинам я должен вставить тот же code (относительно родителя id) в таблицу items. На самом деле я выполняю кучу операторов select во время выполнения (приложение PHP) перед выполнением оператора insert. Что-то вроде:

// Begin transaction...
$categoryCode = Category::selectCode($categoryId);
$depositCode = Deposit::selectCode($depositId);

try {
  $item = Item::insert([
    'category_id' => $categoryId,
    'deposit_id' => $depositId,
    'category_code' => $categoryCode,
    'deposit_code' => $depositCode,
    'name' => $name,
  ]);
} catch (Exception $e) {
  // Rolling back...
}
// Commiting...

Это замедляет процесс и не обеспечивает целостности, основанные на столбцах code.

Я новичок в SQL, но я думаю, что лучшим подходом было бы заполнение этих столбцов автоматически прямо в операторе insert. Как продублировать столбцы {parent}_code на items детской таблице?

Ответы [ 2 ]

1 голос
/ 07 марта 2019

category_code и deposit_code не требуются в таблице элементов.

Таким образом, ваш пример кода становится

// Begin transaction...
//$categoryCode = Category::selectCode($categoryId);
//$depositCode = Deposit::selectCode($depositId);

try {
  $item = Item::insert([
    'category_id' => $categoryId,
    'deposit_id' => $depositId,
    'name' => $name,
  ]);
} catch (Exception $e) {
  // Rolling back...
}
// Commiting...

Когда вы хотите увидеть category_code и deposit_code этого предмета вы просто присоединяетесь к таблицам, используя category_id и deposit_id

SELECT i.name as item_name, c.category_code, d.deposit_code, ....
FROM item i
    JOIN category c ON c.id = i.category_id
    JOIN deposit d ON d.id = i.deposit_id
WHERE .......
1 голос
/ 07 марта 2019

в принципе, вам не нужно {parent} _code в таблице элементов.но иногда это необходимо.если они вам действительно нужны, вы можете сделать «вставить в select», а не «вставить в значения» (), queri выглядит следующим образом

INSERT INTO items (category_id, deposit_id, category_code, deposit_code, name)
SELECT c.category_id, d.deposit_id, c.category_code, d.category_code, {name_val}
FROM categories as c JOIN deposits as d 
  ON (c.category_id= {c_id} and d.deposit_id= {d_id})

это простое перекрестное соединение с указанным значением id.Стоимость ввода-вывода может соответствовать стоимости нескольких запросов.но это уменьшает количество выполнений.и это уменьшит общее время выполнения.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...