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

Child entity not retrieved from array cache #7969

Closed
peterkeatingie opened this issue Jan 3, 2020 · 6 comments
Closed

Child entity not retrieved from array cache #7969

peterkeatingie opened this issue Jan 3, 2020 · 6 comments
Labels
Milestone

Comments

@peterkeatingie
Copy link
Contributor

Bug Report

BC Break | no
Version | 2.7.0

Summary

Entity which is extended from a base class is not retrieved from array cache when using the second level cache.
ZF3 application.

Current behavior

Base class is abstract, with extending class as a child, using single table inheritance and second level cache.
When retrieving the child class using the findBy repository method, calls subsequent to the first one are not found in the cache. The entity is fetched from the database each time.

It looks to me like the entity is put into the cache with a key which is based on its child name but retrieval is attempted using the base class name.

How to reproduce

Entity definitions:

Base class:

<?xml version="1.0" encoding="utf-8"?>
<doctrine-mapping xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                  xmlns="http://doctrine-project.org/schemas/orm/doctrine-mapping"
                  xsi:schemaLocation="http://doctrine-project.org/schemas/orm/doctrine-mapping http://doctrine-project.org/schemas/orm/doctrine-mapping.xsd">
    <entity name="Gts\Base\Entity\Base" table="base" inheritance-type="SINGLE_TABLE">
        <id name="id" type="integer" column="id">
            <generator strategy="IDENTITY"/>
        </id>
        <field name="someField"/>
    </entity>
</doctrine-mapping>

Child class. Here the cache usage is set:

<?xml version="1.0" encoding="utf-8"?>
<doctrine-mapping xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                  xmlns="http://doctrine-project.org/schemas/orm/doctrine-mapping"
                  xsi:schemaLocation="http://doctrine-project.org/schemas/orm/doctrine-mapping http://doctrine-project.org/schemas/orm/doctrine-mapping.xsd">
    <entity name="Gts\Base\Entity\BaseChild" extends="base">
        <cache usage="NONSTRICT_READ_WRITE" />
        <field name="someNewField"/>
    </entity>
</doctrine-mapping>

Doctrine configuration:

'second_level_cache' => [
                    'enabled' => true,
                ],

Calling fetch several times leads to a new db call each time (this is BaseChild repo):

// Doctrine\ORM\EntityRepository
        $this->repository->findBy([
            'someField' => 'Some Field Value',
        ]);

        $this->repository->findBy([
            'someField' => 'Some Field Value',
        ]);

Query log:

INFO: Total time: [0.0005791187286377], from: `base` Executed Query: {"sql":"SELECT t0.someField AS someField_1, t0.id AS id_2, t0.someNewField AS someNewField_3, t0.dtype FROM base t0 WHERE t0.someField = ? AND t0.dtype IN ('basechild')","params":["Some Field Value"],"types":["string"],"executionMS":0.0005791187286376953} [] []
INFO: Total time: [0.00084710121154785], from: `base` Executed Query: {"sql":"SELECT t0.someField AS someField_1, t0.id AS id_2, t0.someNewField AS someNewField_3, t0.dtype FROM base t0 WHERE t0.someField = ? AND t0.dtype IN ('basechild')","params":["Some Field Value"],"types":["string"],"executionMS":0.00026798248291015625} [] []

During debugging, I see that the entity is put into the array cache after the first call to the repository with the following key:

DoctrineModule:gts_base_entity_basechild[gts_base_entity_basechild_gts.base.entity.basechild_1][1]

But when retrieving the following key is used to find the entry:

DoctrineModule:gts_base_entity_basechild[gts_base_entity_basechild_gts.base.entity.base_1][1]

The reason for this is that in Doctrine\ORM\Cache\DefaultQueryCache::put (line 284) the cache key comes from the found entity however the key to retrieve comes from the root entity name in Doctrine\ORM\Cache\DefaultQueryCache::get (line 121).

Expected behavior

The second call to the repository should get the entity from the cache instead of making another query on the DB.

Of course it's possible that I'm missing some configuration and this may be expected as I have it configured - in which case any guidance regarding the configuration would be much appreciated.

This works as I would expect on any entity which does not have a base class.

@beberlei beberlei added the Bug label Jan 8, 2020
@peterkeatingie
Copy link
Contributor Author

Hi all, just checking to see if you had a chance to look at this since? Do you think it might be a bug?
Thanks,
Peter.

@SenseException
Copy link
Member

It was already labelled as a bug. Do you feel like you want to try to fix it in a pull request?

@peterkeatingie
Copy link
Contributor Author

Sure, let me see what I can do, thanks.

@peterkeatingie
Copy link
Contributor Author

PR: #8009

@peterkeatingie
Copy link
Contributor Author

New PR against 2.7 #8023

@beberlei beberlei added this to the 2.7.2 milestone Feb 16, 2020
@beberlei
Copy link
Member

beberlei commented Mar 1, 2020

Fixed by #8023

@beberlei beberlei closed this as completed Mar 1, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

3 participants