Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

[Validator] Don't add multiple MemberMetadata for the same property and the same class when merging constraints.#22571

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 ourterms of service andprivacy statement. We’ll occasionally send you account related emails.

Already on GitHub?Sign in to your account

Closed

Conversation

@fancyweb
Copy link
Contributor

@fancywebfancyweb commentedApr 28, 2017
edited
Loading

QA
Branch?2.7
Bug fix?yes
New feature?no
BC breaks?no
Deprecations?no
Tests pass?yes
Fixed tickets#22538
LicenseMIT
Doc PR-

Hello, before reading my comments, you should look at the fixed ticket for more context.

So, given the following classes (taken from the example) :

interface PriceInterface {}interface VariantPriceInterfaceextends PriceInterface {}abstractclass AbstractPriceimplements PriceInterface {}class VariantSamplePriceextends AbstractPriceimplements VariantPriceInterface {}

and validation file :

PriceInterface:getters:value:            -NotBlank:~

To begin, I tried to improve the work done by@lemoinem to fix the previous issue of double validation I reported (cf#19943). I tried to make it work with the new case I have found but I couldn't. IMO, it is impossible without changing some public methods signatures. I will describe the problem with the example classes.

The problem is that both classAbstractPrice and interfaceVariantPriceInterface implements thePriceInterface interface but when you get their metadata, you get them independently. I mean there is no "context" that indicates that in reality, we want the metadata for theVariantSamplePrice model. In other words, both classes don't know about each other, they cannot know that they both implement the same interface, and have no way of knowing if the constraints for thePriceInterface have already been added or no.

So I had a different approach, and thought that I could "clean" the duplicated constraints after they were all added. There are several ways to do this, I chose to make the check as soon as possible, when the constraints are merged, so the metadata are in an "invalid" state the shortest time. The check is simple : don't mergeMemberMetadata constraints if there are already defined for the same property and the same class.

To illustrate with my example : at a given time, theVariantSamplePrice metadata will already have aGetterMetadata for the propertyvalue of the classPriceInterface either coming from theAbstractPrice or theVariantPriceInterface metadata. Then, thePriceInterface metadata will be merged a second time in theVariantSamplePrice metadata (coming from the other class metadata). But with the check, the constraints won't be merged another time. Because aMemberMetadata for the same property and of the same class exists so it means that the exact same constraints have already been added.

My main concern is the choice of whichMemberMetadata should be kept as there are not exactly the same : depending of of its class, the groups in the constraints are not the same. I honestly don't know if this is a problem or not.

Also, I originally deleted@lemoinem work because it was not really needed anymore and it covers less cases. But actually, as long as there are only interfaces concerned, it works better because the metadata are never "invalid". But I don't know if it's logical to keep both checks in different files, I need advice on this.

@nicolas-grekasnicolas-grekas added this to the2.7 milestoneApr 28, 2017

$metadata->mergeConstraints($otherMetadata);

$this->assertCount(1,$metadata->getPropertyMetadata('data'));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

But the two constraints are different? So this should be 2 here imho.

Copy link
Contributor

@ro0NLro0NLMay 3, 2017
edited
Loading

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

it's just a test :) the behavior is actually correct imo. Skip constraints from the same class/property (i.e. the ones we already visited). in real life these are the same ;-)

Copy link
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Indeed, the constraint doesn't matter. What matters in this test is that it's the same metadata class (self::INTERFACE_A_CLASS) and the same getter "property" (data). However, I agree that the constraint should maybe be the same so it's easier to understand.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

i actually liked you used different constraints :P it shows we're testing behavior

Copy link
Contributor

@dmaicherdmaicherMay 3, 2017
edited
Loading

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Not sure I would agree that they are always "the same" in "real-life" 😉 Seems like a BC break to me.

Imho we would have to check if the constraints are actually 100% the same, so same class & same options. Only then we have real duplicates.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

maybe you're right.. we cannot foresee the possible things people are doing. I dont like the idea of a deep comparison nightmare; see#15950 which we need to consider as well.

I think we actually need to prevent the wrong call tomergeConstraint based on the above inheritance.

@dmaicher
Copy link
Contributor

One different approach that I'm using in one of my apps is that I simply only render "unique" error messages as this simply makes the most sense to the end-user.

Can we maybe go into that direction? So even if constraints are duplicated we move the de- duplication to the validation phase?

Just an idea 😋

@ro0NL
Copy link
Contributor

clever.. :) but still imo. this needs a fix low-level. Like done in#20078; filtering out duplicated interfaces. That needs to cover above usecase.

@ro0NL
Copy link
Contributor

@fancyweb i played with it yesterday, and you're absolutely right. The approach is hard... (i re-read you issue once more) and you encountered everything already :P

However, i think i got something (forgot to push, but i can show you later). My idea was to track visited classes, and simply skip ones we already visited. It seems to work, in terms of i get the same no. of constraints. However some constraints have different groups (BC break), which probably means we need to add implicit groups for the classes we skipped (not sure, here's where i stopped :))

The failing test would be

diff --git a/src/Symfony/Component/Validator/Tests/Fixtures/EntityParent.php b/src/Symfony/Component/Validator/Tests/Fixtures/EntityParent.phpindex 4674f8b35a..8aaf21b719 100644--- a/src/Symfony/Component/Validator/Tests/Fixtures/EntityParent.php+++ b/src/Symfony/Component/Validator/Tests/Fixtures/EntityParent.php@@ -13,7 +13,7 @@ namespace Symfony\Component\Validator\Tests\Fixtures;  use Symfony\Component\Validator\Constraints\NotNull;-class EntityParent implements EntityInterfaceA+class EntityParent implements EntityInterfaceA, EntityParentInterface {     protected $firstName;     private $internal;

@nicolas-grekas
Copy link
Member

ping@fancyweb

@fancyweb
Copy link
ContributorAuthor

We can close this as my solution is more a hack than a fix and it breaks BC. I'm working on a new solution atm and will open a new PR...

@fancywebfancyweb deleted the double-validation-interfaces branchAugust 9, 2019 07:14
Sign up for freeto join this conversation on GitHub. Already have an account?Sign in to comment

Reviewers

2 more reviewers

@dmaicherdmaicherdmaicher left review comments

@ro0NLro0NLro0NL left review comments

Reviewers whose approvals may not affect merge requirements

Assignees

No one assigned

Projects

None yet

Milestone

2.7

Development

Successfully merging this pull request may close these issues.

5 participants

@fancyweb@dmaicher@ro0NL@nicolas-grekas@carsonbot

[8]ページ先頭

©2009-2025 Movatter.jp