doctrine2 leftjoin addselect where条件

rqcrx0a6  于 2021-07-24  发布在  Java
关注(0)|答案(0)|浏览(258)

我试图在relates实体中创建一个2 addselect查询,其中where条件只应添加一些关系。
我有实体:
maquina=>服务器。
fisica=>从服务器扩展(它将是一个物理服务器)
partition=>从服务器扩展(它将是一个虚拟服务器并有一个物理服务器)
instancia=>安装在服务器中的产品。一个服务器可以有多个instancia,而instancia只能有一个服务器。

class Maquina
{
    public function __construct() {
        $this->instancias = new ArrayCollection();
        $this->particiones = new ArrayCollection();
    }

    /**
     * @ORM\OneToMany(targetEntity="App\Entity\Instancia", mappedBy="maquina")
     */
    private $instancias;

    /**
     * @ORM\OneToMany(targetEntity="App\Entity\Particion", mappedBy="maquina")
     */
    private $particiones;
}

class Fisica extends Maquina{}

class Particion extends Maquina
{
    public function __construct() {
        $this->instancias = new ArrayCollection();
    }

    /**
     * @ORM\OneToMany(targetEntity="App\Entity\Instancia", mappedBy="maquina")
     */
    private $instancias;

    /**
     * @ORM\ManyToOne(targetEntity="App\Entity\Maquina", inversedBy="particiones")
     * @ORM\JoinColumn(name="contenedor", referencedColumnName="id")
     */
    private $contenedor;
}

class Instancia
{
   /**
     * @ORM\ManyToOne(targetEntity="App\Entity\Maquina", inversedBy="instancias")
     * @ORM\JoinColumn(name="maquina", referencedColumnName="id", nullable=false))
     */
    private $maquina;
}

我要做的是一个查询,返回所有物理服务器(fisica),这些服务器有一个特定的产品(带有他们的id),或者有任何虚拟服务器有一个特定的产品(带有他们的id)。例如,我需要以下结果:

/*A Physical Server with the specific product. The virtuals Server of this Pshysical Server doesn't have the specific products*/
Array ( [id] => 1877 [nombre] => physicalA [discriminador] => fisica [instancias] => Array ( [0] => Array ( [id] => 28000 ) ) [particiones] => Array ( ) )

/*A Physical Server without the specific prodcuto. The virtuals Server of this Physical Server have the specific products*/
Array ( [id] => 1925 [nombre] => physicalB [discriminador] => fisica [instancias] => Array ( ) [particiones] => Array ( [0] => Array ( [id] => 9183 [nombre] => virtualB [discriminador] => particion [instancias] => Array ( [0] => Array ( [id] => 27847 ) ) ) ) )

所以我问:

$qb = $this->em->createQueryBuilder();
    $qb->select('partial F.{id, nombre}')
        ->from('App\Entity\Fisica', 'F')             
        ->leftJoin('F.instancias', 'I')->addSelect('partial I.{id}')
        ->where('I.producto = :producto AND I.edicion = :edicion')
        ->leftJoin('F.particiones', 'MV')->addSelect('partial MV.{id, nombre}')
        ->leftJoin('MV.instancias', 'IMV')->addSelect('partial IMV.{id}')
        ->orWhere('IVM.producto = :producto AND IVM.edicion = :edicion')
        ->setparameter('producto', $producto)
        ->setparameter('edicion', $edicion);  
    $fisicas = $qb->getQuery()->getArrayResult();

问题是,当只在虚拟服务器中找到产品时,即使没有指定产品,物理服务器也会返回所有产品。
我认为where/或where有一些问题,但我不知道怎么做。
有什么办法吗?谢谢!
已编辑:try do filter only results with instances(不起作用,因为groupby只显示partition的第一次出现)

$qb = $this->em->createQueryBuilder();
    $qb->select('partial F.{id, nombre, clase, coresTotales}')
        ->from('App\Entity\Fisica', 'F')             
        ->leftJoin('F.instancias', 'I', 'WITH', 'I.producto = :producto AND I.edicion = :edicion')->addSelect('partial I.{id}')
        ->leftJoin('F.particiones', 'MV')->addSelect('partial MV.{id, nombre, clase, coresVirtuales}')
        ->innerJoin('MV.instancias', 'IMV', 'WITH', 'IVM.producto = :producto AND IVM.edicion = :edicion')->addSelect('partial IMV.{id}')
        ->setparameter('producto', $productoLicenciable)
        ->setparameter('edicion', $edicion)
        ->setParameter('sinCoste', '%Sin Coste%')
        ->groupBy('F.id')->having('COUNT(I) > 0 OR COUNT(IMV) > 0');

暂无答案!

目前还没有任何答案,快来回答吧!

相关问题