Доступ к детям от родителей должен работать. И наоборот тоже.
Прежде всего, убедитесь, что ваш конструктор объявляет новую коллекцию ArrayCollection для ваших детей. Очень важно при использовании отношения OneToMany, потому что Doctrine использует ArrayCollection для правильной загрузки дочерних данных.
use Doctrine\Common\Collections\ArrayCollection;
...
public function __construct(){
$this->children = new ArrayCollection();
}
Если это все еще не работает, я бы предложил изменить режим выборки для вашей сущности. mapping.
/**
* @ORM\OneToMany(targetEntity="App\Entity\Menu", mappedBy="parent", fetch="EAGER")
*/
private $children;
Осторожно, режим активного извлечения загрузит полный массив при первом извлечении БД. Обычно doctrine будет использовать отложенную загрузку, которая вызывает вызов БД при использовании метода get (). Режим активной выборки может быть опасным, потому что каждый раз, когда вы будете запрашивать меню, будут загружены также все дочерние элементы, что может привести к большим накладным расходам.
Надеюсь, это поможет!
РЕДАКТИРОВАТЬ: Существует Я думаю, что вы можете попробовать эту аннотацию, чтобы она работала с отложенной загрузкой. Аннотация: @ORM \ JoinColumn.
/**
* @ORM\ManyToOne(targetEntity="App\Entity\Menu", inversedBy="children", fetch="LAZY")
* @ORM\JoinColumn(name="parent_id", referencedColumnName="id", onUpdate="CASCADE", onDelete="CASCADE")
*/
protected $parent;
Это может все еще не работать, есть специфическое c поведение с самоссылающимися сущностями, вы можете прочитать об этом здесь: Doctrine - самоссылающаяся сущность - отключить выборку дочерних элементов В нем говорится о том, что коллекции могут не инициализироваться должным образом при работе с самоссылающимися сущностями.
Что касается извлечения с нетерпением, то оно должно загрузить все дерево, но это ограничение к этому. Ограничением является фактическое MySQL количество лимитов соединения (по умолчанию 64 из памяти). Это может быть сделано довольно быстро.
Если вам когда-нибудь понадобится загрузить все меню, структурированное как дерево, я бы предложил запросить всю таблицу в виде плоского массива, а затем построить дерево с помощью функции, упомянутой здесь Построить дерево из плоского массива в PHP. Поэтому 1 запрос вместо N запросов в зависимости от количества веток в вашем дереве. Если вам когда-либо понадобится загрузить меню из указанного узла c внутри дерева в качестве начальной точки, вы можете запросить только результат из родительского узла, который вы хотите, в виде плоских данных, а затем снова построить дерево. Как показано здесь Как создать MySQL иерархический рекурсивный запрос