Skip to content

Commit 65a8b7d

Browse files
committed
fix: permit appropriate computed member expressions and prototype access
1 parent 55c78db commit 65a8b7d

File tree

5 files changed

+41
-14
lines changed

5 files changed

+41
-14
lines changed

Diff for: __tests__/spec-only.js

+19
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,10 @@ ruleTester.run('spec-only', rule, {
99
'Promise.resolve()',
1010
'Promise.reject()',
1111
'Promise.all()',
12+
'Promise["all"]',
13+
'Promise[method];',
1214
'Promise.race()',
15+
'var ctch = Promise.prototype.catch',
1316
'Promise.withResolvers()',
1417
'new Promise(function (resolve, reject) {})',
1518
'SomeClass.resolve()',
@@ -22,6 +25,14 @@ ruleTester.run('spec-only', rule, {
2225
},
2326
],
2427
},
28+
{
29+
code: 'Promise.prototype.permittedInstanceMethod',
30+
options: [
31+
{
32+
allowedMethods: ['permittedInstanceMethod'],
33+
},
34+
],
35+
},
2536
],
2637
invalid: [
2738
{
@@ -53,5 +64,13 @@ ruleTester.run('spec-only', rule, {
5364
`,
5465
errors: [{ message: "Avoid using non-standard 'Promise.done'" }],
5566
},
67+
{
68+
code: `var done = Promise.prototype.done`,
69+
errors: [{ message: "Avoid using non-standard 'Promise.prototype'" }],
70+
},
71+
{
72+
code: `Promise["done"];`,
73+
errors: [{ message: "Avoid using non-standard 'Promise.done'" }],
74+
},
5675
],
5776
})

Diff for: rules/lib/is-promise.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ function isPromise(expression) {
2929
expression.callee.type === 'MemberExpression' &&
3030
expression.callee.object.type === 'Identifier' &&
3131
expression.callee.object.name === 'Promise' &&
32-
PROMISE_STATICS[expression.callee.property.name] &&
32+
PROMISE_STATICS.has(expression.callee.property.name) &&
3333
expression.callee.property.name !== 'withResolvers')
3434
)
3535
}

Diff for: rules/lib/promise-statics.js

+9-9
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
11
'use strict'
22

3-
module.exports = {
4-
all: true,
5-
allSettled: true,
6-
any: true,
7-
race: true,
8-
reject: true,
9-
resolve: true,
10-
withResolvers: true,
11-
}
3+
module.exports = new Set([
4+
'all',
5+
'allSettled',
6+
'any',
7+
'race',
8+
'reject',
9+
'resolve',
10+
'withResolvers',
11+
])

Diff for: rules/no-new-statics.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ module.exports = {
2222
if (
2323
node.callee.type === 'MemberExpression' &&
2424
node.callee.object.name === 'Promise' &&
25-
PROMISE_STATICS[node.callee.property.name]
25+
PROMISE_STATICS.has(node.callee.property.name)
2626
) {
2727
context.report({
2828
node,

Diff for: rules/spec-only.js

+11-3
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,8 @@
33
const PROMISE_STATICS = require('./lib/promise-statics')
44
const getDocsUrl = require('./lib/get-docs-url')
55

6+
const PROMISE_INSTANCE_METHODS = new Set(['then', 'catch', 'finally'])
7+
68
module.exports = {
79
meta: {
810
type: 'problem',
@@ -35,14 +37,20 @@ module.exports = {
3537
MemberExpression(node) {
3638
if (
3739
node.object.type === 'Identifier' &&
40+
(!node.computed || node.property.type === 'Literal') &&
3841
node.object.name === 'Promise' &&
39-
!(node.property.name in PROMISE_STATICS) &&
40-
!allowedMethods.includes(node.property.name)
42+
((node.property.name && !PROMISE_STATICS.has(node.property.name)) ||
43+
(node.property.value &&
44+
!PROMISE_STATICS.has(node.property.value))) &&
45+
(node.property.name !== 'prototype' ||
46+
(!PROMISE_INSTANCE_METHODS.has(node?.parent?.property?.name) &&
47+
!allowedMethods.includes(node?.parent?.property?.name))) &&
48+
!allowedMethods.includes(node.property.name ?? node.property.value)
4149
) {
4250
context.report({
4351
node,
4452
messageId: 'avoidNonStandard',
45-
data: { name: node.property.name },
53+
data: { name: node.property.name ?? node.property.value },
4654
})
4755
}
4856
},

0 commit comments

Comments
 (0)