CakePHP обновляется, когда он должен вставлять модель hasAndBelongsToMany
-
20-09-2019 - |
Вопрос
У меня есть небольшая проблема.Я создаю сайт, на котором есть теги и вопросы.У меня есть модель вопроса, модель тега, модель QuestionsTag, все прекрасно сочетается друг с другом.Пользователь, задавая что-либо, помещает теги в поле, разделенное пробелом (foo bar baz), как и в stackoverflow.com.
Теперь, вот код для проверки, существует ли тег уже или нет, и ввода тега в базу данных и требуемых ассоциаций:
function create () {
if (!empty($this->data)) {
$this->data['Question']['user_id'] = 1;
$question = $this->Question->save ($this->data);
/**
* Preverimo če se je vprašanje shranilo, če se je,
* vprašanje označimo.
*/
if ($question) {
$tags = explode (' ', $this->data['Question']['tags']);
foreach ($tags as $tag){
if (($tagId = $this->Tag->existsByName($tag)) != false) {
/**
* Značka že obstaja, torej samo povezemo trenuten
* id z vprašanjem
*/
$this->QuestionsTag->save (array(
'question_id' => $this->Question->id,
'tag_id' => $tagId
));
}
else {
/**
* Značka še ne obstaja, jo ustvarimo!
*/
$this->Tag->save (array(
'name' => $tag
));
// Sedaj pa shranimo
$this->QuestionsTag->save(array(
'question_id' => $this->Question->id,
'tag_id' => $this->Tag->id
));
$this->Tag->id = false;
}
; }
}
}
}
Проблема в следующем: вопрос имеет идентификатор 1, и я хочу, чтобы у него были теги с идентификаторами 1, 2, 3.
Когда вызываются 2-е и 3-е сохранения, Cake видит, что в таблице questions_tags уже есть вопрос с идентификатором 1, поэтому он просто обновляет тег.
Но это неверно, так как в этой таблице должно быть много вопросов с одинаковым идентификатором, поскольку они относятся к разным тегам, принадлежащим им.
Итак, есть ли способ предотвратить это?Запретить обновление метода сохранения?
Спасибо!
Решение
Такое поведение не характерно для отношений HABTM.Вы вызываете save()
метод внутри цикла.После первого сохранения, id
значение установлено, и каждый последующий вызов сохранения видит идентификатор и предполагает, что это обновление.Внутри цикла вам сначала нужно вызвать model->create()
чтобы сбросить значение идентификатора, которое может существовать.
Из документов CakePHP по адресу http://book.cakephp.org/view/75/Saving-Your-Data:
При вызове save в цикле не забудьте вызвать create().
В вашем случае это выглядело бы примерно так:
$this->QuestionsTag->create();
$this->QuestionsTag->save (array(
'question_id' => $this->Question->id,
'tag_id' => $tagId
));
Другие советы
Проверьте Сохранить все.Вы можете сделать один звонок в $this->Question->saveAll()
, и это также сохранит все связанные данные, которые вы предоставляете.Обратите внимание, что с данными HABTM он будет выполнять DELETE
для любого questions_tags
связанный с этим question_id
, затем выполните INSERT
для всех tag_id
это включено в ваши данные.
если вы хотите убедиться, что сделана новая запись (INSERT), а не обновление, вы можете установить $this->create();
прямо перед вызовом сохранения.Видишь http://book.cakephp.org/view/75/Saving-Your-Data (в верхней части страницы):При вызове save в цикле не забудьте вызвать create().