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

[SecurityBundle] support custom functions inside allow_if expressions#26263

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
dmaicher wants to merge1 commit intosymfony:2.7fromdmaicher:fix-23208

Conversation

@dmaicher
Copy link
Contributor

@dmaicherdmaicher commentedFeb 21, 2018
edited
Loading

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

This is a follow up for#24309.


Problem:
TheSecurityExtension was instantiating an\Symfony\Component\Security\Core\Authorization\ExpressionLanguage instance to parse the expressions defined in the access control config viaallow_if: "...". So it used a pre-parsedSerializedParsedExpression instead of a rawExpression probably for performance reasons.

This has the serious drawback (and that's the bug) that it does not use the service'security.expression_language' for this during the compiler pass. So any customizations for the service (like custom providers with functions) are completely ignored here on compile time.


Proposed fix
I propose to not dump parsed expressions at all and to leave this for run-time and caching.

I did some benchmarks and would like to hear your thoughts on this.
Using this small benchmark script (https://gist.github.com/dmaicher/ae506ff436a4647f3eaf7e59ec4c4aa1) I get the following numbers:

UsingNullAdapter:

raw:    39.814957857132s parsed: 19.232628822327s

UsingArrayAdapter for caching there is almost no difference:

raw:    21.031932115555s parsed: 19.204074144363s

So on my laptop the difference for theNullAdapter case is roughly 20s for 500 thousand evaluations. Which means for one evaluation it's in the range of 40 microseconds or0.04ms.

Maybe we can make use ofcache.system for the expression language on 3.3+?

WDYT?

@nicolas-grekas
Copy link
Member

Should this really be done as a bug fix? Can't we consider it's a limitation for sure, but that's how it works for now? If you agree, then the cache warmup should be added in the PR on master.

@dmaicher
Copy link
ContributorAuthor

We can also consider it as a undocumented limitation and I can add it as a feature to master. I just find the current behavior kind of weird to be honest. But I don't really mind 😊

Should we usecache.system then for the expression language cache?

@nicolas-grekas
Copy link
Member

Should we use cache.system then for the expression language cache?

a dedicated pool instead, so userland items cannot collide with internals - see egcache.validator

dmaicher reacted with thumbs up emoji

@stof
Copy link
Member

An option for 2.7 could be to keep trying to parse in the extension at compile time, but fallback to runtime parsing (using Expression instead of SerializedParsedExpression) in case of an invalid function being used (as this is the only kind of parse error which can change once registering custom functions). This way, only projects using a custom function in theirallow_if expression would be affected by the slower code path.

// security
if ($container->has('security.access.expression_voter')) {
$definition =$container->findDefinition('security.access.expression_voter');
if ($container->has('security.expression_language')) {
Copy link
Member

Choose a reason for hiding this comment

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

why changing the registration logic ?

Copy link
Member

Choose a reason for hiding this comment

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

hmm, registering providers on the right service rather than relying on delegation still makes sense though, to ensure that thesecurity.expression_language service is usable even if it is instantiated earlier than the ExpressionVoter due to injecting it elsewhere and due to voters being lazy-loaded).
We should probably even deprecated\Symfony\Component\Security\Core\Authorization\Voter\ExpressionVoter::addExpressionLanguageProvider in master as it only delegates the call and the ExpressionLanguage instance is always injected from the outside.

Copy link
ContributorAuthor

Choose a reason for hiding this comment

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

I think adding it tosecurity.expression_language directly makes more sense? Not even sure whyExpressionVoter::addExpressionLanguageProvider exists. Maybe I'm missing something?

If someone injectssecurity.expression_language and uses it without theExpressionVoter service ever being instantiated then the custom providers would be missing?

But if it makes merging etc harder I can also revert it.

Copy link
ContributorAuthor

Choose a reason for hiding this comment

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

@stof exactly 😊

👍 for deprecating it

Choose a reason for hiding this comment

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

is this change required for 2.7? if not, better revert, isn't it, and do it on master only?

Copy link
ContributorAuthor

Choose a reason for hiding this comment

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

No its not required 👍 will revert and apply to master together with the deprecation then

Copy link
ContributorAuthor

Choose a reason for hiding this comment

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

@nicolas-grekas removed 😉

@dmaicher
Copy link
ContributorAuthor

dmaicher commentedFeb 27, 2018
edited
Loading

An option for 2.7 could be to keep trying to parse in the extension at compile time, but fallback to runtime parsing (using Expression instead of SerializedParsedExpression) in case of an invalid function being used (as this is the only kind of parse error which can change once registering custom functions). This way, only projects using a custom function in their allow_if expression would be affected by the slower code path.

@stof yes I was also thinking about that.

We could catchSyntaxError but this can also mean the expression simply has a wrong syntax 🙈So as a side effect instead of at compile time the error would show up on run-time. But I guess thats not a big problem? => actually that's the case already with my current fix here 😊

@dmaicherdmaicherforce-pushed thefix-23208 branch 2 times, most recently from69f6e3c to537222fCompareFebruary 27, 2018 19:34
@dmaicher
Copy link
ContributorAuthor

@stof@nicolas-grekas I updated it so we keep trying to parse the expression on compile time and we simply fallback to using a raw expression if it fails.

Let me know what you think 😉

I could create a separate PR for master to use a new cache pool + deprecateExpressionVoter::addExpressionLanguageProvider.

@dmaicherdmaicher changed the title[SecurityBundle] do not pre-parse allow_if expressions to support custom functions[SecurityBundle] support custom functions inside allow_if expressionsFeb 27, 2018
Copy link
Member

@nicolas-grekasnicolas-grekas left a comment

Choose a reason for hiding this comment

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

I'm wondering if the runtime error is an acceptable DX downgrade (vs the current compile time failure)
WDYT?

@dmaicher
Copy link
ContributorAuthor

dmaicher commentedFeb 28, 2018
edited
Loading

Hmm not sure its a big problem. I mean when using the FrameworkExtraBundle@Security annotation with an expression it also appears on run-time for example?

What do you think@stof ?

@dmaicher
Copy link
ContributorAuthor

@nicolas-grekas@stof should I continue to work on this? Or should we close the issue as "won't fix"?

@nicolas-grekas
Copy link
Member

@dmaicher move as new feature on master?

@dmaicher
Copy link
ContributorAuthor

dmaicher commentedMar 19, 2018
edited
Loading

@nicolas-grekas ok 😉 Will prepare a new PR soon for master that

  • does not pre-parse expressions anymore at compile-time
  • deprecatesExpressionVoter::addExpressionLanguageProvider
  • adds a cache pool for the security expression language

fabpot added a commit that referenced this pull requestApr 6, 2018
…low_if expressions (dmaicher)This PR was merged into the 4.1-dev branch.Discussion----------[SecurityBundle] allow using custom function inside allow_if expressions| Q             | A| ------------- | ---| Branch?       | master| Bug fix?      | no| New feature?  | yes| BC breaks?    | no| Deprecations? | yes| Tests pass?   | no| Fixed tickets |#23208| License       | MIT| Doc PR        |symfony/symfony-docs#9552This is a follow-up for#26263As discussed there I propose to allow using custom functions as a new feature only and thus targeting `master` here.If we agree to move forward with this there are some todos:- [x] fix tests- [x] add cache warmer for allow_if expressions- [x] update documentation to mention this new feature- [x] update UPGRADE filesping@nicolas-grekas@stofCommits-------41552cd [SecurityBundle] allow using custom function inside allow_if expressions
Sign up for freeto join this conversation on GitHub. Already have an account?Sign in to comment

Reviewers

@nicolas-grekasnicolas-grekasnicolas-grekas left review comments

@stofstofstof left review comments

Assignees

No one assigned

Projects

None yet

Milestone

2.7

Development

Successfully merging this pull request may close these issues.

4 participants

@dmaicher@nicolas-grekas@stof@carsonbot

[8]ページ先頭

©2009-2025 Movatter.jp