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

Update: Handle locally unsupported regex in computed property keys #12056

Merged
merged 2 commits into from Dec 25, 2019
Merged

Update: Handle locally unsupported regex in computed property keys #12056

merged 2 commits into from Dec 25, 2019

Conversation

mdjermanovic
Copy link
Member

@mdjermanovic mdjermanovic commented Aug 3, 2019

What is the purpose of this pull request? (put an "X" next to item)

[X] Bug fix

Tell us about your environment

  • ESLint Version: 6.1.0
  • Node Version: 8.16.0
  • npm Version: 6.4.1

What parser (default, Babel-ESLint, etc.) are you using?

default

Please show your full configuration:

Configuration
module.exports = {
  parserOptions: {
    ecmaVersion: 2018,
  },
};

What did you do? Please include the actual source code causing the issue.

This bug is observable in environments that don't support ES2018 regexp syntax, namely Node 8.

For the online demo use Firefox (current Firefox version is 68, still doesn't support this syntax), results are different when compared to Chrome.

This bug affects 5 rules:


no-dupe-keys false negative:

/*eslint no-dupe-keys: "error"*/
({ "/(?<zero>0)/": 1, [/(?<zero>0)/]: 2 })

Demo link (open in Firefox)


no-dupe-keys false positive:

/*eslint no-dupe-keys: "error"*/
({ null: 1, [/(?<zero>0)/]: 2 })

Demo link (open in Firefox)


sort-keys false negative:

/*eslint sort-keys: "error"*/
({ null: 1, [/(?<zero>0)/]: 2 })

Demo link (open in Firefox)


sort-keys false positive:

/*eslint sort-keys: "error"*/
({ [/(?<zero>0)/]: 1, "/(?<zero>0)/": 2 })

Demo link (open in Firefox)


no-self-assign false negative:

/*eslint no-self-assign: "error"*/
foo["/(?<zero>0)/"] = foo[/(?<zero>0)/]

Demo link (open in Firefox)


no-self-assign false positive:

/*eslint no-self-assign: "error"*/
foo.null = foo[/(?<zero>0)/];

Demo link (open in Firefox)


yoda false negative:

/*eslint yoda: ["error", "never", { "exceptRange": true }]*/
if (1 < foo.null && foo[/(?<zero>0)/] < 10) {}

Demo link (open in Firefox)


yoda false positive:

/*eslint yoda: ["error", "never", { "exceptRange": true }]*/
if (1 < foo["/(?<zero>0)/"] && foo[/(?<zero>0)/] < 10) {}

Demo link (open in Firefox)


no-restricted-properties false negative:

/*eslint no-restricted-properties: ["error", { "property": "/(?<zero>0)/" }]*/
foo[/(?<zero>0)/];

Demo link (open in Firefox)


no-restricted-properties false positive:

/*eslint no-restricted-properties: ["error", { "property": "null" }]*/
foo[/(?<zero>0)/];

Demo link (open in Firefox)

What did you expect to happen?

Warnings for 'false negative' examples, no warnings for 'false positive' examples.

What actually happened? Please include the actual, raw output from ESLint.

The opposite.

What changes did you make? (Give an overview)

Fixed astUtils.getStaticPropertyName

Is there anything you'd like reviewers to focus on?

Part of the code is extracted to new function getStaticStringValue, it's easier to test and it might be useful for something else.

Unrelated to this PR:

  • The same fix should be added for bigint.
  • accesor-pairs should use getStaticPropertyName, but this rule doesn't work well. It should enforce pairs per key, not per the whole literal. I'm working on this, a PR will be ready very soon.
  • Some other rules might also use getStaticPropertyName instead of a partial/duplicate logic, I'm working on this.
  • Some rules are treating empty string name as null, I'm working on this, will be ready very soon.

@eslint-deprecated eslint-deprecated bot added the triage An ESLint team member will look at this issue soon label Aug 3, 2019
Copy link
Member

@platinumazure platinumazure left a comment

Choose a reason for hiding this comment

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

LGTM, thanks for contributing!

Copy link
Member

@kaicataldo kaicataldo left a comment

Choose a reason for hiding this comment

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

LGTM, thanks!

@kaicataldo kaicataldo added enhancement This change enhances an existing feature of ESLint evaluating The team will evaluate this issue to decide whether it meets the criteria for inclusion rule Relates to ESLint's core rules and removed triage An ESLint team member will look at this issue soon labels Aug 3, 2019
@kaicataldo
Copy link
Member

Sorry, to avoid confusion I usually wait to review until after a change is accepted. Code LGTM and I support this change, but we’ll need another 👍🏼 And a champion.

@mysticatea
Copy link
Member

Would you try getPropertyName function of eslint-utils? I guess that the utility covers more cases.

@mdjermanovic
Copy link
Member Author

Sorry, to avoid confusion I usually wait to review until after a change is accepted. Code LGTM and I support this change, but we’ll need another 👍🏼 And a champion.

Sorry, I should be more specific and the title/commit message indeed sounds like this is an enhancement.

This was supposed to be a bug fix. The title has 'Update' prefix because the fix can produce more warnings.

The function already supports regexp literals, but it doesn't 'support' RegExpLiteral extension of the Literal interface, i.e. the regex property.

The bug is in return String(prop.value) which will evaluate to "null" string if the ESLint is executed in an environment that doesn't support given regex syntax.

@mdjermanovic
Copy link
Member Author

Would you try getPropertyName function of eslint-utils?

I'll try it on Node 8 with test cases from this PR to be sure, but I think it doesn't use regex properties?

Literal(node) {
        //istanbul ignore if : this is implementation-specific behavior.
        if (node.regex != null && node.value == null) {
            // It was a RegExp literal, but Node.js didn't support it.
            return null
        }
        return node
    },

instead of return null it might be something like

return { value: `/${node.regex.pattern}/${node.regex.flags}` }

or maybe there is a specific reason to return null in this scenario? I'm asking because it would apply to this PR as well.

I guess that the utility covers more cases.

Looks like a lot more, even without the scope argument, I'm not sure would it be a breaking change?

@mdjermanovic
Copy link
Member Author

I think I see the reason now, getStaticValue() returns the value itself, which is impossible in this scenario. But then there is a problem with getStringIfConstant() which doesn't return the string in this scenario, although it would be possible.

@mdjermanovic mdjermanovic changed the title Update: Support RegExpLiteral in astUtils.getStaticPropertyName Update: Handle locally unsupported regex in computed property keys Aug 7, 2019
@mdjermanovic
Copy link
Member Author

Changed the title and commit message. I still believe this is a bug fix rather than enhancement :)

