Fix incorrect instance of ReflectionProperty created for public typed properties#103
Conversation
|
Thanks for your contribution. Your switch in the if-block is supposed to fix an issue with the created ReflectionProperty instance. Can you please create a test that covers this issue and prevents regression in this project? |
aeffd13 to
ed88927
Compare
|
I've added the tests for this issue. Can you check again, please? |
| self::assertNotInstanceOf(TypedNoDefaultReflectionProperty::class, $reflProp); | ||
| } | ||
|
|
||
| public function testGetTypedPublicNoDefaultPropertyWorksWithGetValue() : void |
There was a problem hiding this comment.
This test got changed by your PR. If the old test using RuntimePublicReflectionProperty would fail with your changes, you might have implemented a BC-break here and 1.3.x wouldn't be the appropriate target branch.
There was a problem hiding this comment.
The old test fails with the fix - but wouldn't the old behaviour be considered a bug?
There was a problem hiding this comment.
A bugfix that introduces BC break could only be merged into a major release. The fix should also be reviewed by other maintainers too.
There was a problem hiding this comment.
This fix has been hold off for too long... as it is we might not even have it for version 3.0... Wouldn't it be possible to preserve BC? e.g. use a new class that extends RuntimePublicReflectionProperty but uses the same code as TypedNoDefaultReflectionProperty?
There was a problem hiding this comment.
Thanks for the suggestion. To avoid code duplication, I've added a trait to hold the common methods, although I'm not sure if it's the best approach.
The test now covers the old and the new behaviours.
There was a problem hiding this comment.
Well my question was primarily to @SenseException (and other maintainers), but I was thinking to something like that yes 🙂 Thanks, now let's wait for new reviews 😉
|
Will this be merged? As of today it is still impossible to remove entities where the id property is public and this seems to be the fix. |
|
There's #103 (comment) that needs to be checked/addressed |
ffc3e12 to
2b3a92c
Compare
|
Please associate your email address with your Github account, or change the |
|
My review has been requested. Before I review this, I obviously have to read #102, which mentions an incorrect type but does not explain what makes it incorrect, and refers me to doctrine/orm#7999. I might find the time and energy to review this one day, but today is not that day, sorry. If you want to speed things up, please squash your commits into one, and improve your commit message according to the contributing guide. It would be great if it mentioned the reason you are doing this, #103 (comment) , what changes you made and why they fix the issue. |
|
@greg0ire: I can at least recap what led me here: The original issue is indeed doctrine/orm#7999: you get a /** @ORM\Entity */
class MyEntity {
/** @ORM\Id @ORM\GeneratedValue @ORM\Column(type="integer") */
public int $id;
}
$myEntity = $entityManager->find(MyEntity::class, 42); // let's assume it exists
$entityManager->remove($myEntity);
$entityManager->flush(); // Typed property Entity::$id must be int, null used(because Doctrine tries to "reset" the id to Then doctrine/reflection#35 fixed it but only for Now this PR aims to fix it also for public properties (note: the first fix was simply to reverse the order, resulting in what was initially proposed in #90, but since eventually #94 chose the "wrong" order, there was some BC-change requested). (As for the EXTRA_LAZY issue, it actually seems unrelated.) But indeed, there is place for improvement of the commit message (@joaojacome 😉) |
|
Thanks, I will try to look at this today, it looks a bit more approachable now :) |
tests/Doctrine/Tests_PHP74/Persistence/Mapping/RuntimeReflectionServiceTest.php
Show resolved
Hide resolved
lib/Doctrine/Persistence/Reflection/TypedNoDefaultReflectionPropertyBase.php
Outdated
Show resolved
Hide resolved
lib/Doctrine/Persistence/Reflection/TypedNoDefaultRuntimePublicReflectionProperty.php
Outdated
Show resolved
Hide resolved
I'll squash it and give it a proper message :) |
… untyped ones Due to how PHP 7.4 works, if you have a typed public property that does not support null values, whenever Doctrine tries to delete an entity with such properties, it raises a TypeError. This happens because of the new default "uninitialized" value for typed properties. In previous versions of PHP, the default uninitialized value was null. My fist idea was to just reverse the order, and while that worked, it introduced a BC break. Now, as per @guilliamxavier suggestion, I've moved the methods from the class TypedNoDefaultRuntimePublicReflectionProperty to a trait, then I proceeded to create a new class extending RuntimePublicReflectionProperty, that uses the new trait. With this, whenever Doctrine tries to access a public property with no default value set, it will properly unset the property instead of setting it as null getting a PHP TypeError. Reordered property type resolution so typed properties get resolved first, added tests for covering multiple scenarios Fixes doctrine#102 Fixes doctrine/orm#7999 Co-authored-by: Guilliam Xavier <guilliamxavier@users.noreply.github.com>
58eb227 to
dc3d9eb
Compare
greg0ire
left a comment
There was a problem hiding this comment.
Now that's a commit message! It feels a lot safer to merge this, thanks a lot!
|
Thanks everyone! |
Resolves #102