Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add the ability to add "INSTANCE OF" for Criteria Expression Comparison #113

Closed
trickeyone opened this issue Mar 1, 2017 · 6 comments
Closed

Comments

@trickeyone
Copy link
Contributor

I don't know how many other people are in need of it, but dealing with a a relational DB and the Doctrine Discriminator mapping is really handy. That is, until you need to limit the results from a Collection to a relation that has a relation of a particular discriminator type.

For example:

/**
 * @ORM\Entity()
 */
class ParentObject
{
    /**
     * @var Collection
     * @ORM\OneToMany(targetEntity="ChildObject", mappedBy="parentObject")
     */
    private $childObjects;

    public function getPublishedChildObjects()
    {
        $criteria = Criteria::create();
        $criteria->andWhere(
            Criteria::expr()->instanceOf('childObjects.status', Status\Published::class);
        );
        return $this->childObjects->matching($criteria);
    }
}

/**
 * @ORM\Entity()
 */
class ChildObject
{
    /**
     * @var ParentObject
     * @ORM\ManyToOne(targetEntity="ParentObject", inversedBy="childObject")
     */
    private $parentObject;

    /**
     * @var Status
     * @ORM\ManyToOne(targetEntity="Status")
     */
    private $status;
}

/**
 * @ORM\Entity()
 * @ORM\InheritanceType("SINGLE_TABLE")
 * @ORM\DiscriminatorColumn(name="type", type="string")
 * @ORM\DiscriminatorMap({
 *     "draft" = "Status\Draft",
 *     "published" = "Status\Published"
 * })
 */
class Status
{
    private $id;
}

/* @var ParentObject $parentObject */
$parentObject = <Get ParentObject from query>;
$publishedChildObjects = $object1->getPublishedChildObjects();

The actual need is more complex with multiple status types. It would be nice to be able to do the above with collections.

@Ocramius
Copy link
Member

Ocramius commented Mar 2, 2017

Duplicate of doctrine/orm#5908

@trickeyone
Copy link
Contributor Author

Thanks @Ocramius! Didn't know there was a request on the main doctrine2 project.

@trickeyone
Copy link
Contributor Author

trickeyone commented Oct 18, 2018

As a note, I've found that if I use:

$type1 = new Type\Type1();
$type2 = new Type\Type2();
Criteria::expr()->andWhere(
  'field',
  Criteria::expr()->in([$type1, $type2])
);

Where Type/Type1 and Type/Type2 are discriminators with IDs, the desired outcome can be achieved.

@trickeyone
Copy link
Contributor Author

Followup on my previous comment. My solution that did work for 1.4 doesn't work with 1.5 because the Comparison::IN comparator now does a strict in_array

greg0ire pushed a commit to trickeyone/collections that referenced this issue Jul 25, 2020
Switching to strict checking in doctrine#97 was a minor BC-break, which can be
alleviated by doing it only for scalar values. As a consequence, 2
objects that are equal but not the same will pass the check.

Fixes doctrine#113
@7ochem
Copy link

7ochem commented Sep 29, 2021

I wanted to filter a collection by a specific type and ran into the same issue:

$object->getItems()->matching(
    Criteria::create()->where(
        Criteria::expr()->instanceOf(Some::class)
    )
);

But instanceOf() obviously does not exist. The "items" here is a collection of subtypes which all extend some base class.

If this is still a thing, then I could take a shot at this and try to add it to doctrine/collections and doctrine/orm

@trickeyone
Copy link
Contributor Author

@7ochem It looks like my PR (#249) was accepted and added to 1.6.8, which restored only strict-checking for scalar values. This re-enabled my original work-around. That said, I think having an equivalent of INSTANCE OF for collections would be extremely beneficial.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants