При вставке сущности с ассоциациями есть ли способ просто использовать FK вместо извлечения сущности?
Мне нужно вставить объект, у которого есть ассоциации.
Если у меня уже есть FK связанных сущностей, есть ли способ вставить первичную сущность в БД только с заполненными FK?
Или я всегда должен
- извлеките связанные сущности с помощью FK,
- заполните свойства первичной сущности, относящиеся к ассоциациям,
- , а затем вызовите метод persist.
4 answers
Вам нужен ссылочный прокси-сервер
Допустим, у меня есть Сообщения и теги. Сообщение имеет множество Тегов. Я получаю кучу тегов от пользователя, который поставил кучу флажков.
Следующее добавит теги в существующую запись, не извлекая сначала каждый объект тега. Он делает это с помощью ссылочных прокси-серверов, сгенерированных EntityManager::getReference()
:
$tag_ids = $_POST['tag_id']; // an array of integers representing tag IDs.
$post = $em->getRepository('Post')->find($post_id); // returns a Post entity.
foreach($tags_ids as $tid){
$post->addTag($em->getReference('Tag',$tid));
}
$em->persist($post);
$em->flush();
В отношении использования ссылочный прокси-сервер
В моих исследованиях это лишь частично является решением, следующим образом:
Да, вам не нужно активно извлекать связанную запись (потому что вы создаете запись прокси-сервера), но когда вы удаляете (фиксируете) транзакцию обновления, она все равно сначала выполняет инструкцию select для извлечения связанной записи, а затем только выполняет обновление (все за один заход в бд).
Это неэффективно и не должно быть необходимым (у нас есть идентификатор внешнего ключа, зачем извлекать запись..?)
Таким образом, хотя это и не полное решение, вы получаете только одно подключение к базе данных (что хорошо) и немного упрощенный код.
Я не уверен, есть ли решение этой проблемы на данный момент...??
Надеюсь, в будущем модули доктрины будут обновляться, и при использовании логики прокси мы должны получить автоматическое повышение производительности...
Вы должны получить объект, который должен быть связан, и установить связь.
Я предполагаю, что вы могли бы вручную указать взаимосвязь, напрямую обращаясь к базе данных через уровень DBAL, но я бы не рекомендовал этого, и я не пробовал.
Вы можете сделать это с помощью EntityManager::объединить
$post = new Post();
$post->setPostCategory(['id' => 1]);
$em->persist($em->merge($post));
$em->flush();