From 8d83099f6984bc68f6ee28c89f86f8f1a297a09c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Iv=C3=A1n=20Ovejero?= Date: Wed, 14 Sep 2022 12:08:27 +0200 Subject: [PATCH] Migrate away from restorers (#127) * Refactor to `getExtendsValue` * Remove unused function * Pin ESLint version to n8n's version --- .../getters/credentialClassBody.getters.ts | 23 +++++++++++-------- lib/ast/index.ts | 1 + lib/ast/utils/index.ts | 2 ++ lib/ast/utils/restoreValue.ts | 7 ++++++ ...class-field-display-name-missing-oauth2.ts | 11 +++++---- .../cred-class-field-name-missing-oauth2.ts | 6 ++--- .../cred-class-name-missing-oauth2-suffix.ts | 10 +++++--- lib/types.ts | 5 +++- package.json | 2 +- 9 files changed, 46 insertions(+), 21 deletions(-) create mode 100644 lib/ast/utils/restoreValue.ts diff --git a/lib/ast/getters/credentialClassBody.getters.ts b/lib/ast/getters/credentialClassBody.getters.ts index e0a6389..f8305c3 100644 --- a/lib/ast/getters/credentialClassBody.getters.ts +++ b/lib/ast/getters/credentialClassBody.getters.ts @@ -1,7 +1,7 @@ import { TSESTree } from "@typescript-eslint/utils"; import { id } from "../identifiers"; -import { restoreArray } from "../restorers"; -import type { StringClassField } from "../../types"; +import { restoreValue } from "../utils/restoreValue"; +import type { GenericContext, StringClassField } from "../../types"; // ---------------------------------- // credClassBody @@ -37,13 +37,18 @@ export function getPlaceholder(classBody: TSESTree.ClassBody) { return getStringClassField(id.credClassBody.isPlaceholder, classBody); } -export function getExtendsOAuth2(classBody: TSESTree.ClassBody) { - const found = classBody.body.find(id.credClassBody.isFieldExtends); +/** + * Get the value for the `extends` field in a cred class, e.g. `[ 'oAuth2Api' ]` + */ +export function getExtendsValue( + classBody: TSESTree.ClassBody, + context: GenericContext +) { + const extendsNode = classBody.body.find(id.credClassBody.isFieldExtends); - if (!found) return null; + if (!extendsNode) return null; - return { - ast: found, - value: restoreArray(found.value.elements), - }; + const extendsSource = context.getSourceCode().getText(extendsNode.value); + + return restoreValue(extendsSource) ?? null; } diff --git a/lib/ast/index.ts b/lib/ast/index.ts index ee2134d..fe86751 100644 --- a/lib/ast/index.ts +++ b/lib/ast/index.ts @@ -3,5 +3,6 @@ export * from "./utils/filename"; export * from "./utils/format"; export * from "./utils/insertion"; export * from "./utils/range"; +export * from "./utils/restoreValue"; export * from "./utils/rule"; export * from "./utils/sort"; diff --git a/lib/ast/utils/index.ts b/lib/ast/utils/index.ts index b05da5d..f689612 100644 --- a/lib/ast/utils/index.ts +++ b/lib/ast/utils/index.ts @@ -2,6 +2,7 @@ import * as filename from "./filename"; import * as format from "./format"; import * as insertion from "./insertion"; import * as range from "./range"; +import * as restoreValue from "./restoreValue"; import * as rule from "./rule"; import * as sort from "./sort"; @@ -10,6 +11,7 @@ export const utils = { ...format, ...insertion, ...range, + ...restoreValue, ...rule, ...sort, }; diff --git a/lib/ast/utils/restoreValue.ts b/lib/ast/utils/restoreValue.ts new file mode 100644 index 0000000..fc618d6 --- /dev/null +++ b/lib/ast/utils/restoreValue.ts @@ -0,0 +1,7 @@ +export function restoreValue(source: string): T | null { + try { + return eval(`(${source})`); + } catch (error) { + return null; + } +} diff --git a/lib/rules/cred-class-field-display-name-missing-oauth2.ts b/lib/rules/cred-class-field-display-name-missing-oauth2.ts index ab2ef45..f7862df 100644 --- a/lib/rules/cred-class-field-display-name-missing-oauth2.ts +++ b/lib/rules/cred-class-field-display-name-missing-oauth2.ts @@ -13,7 +13,7 @@ export default utils.createRule({ }, schema: [], messages: { - addOAuth2: "Insert 'OAuth2' [non-autofixable]", // unpredictable input + addOAuth2: "Add 'OAuth2' [non-autofixable]", }, }, defaultOptions: [], @@ -22,16 +22,19 @@ export default utils.createRule({ ClassDeclaration(node) { if (!id.isCredentialClass(node)) return; - const extendsOAuth2 = getters.credClassBody.getExtendsOAuth2(node.body); + const extendsValue = getters.credClassBody.getExtendsValue( + node.body, + context + ); - if (!extendsOAuth2) return; + if (!extendsValue) return; const displayName = getters.credClassBody.getDisplayName(node.body); if (!displayName) return; if ( - extendsOAuth2.value.includes("oAuth2Api") && + extendsValue.includes("oAuth2Api") && !displayName.value.endsWith("OAuth2 API") ) { context.report({ diff --git a/lib/rules/cred-class-field-name-missing-oauth2.ts b/lib/rules/cred-class-field-name-missing-oauth2.ts index 192fd9e..9d255f3 100644 --- a/lib/rules/cred-class-field-name-missing-oauth2.ts +++ b/lib/rules/cred-class-field-name-missing-oauth2.ts @@ -24,16 +24,16 @@ export default utils.createRule({ const { body: classBody } = node; - const extendsOAuth2 = getters.credClassBody.getExtendsOAuth2(classBody); + const extendsValue = getters.credClassBody.getExtendsValue(classBody, context); - if (!extendsOAuth2) return; + if (!extendsValue) return; const name = getters.credClassBody.getName(classBody); if (!name) return; if ( - extendsOAuth2.value.includes("oAuth2Api") && + extendsValue.includes("oAuth2Api") && !name.value.endsWith("OAuth2Api") ) { context.report({ diff --git a/lib/rules/cred-class-name-missing-oauth2-suffix.ts b/lib/rules/cred-class-name-missing-oauth2-suffix.ts index 168c47a..dbb3d16 100644 --- a/lib/rules/cred-class-name-missing-oauth2-suffix.ts +++ b/lib/rules/cred-class-name-missing-oauth2-suffix.ts @@ -1,6 +1,7 @@ import { utils } from "../ast/utils"; import { id } from "../ast/identifiers"; import { getters } from "../ast/getters"; +import { RuleContext } from "@typescript-eslint/utils/dist/ts-eslint"; export default utils.createRule({ name: utils.getRuleName(module), @@ -22,16 +23,19 @@ export default utils.createRule({ ClassDeclaration(node) { if (!id.isCredentialClass(node)) return; - const extendsOAuth2 = getters.credClassBody.getExtendsOAuth2(node.body); + const extendsValue = getters.credClassBody.getExtendsValue( + node.body, + context + ); - if (!extendsOAuth2) return; + if (!extendsValue) return; const className = getters.getClassName(node); if (!className) return; if ( - extendsOAuth2.value.includes("oAuth2Api") && + extendsValue.includes("oAuth2Api") && !className.value.endsWith("OAuth2Api") ) { context.report({ diff --git a/lib/types.ts b/lib/types.ts index 58a12fe..a4e0e47 100644 --- a/lib/types.ts +++ b/lib/types.ts @@ -1,4 +1,5 @@ -import { AST_NODE_TYPES, TSESTree } from "@typescript-eslint/utils"; +import type { AST_NODE_TYPES, TSESTree } from "@typescript-eslint/utils"; +import type { RuleContext } from "@typescript-eslint/utils/dist/ts-eslint"; type BaseProperty = TSESTree.PropertyNonComputedName; @@ -44,3 +45,5 @@ export type TemplateStringProperty = BaseProperty & { export type StringClassField = TSESTree.PropertyDefinitionNonComputedName & { value: { value: string }; }; + +export type GenericContext = Readonly>; // TODO: Type properly \ No newline at end of file diff --git a/package.json b/package.json index 5228a77..8f1e01e 100644 --- a/package.json +++ b/package.json @@ -47,7 +47,7 @@ "@typescript-eslint/parser": "^5.33.0", "esbuild": "^0.15.0", "esbuild-jest": "^0.5.0", - "eslint": "^8.0.0", + "eslint": "8.23.0", "eslint-config-airbnb-typescript": "^17.0.0", "eslint-config-prettier": "^8.5.0", "eslint-docgen": "^0.7.1",