Search code examples
phpcachingormdoctrine-ormdoctrine

Doctrine ORM cache errors after removing entity property


I've removed the column/property id from my Entity and I think there are some caching problems that causes the following errors when trying to access the Entity:

Uncaught ReflectionException: Given object is not an instance of the class this property was declared in in [...]/vendor/doctrine/persistence/src/Persistence/Reflection/TypedNoDefaultReflectionPropertyBase.php:33
Stack trace:
#0 .../vendor/doctrine/persistence/src/Persistence/Reflection/TypedNoDefaultReflectionPropertyBase.php(33): ReflectionProperty->isInitialized(Object(Project\Entities\Entity))
#1 .../vendor/doctrine/orm/src/UnitOfWork.php(586): Doctrine\Persistence\Reflection\TypedNoDefaultReflectionProperty->getValue(Object(Project\Entities\Entity))
...
Creation of dynamic property Project\Entities\Entity::$id is deprecated;
.../vendor/doctrine/persistence/src/Persistence/Reflection/RuntimeReflectionProperty.php; 60

I've run php config/cli-config.php orm:generate-proxies (successfully generated new proxies), but when tried any from the following to clear cache:

  1. php config/cli-config.php orm:clear-cache:query
  2. php config/cli-config.php orm:clear-cache:metadata
  3. php config/cli-config.php orm:clear-cache:result

I get such error:

In MemcachedAdapter.php line 300:
                                                     
  MemcachedAdapter client error: connection failure  
                                                     

The 'hotfix' is to change the isDevMode param to true here:

return new EntityManager(
    DriverManager::getConnection($params),
    ORMSetup::createAttributeMetadataConfiguration(
        paths: [__DIR__ . '/../Entities'],
        isDevMode: true, // :(
        proxyDir: __DIR__ . '/../../../tmp',
    ),
);

Please help me properly fix these errors. I have no idea what to do/check next.

Running on:

  1. PHP 8.2
  2. Doctrine ORM 3.1.0
  3. Doctrine DBAL 4.0.1
  4. Symfony cache 7.0.4

cli-config.php is basically:

ConsoleRunner::run(new SingleManagerProvider($entity_manager));

To clarify:

I've changed this:

#[Id]
#[Column(name: 'id', type: Types::INTEGER, updatable: false, options: ['unsigned' => true])]
#[GeneratedValue]
private int $id;

to this:

#[Id]
#[OneToOne(targetEntity: Base::class, inversedBy: 'entity')]
#[JoinColumn(name: 'id', referencedColumnName: 'id', unique: true)]
private Base $base;

and SHOW CREATE TABLE entity; gives:

CREATE TABLE `entity` (
  `id` int unsigned NOT NULL,
  PRIMARY KEY (`id`),
  KEY `entity_base_fk` (`id`),
  CONSTRAINT `entity_base_fk` FOREIGN KEY (`id`) REFERENCES `base` (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci

Solution

  • Turned out it's because of apcu cache which

    is only accessible to the webserver.

    and in php.ini apc was disabled for CLI explaining why orm:clear-cache defaulted to MemcachedAdapter

    apc.enable_cli=0
    

    enabling it doesn't help as they are different caches for webserver and CLI, so I needed to trigger apcu_clear_cache() in a webserver using e.g. curl to a specific (secured) script