Symfony2, Doctrine2 - display items by Category wi

2019-02-16 03:03发布

I'm creating second route for display all articles by category in the URL. There is my route for that:

default_blog_category:
    path:     /category/{slug}/{page}
    defaults: { _controller: AcmeBlogBundle:Default:indexByCategory, page: 1 }

And here is my try, to get items by category, but it does not works (I'll get this error message:

[Semantical Error] line 0, col 47 near 'categories =': Error: Invalid PathExpression. StateFieldPathExpression or SingleValuedAssociationField expected.

):

public function indexByCategoryAction($slug, $page)
{
    $em = $this->getDoctrine()->getManager();
    $dql = "SELECT a FROM AcmeBlogBundle:Article a WHERE a.categories = :category ORDER BY a.published DESC";
    $query = $em->createQuery($dql)->setParameter('category', $slug);

    $paginator = $this->get('knp_paginator');
    $pagination = $paginator->paginate(
        $query,
        $this->get('request')->query->get('page', $page),
        10
    );

    return $this->render('AcmeBlogBundle:Default:index.html.twig', array('pagination' => $pagination));
}

I'm not sure, how to use WHERE in my query for now, here is also my Article.php entity:

<?php

namespace Acme\BlogBundle\Entity;

use Doctrine\ORM\Mapping as ORM;
use Symfony\Component\Validator\Constraints as Assert;
use Gedmo\Mapping\Annotation as Gedmo;

/**
 * @ORM\Entity(repositoryClass="Acme\BlogBundle\Entity\ArticleRepository")
 * @ORM\Table(name="articles") 
 */
class Article
{
    /**
     * @ORM\Id
     * @ORM\Column(type="integer")
     * @ORM\GeneratedValue(strategy="AUTO")
     */
    private $id;              

    /**
     * @ORM\Column(type="string", length=200)    
     * @Assert\NotBlank(
     *      message = "Title cannot be blank"      
     * )    
     * @Assert\Length(
     *      min = "3",
     *      minMessage = "Title is too short"         
     * )     
     */     
    private $title;

    /**
     * @Gedmo\Slug(fields={"title"}, updatable=true, separator="-") 
     * 
     * @ORM\Column(name="slug", type="string", length=200, nullable=false, unique=true)
     */
    private $slug;

    /**
     * @ORM\Column(type="datetime")    
     * @Assert\NotBlank(
     *      message = "DateTime cannot be blank"
     * )
     * @Assert\DateTime(
     *      message = "DateTime is not valid"
     * )     
     */
    protected $published;

    /**
     * @ORM\ManyToMany(targetEntity="Category", inversedBy="articles")
     * @Assert\Count(min = 1, minMessage = "Choose any category") 
     */
    private $categories;

    /**
     * @ORM\OneToMany(targetEntity="Comment", mappedBy="article")
     * @ORM\OrderBy({"published" = "ASC"})     
     */
    private $comments;                       

    /**
     * @ORM\Column(type="text")
     * @Assert\NotBlank(
     *      message = "Perex cannot be blank"      
     * )    
     * @Assert\Length(
     *      min = "5",
     *      minMessage = "Perex is too short"         
     * )     
     */
    private $perex;

    /**
     * @ORM\Column(type="text")
     * @Assert\NotBlank(
     *      message = "Content cannot be blank"      
     * )    
     * @Assert\Length(
     *      min = "10",
     *      minMessage = "Content must have min. 10 characters"         
     * )     
     */
    private $content;

    /**
     * @ORM\Column(type="string", length=200)     
     */     
    private $description;

    /**
     * @ORM\Column(type="string", length=200)     
     */     
    private $keywords;

    /**
     * Constructor
     */
    public function __construct()
    {
        $this->categories = new \Doctrine\Common\Collections\ArrayCollection();
        $this->comments = new \Doctrine\Common\Collections\ArrayCollection();
    }

    /**
     * Get id
     *
     * @return integer 
     */
    public function getId()
    {
        return $this->id;
    }

