拥有这些表,实体(伪代码以显示关系)。
article
id
name
author_id
type_id
category_id
author
id
name
type
id
name
category
id
name
现在在我的控制器中,我这样做
public function indexAction()
{
$articles = $this->getDoctrine()
->getRepository('AppBundle:Articles')
->findAll();
$authors = $this->getDoctrine()
->getRepository('AppBundle:Author');
$types = $this->getDoctrine()
->getRepository('AppBundle:Type');
$categories = $this->getDoctrine()
->getRepository('AppBundle:Category');
return $this->render('article/index.html.twig', array(
'articles' => $articles,
'authors' => $authors,
'types' => $types,
'categories' => $categories
));
}
在我看来,这个:
<tbody>
{% for exploit in exploits %}
<tr>
<th scope="row">{{ article.id }}</th>
<td>{{ article.name }}</td>
<td> {{ authors.findOneById(article.author) }} </td>
<td> {{ types.findOneById(article.type) }} </td>
<td> {{ categories.findOneById(article.category) }} </td>
<td>{{ article.date|date('F j, Y, g:i a') }}</td>
<td>
<a href="/details/{{ article.id }}" class="btn btn-success">View</a>
<a href="/edit/{{ article.id }}" class="btn btn-default">Edit</a>
<a href="/delete/{{ article.id }}" class="btn btn-danger">Delete</a>
</td>
</tr>
{% endfor %}
</tbody>
这样可行,但它会对每个条目执行查询,这不是最佳选择。
如何在Controller和View中更容易地显示它?没有这么多的查询,只有一个。
谢谢,
更新3:
按照Salah的建议,但仍然是同样的错误:
Impossible to access an attribute ("name") on a integer variable ("1").
我现在使用Exploit Entity。而不是Article Entity。
::::::::::::::
Author.php
::::::::::::::
<?php
namespace AppBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
use AppBundle\Entity\Exploit;
/**
* Author
*
* @ORM\Table(name="author", indexes={@ORM\Index(name="author_name_id_idx", columns={"id"})})
* @ORM\Entity
*/
class Author
{
/**
* @ORM\Id
* @ORM\GeneratedValue(strategy="NONE")
*/
private $id;
/**
* @var string
*
* @ORM\Column(name="name", author="string", length=255, nullable=false)
*/
private $name;
/**
* @ORM\OneToMany(targetEntity="AppBundle\Entity\Exploit", mappedBy="author", cascade={"persist", "remove"})
* @ORM\JoinColumn(name="exploits", referencedColumnName="id")
*/
private $exploits;
/**
* Author constructor.
*/
public function __construct()
{
$this->exploits = new ArrayCollection();
}
/**
* Set name
*
* @param string $name
*
* @return Author
*/
public function setName($name)
{
$this->name = $name;
return $this;
}
/**
* Get name
*
* @return string
*/
public function getName()
{
return $this->name;
}
/**
* Get id
*
*/
public function getId()
{
return $this->id;
}
public function __toString()
{
return $this->name;
}
/**
* @param Exploits $exploit
*
* @return Author
*/
public function addExploit($exploit)
{
$this->exploits->add($exploit);
return $this;
}
/**
* @param Collection $exploits
*
* @return Author
*/
public function setExploits(Collection $exploits)
{
$this->exploits->clear();
foreach ($exploits as $exploit) {
$exploit->add($this);
}
$this->exploits = $exploits;
return $this;
}
}
::::::::::::::
Category.php
::::::::::::::
<?php
namespace AppBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
use AppBundle\Entity\Exploit;
/**
* Category
*
* @ORM\Table(name="category", indexes={@ORM\Index(name="category_name_id_idx", columns={"id"})})
* @ORM\Entity
*/
class Category
{
/**
* @ORM\Id
* @ORM\GeneratedValue(strategy="NONE")
*/
private $id;
/**
* @var string
*
* @ORM\Column(name="name", category="string", length=255, nullable=false)
*/
private $name;
/**
* @ORM\OneToMany(targetEntity="AppBundle\Entity\Exploit", mappedBy="category", cascade={"persist", "remove"})
* @ORM\JoinColumn(name="exploits", referencedColumnName="id")
*/
private $exploits;
/**
* Author constructor.
*/
public function __construct()
{
$this->exploits = new ArrayCollection();
}
/**
* Set name
*
* @param string $name
*
* @return Author
*/
public function setName($name)
{
$this->name = $name;
return $this;
}
/**
* Get name
*
* @return string
*/
public function getName()
{
return $this->name;
}
/**
* Get id
*
*/
public function getId()
{
return $this->id;
}
public function __toString()
{
return $this->name;
}
/**
* @param Exploits $exploit
*
* @return Author
*/
public function addExploit($exploit)
{
$this->exploits->add($exploit);
return $this;
}
/**
* @param Collection $exploits
*
* @return Author
*/
public function setExploits(Collection $exploits)
{
$this->exploits->clear();
foreach ($exploits as $exploit) {
$exploit->add($this);
}
$this->exploits = $exploits;
return $this;
}
}
::::::::::::::
Exploit.php
::::::::::::::
<?php
namespace AppBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
use AppBundle\Entity\Author;
use AppBundle\Entity\Type;
use AppBundle\Entity\Category;
/**
* Exploit
*
* @ORM\Table(name="exploit", indexes={@ORM\Index(name=exploit_category_idx", columns={"category"}), @ORM\Index(name="exploit_type_idx", columns={"type"}), @ORM\Index(name="exploit_author_idx", columns={"
author"})})
* @ORM\Entity
*/
class Exploit
{
/**
* @var integer
*
* @ORM\Column(name="id", type="bigint", nullable=false)
* @ORM\Id
* @ORM\GeneratedValue(strategy="IDENTITY")
*/
private $id;
/**
* @var string
*
* @ORM\Column(name="edb_id", type="string", length=100, nullable=false)
*/
private $edbId;
/**
* @var \DateTime
*
* @ORM\Column(name="date", type="datetime", nullable=false)
*/
private $date;
/**
* @ORM\ManyToOne(targetEntity="AppBundle\Entity\Author", inversedBy="exploits")
* @ORM\JoinColumn(name="author", referencedColumnName="id")
*/
private $author;
/**
* @var string
*
* @ORM\Column(name="name", type="string", length=255, nullable=false)
*/
private $name;
/**
* @var integer
*
* @ORM\ManyToOne(targetEntity="AppBundle\Entity\Category", inversedBy="exploits")
* @ORM\JoinColumn(name="category", referencedColumnName="id")
*/
private $category;
/**
* @var string
*
* @ORM\Column(name="version", type="string", length=255, nullable=false)
*/
private $version;
/**
* @var integer
*
* @ORM\ManyToOne(targetEntity="AppBundle\Entity\Type", inversedBy="exploits")
* @ORM\JoinColumn(name="type", referencedColumnName="id")
*/
private $type;
/**
* @var string
*
* @ORM\Column(name="content", type="text", nullable=false)
*/
private $content;
/**
* @var string
*
* @ORM\Column(name="dork", type="string", length=255, nullable=true)
*/
private $dork;
/**
* @var string
*
* @ORM\Column(name="software_link", type="string", length=255, nullable=true)
*/
private $softwareLink;
/**
* @var string
*
* @ORM\Column(name="tested_on", type="string", length=255, nullable=true)
*/
private $testedOn;
/**
* Set edbId
*
* @param integer $edbId
*
* @return Exploit
*/
public function setEdbId($edbId)
{
$this->edbId = $edbId;
return $this;
}
/**
* Get edbId
*
* @return integer
*/
public function getEdbId()
{
return $this->edbId;
}
/**
* Set date
*
* @param \DateTime $date
*
* @return Exploit
*/
public function setDate($date)
{
$this->date = $date;
return $this;
}
/**
* Get date
*
* @return \DateTime
*/
public function getDate()
{
return $this->date;
}
/**
* Set author
*
* @param integer $author
*
* @return Exploit
*/
public function setAuthor($author)
{
$this->author = $author;
return $this;
}
/**
* Get author
*
* @return integer
*/
public function getAuthor()
{
return $this->author;
}
/**
* Set name
*
* @param string $name
*
* @return Exploit
*/
public function setName($name)
{
$this->name = $name;
return $this;
}
/**
* Get name
*
* @return string
*/
public function getName()
{
return $this->name;
}
/**
* Set category
*
* @param integer $category
*
* @return Exploit
*/
public function setCategory($category)
{
$this->category = $category;
return $this;
}
/**
* Get category
*
* @return integer
*/
public function getCategory()
{
return $this->category;
}
/**
* Set version
*
* @param string $version
*
* @return Exploit
*/
public function setVersion($version)
{
$this->version = $version;
return $this;
}
/**
* Get version
*
* @return string
*/
public function getVersion()
{
return $this->version;
}
/**
* Set type
*
* @param integer $type
*
* @return Exploit
*/
public function setType($type)
{
$this->type = $type;
return $this;
}
/**
* Get type
*
* @return integer
*/
public function getType()
{
return $this->type;
}
/**
* Set content
*
* @param string $content
*
* @return Exploit
*/
public function setContent($content)
{
$this->content = $content;
return $this;
}
/**
* Get content
*
* @return string
*/
public function getContent()
{
return $this->content;
}
/**
* Set dork
*
* @param string $dork
*
* @return Exploit
*/
public function setDork($dork)
{
$this->dork = $dork;
return $this;
}
/**
* Get dork
*
* @return string
*/
public function getDork()
{
return $this->dork;
}
/**
* Set softwareLink
*
* @param string $softwareLink
*
* @return Exploit
*/
public function setSoftwareLink($softwareLink)
{
$this->softwareLink = $softwareLink;
return $this;
}
/**
* Get softwareLink
*
* @return string
*/
public function getSoftwareLink()
{
return $this->softwareLink;
}
/**
* Set testedOn
*
* @param string $testedOn
*
* @return Exploit
*/
public function setTestedOn($testedOn)
{
$this->testedOn = $testedOn;
return $this;
}
/**
* Get testedOn
*
* @return string
*/
public function getTestedOn()
{
return $this->testedOn;
}
/**
* Get id
*
* @return integer
*/
public function getId()
{
return $this->id;
}
}
::::::::::::::
Type.php
::::::::::::::
<?php
namespace AppBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
use AppBundle\Entity\Exploit;
/**
* Type
*
* @ORM\Table(name="type", indexes={@ORM\Index(name="type_name_id_idx", columns={"id"})})
* @ORM\Entity
*/
class Type
{
/**
* @ORM\Id
* @ORM\GeneratedValue(strategy="NONE")
*/
private $id;
/**
* @var string
*
* @ORM\Column(name="name", type="string", length=255, nullable=false)
*/
private $name;
/**
* @ORM\OneToMany(targetEntity="AppBundle\Entity\Exploit", mappedBy="type", cascade={"persist", "remove"})
* @ORM\JoinColumn(name="exploits", referencedColumnName="id")
*/
private $exploits;
/**
* Type constructor.
*/
public function __construct()
{
$this->exploits = new ArrayCollection();
}
/**
* Set name
*
* @param string $name
*
* @return Type
*/
public function setName($name)
{
$this->name = $name;
return $this;
}
/**
* Get name
*
* @return string
*/
public function getName()
{
return $this->name;
}
/**
* Get id
*
*/
public function getId()
{
return $this->id;
}
public function __toString()
{
return $this->name;
}
/**
* @param Exploits $exploit
*
* @return Type
*/
public function addExploit($exploit)
{
$this->exploits->add($exploit);
return $this;
}
/**
* @param Collection $exploits
*
* @return Type
*/
public function setExploits(Collection $exploits)
{
$this->exploits->clear();
foreach ($exploits as $exploit) {
$exploit->add($this);
}
$this->exploits = $exploits;
return $this;
}
}
答案 0 :(得分:1)
在 indexAction()中,您只需编写:
$articles = $this->getDoctrine()
->getRepository('AppBundle:Articles')
->findAll();
在视图:
中<th scope="row"> {{ article.id }} </th>
<td> {{ article.name }} </td>
<td> {{ article.author_id.name }} </td>
<td> {{ article.type_id.name }} </td>
<td> {{ article.category_id.name }} </td>
<td>{{ article.date|date('F j, Y, g:i a') }}</td>
P.S:而不是author_id,type_id,category_id,你可以命名它们:author,type, 没有&#39; _id&#39;
的类别修改强>:
<强> Article.php 强>
<?php
namespace AppBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
use AppBundle\Entity\Author;
use AppBundle\Entity\Type;
use AppBundle\Entity\Category;
/**
* Article
*
* @ORM\Table(name="Article", indexes={@ORM\Index(name="Article_category_idx", columns={"category"}), @ORM\Index(name="Article_type_idx", columns={"type"}), @ORM\Index(name="Article_author_idx", columns={"author"})})
* @ORM\Entity
*/
class Article
{
/**
* @var integer
*
* @ORM\Column(name="id", type="bigint", nullable=false)
* @ORM\Id
* @ORM\GeneratedValue(strategy="IDENTITY")
*/
private $id;
/**
* @var string
*
* @ORM\Column(name="edb_id", type="string", length=100, nullable=false)
*/
private $edbId;
/**
* @var \DateTime
*
* @ORM\Column(name="date", type="datetime", nullable=false)
*/
private $date;
/**
* @var Author
*
* @ORM\ManyToOne(targetEntity="AppBundle\Entity\Author", inversedBy="articles")
* @ORM\JoinColumn(name="author", referencedColumnName="id")
*/
private $author;
/**
* @var string
*
* @ORM\Column(name="name", type="string", length=255, nullable=false)
*/
private $name;
/**
* @var integer
*
* @ORM\ManyToOne(targetEntity="AppBundle\Entity\Category", inversedBy="articles")
* @ORM\JoinColumn(name="category", referencedColumnName="id")
*/
private $category;
/**
* @var string
*
* @ORM\Column(name="version", type="string", length=255, nullable=false)
*/
private $version;
/**
* @var integer
*
* @ORM\ManyToOne(targetEntity="AppBundle\Entity\Type", inversedBy="articles")
* @ORM\JoinColumn(name="type", referencedColumnName="id")
*/
private $type;
/**
* @var string
*
* @ORM\Column(name="content", type="text", nullable=false)
*/
private $content;
/**
* @var string
*
* @ORM\Column(name="dork", type="string", length=255, nullable=true)
*/
private $dork;
/**
* @var string
*
* @ORM\Column(name="software_link", type="string", length=255, nullable=true)
*/
private $softwareLink;
/**
* @var string
*
* @ORM\Column(name="tested_on", type="string", length=255, nullable=true)
*/
private $testedOn;
/**
* Get id
*
* @return integer
*/
public function getId()
{
return $this->id;
}
/**
* Set edbId
*
* @param string $edbId
*
* @return Article
*/
public function setEdbId($edbId)
{
$this->edbId = $edbId;
return $this;
}
/**
* Get edbId
*
* @return string
*/
public function getEdbId()
{
return $this->edbId;
}
/**
* Set date
*
* @param \DateTime $date
*
* @return Article
*/
public function setDate($date)
{
$this->date = $date;
return $this;
}
/**
* Get date
*
* @return \DateTime
*/
public function getDate()
{
return $this->date;
}
/**
* Set author
*
* @param Author $author
*
* @return Article
*/
public function setAuthor($author)
{
$this->author = $author;
return $this;
}
/**
* Get author
*
* @return Author
*/
public function getAuthor()
{
return $this->author;
}
/**
* Set name
*
* @param string $name
*
* @return Article
*/
public function setName($name)
{
$this->name = $name;
return $this;
}
/**
* Get name
*
* @return string
*/
public function getName()
{
return $this->name;
}
/**
* Set category
*
* @param Category $category
*
* @return Article
*/
public function setCategory($category)
{
$this->category = $category;
return $this;
}
/**
* Get category
*
* @return Category
*/
public function getCategory()
{
return $this->category;
}
/**
* Set version
*
* @param string $version
*
* @return Article
*/
public function setVersion($version)
{
$this->version = $version;
return $this;
}
/**
* Get version
*
* @return string
*/
public function getVersion()
{
return $this->version;
}
/**
* Set type
*
* @param Type $type
*
* @return Article
*/
public function setType($type)
{
$this->type = $type;
return $this;
}
/**
* Get type
*
* @return Type
*/
public function getType()
{
return $this->type;
}
/**
* 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;
}
/**
* Set dork
*
* @param string $dork
*
* @return Article
*/
public function setDork($dork)
{
$this->dork = $dork;
return $this;
}
/**
* Get dork
*
* @return string
*/
public function getDork()
{
return $this->dork;
}
/**
* Set softwareLink
*
* @param string $softwareLink
*
* @return Article
*/
public function setSoftwareLink($softwareLink)
{
$this->softwareLink = $softwareLink;
return $this;
}
/**
* Get softwareLink
*
* @return string
*/
public function getSoftwareLink()
{
return $this->softwareLink;
}
/**
* Set testedOn
*
* @param string $testedOn
*
* @return Article
*/
public function setTestedOn($testedOn)
{
$this->testedOn = $testedOn;
return $this;
}
/**
* Get testedOn
*
* @return string
*/
public function getTestedOn()
{
return $this->testedOn;
}
}
<强> Type.php:强>
<?php
namespace AppBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
use AppBundle\Entity\Author;
/**
* Type
*
* @ORM\Table(name="type", indexes={@ORM\Index(name="type_name_id_idx", columns={"id"})})
* @ORM\Entity
*/
class Type
{
/**
* @ORM\Id
* @ORM\GeneratedValue(strategy="NONE")
*/
private $id;
/**
* @var string
*
* @ORM\Column(name="name", type="string", length=255, nullable=false)
*/
private $name;
/**
* @ORM\OneToMany(targetEntity="AppBundle\Entity\Article", mappedBy="type", cascade={"persist", "remove"})
* @ORM\JoinColumn(name="articles", referencedColumnName="id")
*/
private $articles;
/**
* Type constructor.
*/
public function __construct()
{
$this->articles = new ArrayCollection();
}
/**
* Set name
*
* @param string $name
*
* @return Type
*/
public function setName($name)
{
$this->name = $name;
return $this;
}
/**
* Get name
*
* @return string
*/
public function getName()
{
return $this->name;
}
/**
* Get id
*
*/
public function getId()
{
return $this->id;
}
public function __toString()
{
return $this->name;
}
/**
* @param Articles $article
*
* @return Type
*/
public function addArticle($article)
{
$this->articles->add($article);
return $this;
}
/**
* @param Collection $articles
*
* @return Type
*/
public function setArticles(Collection $articles)
{
$this->articles->clear();
foreach ($articles as $article) {
$article->add($this);
}
$this->articles = $articles;
return $this;
}
}
然后你做类别和作者的类型
答案 1 :(得分:1)
在您的实体以及漏洞利用
中<强>之前强>
<body onresize="sizer()">
将其更改为
/**
* @ORM\OneToMany(targetEntity="AppBundle\Entity\Exploit",mappedBy="author", cascade={"persist", "remove"})
* @ORM\JoinColumn(name="exploits", referencedColumnName="id")
*/
private $exploits;
这是因为实体漏洞利用是所有关系的拥有方。运行/**
* @ORM\OneToMany(targetEntity="AppBundle\Entity\Exploit",mappedBy="author", cascade={"persist", "remove"})
*/
private $exploits;
以更新数据库结构。
在漏洞利用实体中
bin/console doctrine:schema:update --force
在您的控制器中
/**
* Exploit
*
* @ORM\Table(name="exploit", indexes={@ORM\Index(name=exploit_category_idx", columns={"category"}), @ORM\Index(name="exploit_type_idx", columns={"type"}), @ORM\Index(name="exploit_author_idx", columns={"
author"})})
* @ORM\Entity(repositoryClass="AppBundle\Repository\ExploitRepository")
*/
class Exploit
{
// class properties and methods as is
}
在您的存储库类
中 public function indexAction()
{
$exploits = $this->getDoctrine()
->getRepository('AppBundle:Exploit')
->fetchAllExploits();
return $this->render('article/index.html.twig', array(
'exploits' => $exploits
));
}
在您的视图中
class ExploitRepository extends EntityRepository
{
public function fetchAllExploits(){
return $this
->createQueryBuilder('e')
->leftJoin('e.author','a')
->addSelect('a')
->leftJoin('e.type','t')
->addSelect('t')
->leftJoin('e.category','c')
->addSelect('c')
->getQuery()
->getResult();
}
}
答案 2 :(得分:0)
创建自定义查询加入关系和addSelect(连接的别名)。
Doctrine关系处于Lazy fetch模式,这就是为什么它只在你得到它时加载关系。如果您进行自定义查询并选择关系原则,只需使用一个查询即可对其进行水合。