Venu は正しいです。doctrine に基づくカスタム symfony ルーティングはこれを行う方法を提供します。唯一の複雑さは、親ページのスラッグを追加してスラッグ パラメータを構築し、孫ページにgrandparent-slug/parent-slug/child-slug
例外がスローされるようなスラッグがある場合にのみ発生します。 .
私が与えた例のようにルーティングを使用してスラッグを照合しましたが、注釈に正規表現が必要でした:
/**
* @Route("{slug}", name="page_index", defaults={"slug" = false}, requirements={"slug" = "[0-9a-zA-Z\/\-]*"})
* @Template()
*/
public function indexAction($slug)
{
if ($slug !== false) {
$page = $this->findPage($slug);
上記の要件の注釈は、スラッグがスラッシュとハイフンを含む英数字であってもよいことを意味します。findPage($slug)
次に、スラッグをスラッシュで分解し、正しい子ページを見つけるメソッドを実装する必要があります。
ルートは他の多くのルートと一致するため、このコントローラーを routing.yml ファイルの最後に含め、このアクションをコントローラーのパブリック アクションの最後に含めて、他のすべてのルートが最初に一致するようにすることが重要です。
編集
これは、上記のスラッグからページを見つけるために作成した findPage メソッドです。
protected function findPage($slug_string, $first_page = false)
{
$slug_array = explode("/", $slug_string);
$slug = array_shift($slug_array);
$page = $this->em->getRepository("PagesBundle:Page")->getPageBySlug($slug, $this->site_id);
if (!$page) {
return false;
}
// if only the first matched page is required return it
if ($first_page) {
return $page;
}
// Otherwise loop through the slug array and match recursive
//children until slug array is empty or no match found
while (!empty($slug_array)) {
if ($page->getChildren()) {
$slug = array_shift($slug_array);
foreach ($page->getChildren() as $child_page) {
if ($child_page->getSlug() == $slug) {
$page = $child_page;
break;
}
}
} else {
return false;
}
}
return $page;
}