    /**
     * Set title
     *
     * @param string $title
     * @return Article
     */
    public function setTitle($title)
    {
        $this->title = $title;

        return $this;
    }

    /**
     * Get title
     *
     * @return string 
     */
    public function getTitle()
    {
        return $this->title;
    }

    /**
     * Set slug
     *
     * @param string $slug
     * @return Article
     */
    public function setSlug($slug)
    {
        $this->slug = $slug;

        return $this;
    }

    /**
     * Get slug
     *
     * @return string 
     */
    public function getSlug()
    {
        return $this->slug;
    }

    /**
     * Set content
     *
     * @param string $content
     * @return Article
     */
    public function setContent($content)
    {
        $this->content = $content;

        return $this;
    }

    /**
     * Get content
     *
     * @return string 
     */
    public function getContent()
    {
        return $this->content;
    }

    /**
     * Add categories
     *
     * @param \Acme\BlogBundle\Entity\Category $categories
     * @return Article
     */
    public function addCategory(\Acme\BlogBundle\Entity\Category $categories)
    {
        //$this->categories[] = $categories;

       //return $this;
       if (!$this->categories->contains($categories)) {
            $this->categories->add($categories);
            $categories->addArticle($this);
        }
    }

    /**
     * Remove categories
     *
     * @param \Acme\BlogBundle\Entity\Category $categories
     */
    public function removeCategory(\Acme\BlogBundle\Entity\Category $categories)
    {
        $this->categories->removeElement($categories);
    }

    /**
     * Get categories
     *
     * @return \Doctrine\Common\Collections\Collection 
     */
    public function getCategories()
    {
        return $this->categories;
    }

    /**
     * Add comments
     *
     * @param \Acme\BlogBundle\Entity\Comment $comments
     * @return Article
     */
    public function addComment(\Acme\BlogBundle\Entity\Comment $comments)
    {
        $this->comments[] = $comments;

        return $this;
    }

    /**
     * Remove comments
     *
     * @param \Acme\BlogBundle\Entity\Comment $comments
     */
    public function removeComment(\Acme\BlogBundle\Entity\Comment $comments)
    {
        $this->comments->removeElement($comments);
    }

    /**
     * Get comments
     *
     * @return \Doctrine\Common\Collections\Collection 
     */
    public function getComments()
    {
        return $this->comments;
    }

    /**
     * Set published
     *
     * @param \DateTime $published
     * @return Article
     */
    public function setPublished($published)
    {
        $this->published = $published;

        return $this;
    }

    /**
     * Get published
     *
     * @return \DateTime 
     */
    public function getPublished()
    {
        return $this->published;
    }

    /**
     * Set description
     *
     * @param string $description
     * @return Article
     */
    public function setDescription($description)
    {
        $this->description = $description;

        return $this;
    }

    /**
     * Get description
     *
     * @return string 
     */
    public function getDescription()
    {
        return $this->description;
    }

    /**
     * Set keywords
     *
     * @param string $keywords
     * @return Article
     */
    public function setKeywords($keywords)
    {
        $this->keywords = $keywords;

        return $this;
    }

    /**
     * Get keywords
     *
     * @return string 
     */
    public function getKeywords()
    {
        return $this->keywords;
    }

    /**
     * Set perex
     *
     * @param string $perex
     * @return Article
     */
    public function setPerex($perex)
    {
        $this->perex = $perex;

        return $this;
    }

    /**
     * Get perex
     *
     * @return string 
     */
    public function getPerex()
    {
        return $this->perex;
    }
}

Any idea?

1条回答
beautiful°
2楼-- · 2019-02-16 03:53

You have to join the categories. This code should be placed in the ArticleRepository.

$qb = $this->createQueryBuilder('a');
$qb->add('select', 'a');
$qb->leftJoin('a.category', 'c');
$qb->where('c.name LIKE :category'); /* i have guessed a.name */
$qb->setParameter('category', $slug);
$qb->getQuery()->getResult();

See doctrine query builder and symfony custom repository classes for an tutorial.

查看更多
登录 后发表回答