@kaicataldo
Copy link
Member

@mysticatea Have your concerns been addressed?

@mysticatea
Copy link
Member

I apologize for I lost track on this. LGTM.

@mdjermanovic
Copy link
Member Author

@mysticatea no problem, but this will now collide with #12701, which handles this + bigints as well.

Might be easier to close this PR and do everything in #12701?

@mysticatea
Copy link
Member

Thank you. I'm fine with either way... (1) we merge this PR to master then master to #12701, or (2) I cherry-pick this to #12701. Probably those are samely easy.

@mdjermanovic
Copy link
Member Author

Rebased and fixed conflicts & JSDoc, for the case that this gets merged.

@mysticatea mysticatea merged commit 3fa39a6 into eslint:master Dec 25, 2019
@mysticatea
Copy link
Member

Thank you!

@eslint-deprecated eslint-deprecated bot locked and limited conversation to collaborators Jun 24, 2020
@eslint-deprecated eslint-deprecated bot added the archived due to age This issue has been archived; please open a new issue for any further discussion label Jun 24, 2020
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
archived due to age This issue has been archived; please open a new issue for any further discussion enhancement This change enhances an existing feature of ESLint evaluating The team will evaluate this issue to decide whether it meets the criteria for inclusion rule Relates to ESLint's core rules
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

4 participants