From 6153951f41776127aeac9dd51255d277e6b2abd6 Mon Sep 17 00:00:00 2001 From: Eric Olkowski Date: Thu, 15 Aug 2024 13:29:31 -0400 Subject: [PATCH] fix(Card): updated markup for actionable cards --- .../src/rules/helpers/JSXElements.ts | 27 ------------ .../rules/helpers/getChildJSXElementByName.ts | 41 +++++++++++++++++++ .../rules/helpers/getLocalComponentName.ts | 14 +++---- .../rules/helpers/getSpecifierFromImports.ts | 16 ++++++++ .../src/rules/helpers/index.ts | 4 +- .../src/rules/helpers/nodeIsComponentNamed.ts | 9 ++++ .../emptyStateHeader-move-into-emptyState.ts | 8 ++-- .../masthead-structure-changes.ts | 4 +- .../wizardFooter-warn-update-markup.ts | 11 +++-- 9 files changed, 90 insertions(+), 44 deletions(-) delete mode 100644 packages/eslint-plugin-pf-codemods/src/rules/helpers/JSXElements.ts create mode 100644 packages/eslint-plugin-pf-codemods/src/rules/helpers/getChildJSXElementByName.ts create mode 100644 packages/eslint-plugin-pf-codemods/src/rules/helpers/getSpecifierFromImports.ts create mode 100644 packages/eslint-plugin-pf-codemods/src/rules/helpers/nodeIsComponentNamed.ts diff --git a/packages/eslint-plugin-pf-codemods/src/rules/helpers/JSXElements.ts b/packages/eslint-plugin-pf-codemods/src/rules/helpers/JSXElements.ts deleted file mode 100644 index 9428d7ab6..000000000 --- a/packages/eslint-plugin-pf-codemods/src/rules/helpers/JSXElements.ts +++ /dev/null @@ -1,27 +0,0 @@ -import { JSXElement } from "estree-jsx"; - -export function getChildElementByName(node: JSXElement, name: string) { - return node.children?.find( - (child) => - child.type === "JSXElement" && - child.openingElement.name.type === "JSXIdentifier" && - child.openingElement.name.name === name - ) as JSXElement | undefined; -} - -export function getAllChildElementsByName(node: JSXElement, name: string) { - return node.children?.filter( - (child) => - child.type === "JSXElement" && - child.openingElement.name.type === "JSXIdentifier" && - child.openingElement.name.name === name - ) as JSXElement[]; -} - -export function nodeIsComponentNamed(node: JSXElement, componentName: string) { - if (node.openingElement.name.type === "JSXIdentifier") { - return node.openingElement.name.name === componentName; - } - - return false; -} diff --git a/packages/eslint-plugin-pf-codemods/src/rules/helpers/getChildJSXElementByName.ts b/packages/eslint-plugin-pf-codemods/src/rules/helpers/getChildJSXElementByName.ts new file mode 100644 index 000000000..4f00e951b --- /dev/null +++ b/packages/eslint-plugin-pf-codemods/src/rules/helpers/getChildJSXElementByName.ts @@ -0,0 +1,41 @@ +import { + JSXElement, + JSXText, + JSXExpressionContainer, + JSXSpreadChild, + JSXFragment, +} from "estree-jsx"; + +function getChildJSXElementCallback( + childNode: + | JSXElement + | JSXText + | JSXExpressionContainer + | JSXSpreadChild + | JSXFragment, + name: string +) { + return ( + childNode.type === "JSXElement" && + childNode.openingElement.name.type === "JSXIdentifier" && + childNode.openingElement.name.name === name + ); +} + +/** Can be used to run logic if the specific child element exists, or to run logic on the + * specified element. + */ +export function getChildJSXElementByName(node: JSXElement, name: string) { + return node.children?.find((child) => + getChildJSXElementCallback(child, name) + ) as JSXElement | undefined; +} + +/** Can be used to run logic if the specific child elements exist, or to run logic on the + * specified elements. + */ +export function getAllChildJSXElementsByName(node: JSXElement, name: string) { + return node.children?.filter((child) => + getChildJSXElementCallback(child, name) + ) as JSXElement[]; +} diff --git a/packages/eslint-plugin-pf-codemods/src/rules/helpers/getLocalComponentName.ts b/packages/eslint-plugin-pf-codemods/src/rules/helpers/getLocalComponentName.ts index 7fd25eac9..b0e65492c 100644 --- a/packages/eslint-plugin-pf-codemods/src/rules/helpers/getLocalComponentName.ts +++ b/packages/eslint-plugin-pf-codemods/src/rules/helpers/getLocalComponentName.ts @@ -1,18 +1,18 @@ -import { ImportSpecifier } from "estree-jsx"; +import { ImportSpecifier, ImportDefaultSpecifier } from "estree-jsx"; +import { getSpecifierFromImports } from "./getSpecifierFromImports"; /** Resolves the local name of an import */ export function getLocalComponentName( - namedImports: ImportSpecifier[], + namedImports: (ImportSpecifier | ImportDefaultSpecifier)[], importedName: string ) { - const componentImport = namedImports.find( - (name) => name.imported.name === importedName - ); - + const componentImport = getSpecifierFromImports(namedImports, importedName); + const isDefaultImport = componentImport?.type === "ImportDefaultSpecifier"; const isAlias = + !isDefaultImport && componentImport?.imported.name !== componentImport?.local.name; - if (componentImport && isAlias) { + if ((componentImport && isAlias) || isDefaultImport) { return componentImport.local.name; } diff --git a/packages/eslint-plugin-pf-codemods/src/rules/helpers/getSpecifierFromImports.ts b/packages/eslint-plugin-pf-codemods/src/rules/helpers/getSpecifierFromImports.ts new file mode 100644 index 000000000..83ab9d75a --- /dev/null +++ b/packages/eslint-plugin-pf-codemods/src/rules/helpers/getSpecifierFromImports.ts @@ -0,0 +1,16 @@ +import { ImportSpecifier, ImportDefaultSpecifier } from "estree-jsx"; + +/** Can be used to extract a specific specifier from an array of imports, such as to only + * run logic if X and Y imports are present or to use the specifier properties in other logic. */ +export function getSpecifierFromImports( + imports: (ImportSpecifier | ImportDefaultSpecifier)[], + importedName: string +) { + const importSpecifier = imports.find((imp) => + imp.type === "ImportDefaultSpecifier" + ? imp.local.name === importedName + : imp.imported.name === importedName + ); + + return importSpecifier; +} diff --git a/packages/eslint-plugin-pf-codemods/src/rules/helpers/index.ts b/packages/eslint-plugin-pf-codemods/src/rules/helpers/index.ts index 5e5d6407b..dc0bbe6bd 100644 --- a/packages/eslint-plugin-pf-codemods/src/rules/helpers/index.ts +++ b/packages/eslint-plugin-pf-codemods/src/rules/helpers/index.ts @@ -2,6 +2,7 @@ export * from "./contextReports"; export * from "./findAncestor"; export * from "./fixers"; export * from "./getAttributeName"; +export * from "./getChildJSXElementByName"; export * from "./getCodeModDataTag"; export * from "./getComponentImportName"; export * from "./getDefaultDeclarationString"; @@ -10,6 +11,7 @@ export * from "./getFromPackage"; export * from "./getImportedName"; export * from "./getLocalComponentName"; export * from "./getNodeName"; +export * from "./getSpecifierFromImports"; export * from "./getText"; export * from "./hasCodemodDataTag"; export * from "./helpers"; @@ -17,7 +19,7 @@ export * from "./importAndExport"; export * from "./includesImport"; export * from "./interfaces"; export * from "./JSXAttributes"; -export * from "./JSXElements"; +export * from "./nodeIsComponentNamed"; export * from "./nodeMatches"; export * from "./pfPackageMatches"; export * from "./removeElement"; diff --git a/packages/eslint-plugin-pf-codemods/src/rules/helpers/nodeIsComponentNamed.ts b/packages/eslint-plugin-pf-codemods/src/rules/helpers/nodeIsComponentNamed.ts new file mode 100644 index 000000000..991a6073b --- /dev/null +++ b/packages/eslint-plugin-pf-codemods/src/rules/helpers/nodeIsComponentNamed.ts @@ -0,0 +1,9 @@ +import { JSXElement } from "estree-jsx"; + +export function nodeIsComponentNamed(node: JSXElement, componentName: string) { + if (node.openingElement.name.type === "JSXIdentifier") { + return node.openingElement.name.name === componentName; + } + + return false; +} diff --git a/packages/eslint-plugin-pf-codemods/src/rules/v6/emptyStateHeaderMoveIntoEmptyState/emptyStateHeader-move-into-emptyState.ts b/packages/eslint-plugin-pf-codemods/src/rules/v6/emptyStateHeaderMoveIntoEmptyState/emptyStateHeader-move-into-emptyState.ts index 80027d92b..655ba2302 100644 --- a/packages/eslint-plugin-pf-codemods/src/rules/v6/emptyStateHeaderMoveIntoEmptyState/emptyStateHeader-move-into-emptyState.ts +++ b/packages/eslint-plugin-pf-codemods/src/rules/v6/emptyStateHeaderMoveIntoEmptyState/emptyStateHeader-move-into-emptyState.ts @@ -10,7 +10,7 @@ import { getAttribute, getAttributeText, getAttributeValueText, - getChildElementByName, + getChildJSXElementByName, getDefaultImportsFromPackage, getExpression, getFromPackage, @@ -159,7 +159,7 @@ module.exports = { return; } - const header = getChildElementByName(node, "EmptyStateHeader"); + const header = getChildJSXElementByName(node, "EmptyStateHeader"); const emptyStateTitleTextAttribute = getAttribute(node, "titleText"); if (!header && emptyStateTitleTextAttribute) { @@ -168,7 +168,7 @@ module.exports = { return; } - const titleChild = getChildElementByName(node, "Title"); + const titleChild = getChildJSXElementByName(node, "Title"); if ( (!header || header.type !== "JSXElement") && @@ -194,7 +194,7 @@ module.exports = { removeElements.push(titleChild); } - const emptyStateIconChild = getChildElementByName( + const emptyStateIconChild = getChildJSXElementByName( node, "EmptyStateIcon" ); diff --git a/packages/eslint-plugin-pf-codemods/src/rules/v6/mastheadStructureChanges/masthead-structure-changes.ts b/packages/eslint-plugin-pf-codemods/src/rules/v6/mastheadStructureChanges/masthead-structure-changes.ts index 95f47fe5f..d980355d3 100644 --- a/packages/eslint-plugin-pf-codemods/src/rules/v6/mastheadStructureChanges/masthead-structure-changes.ts +++ b/packages/eslint-plugin-pf-codemods/src/rules/v6/mastheadStructureChanges/masthead-structure-changes.ts @@ -3,7 +3,7 @@ import { ImportSpecifier } from "estree-jsx"; import { JSXOpeningElementWithParent } from "../../helpers"; import { getAllImportsFromPackage, - getChildElementByName, + getChildJSXElementByName, getImportedName, getLocalComponentName, hasCodeModDataTag, @@ -21,7 +21,7 @@ function moveNodeIntoMastheadMain( } const localMastheadMain = getLocalComponentName(namedImports, "MastheadMain"); - const mastheadMain = getChildElementByName( + const mastheadMain = getChildJSXElementByName( node.parent.parent, localMastheadMain ); diff --git a/packages/eslint-plugin-pf-codemods/src/rules/v6/wizardFooterWarnUpdateMarkup/wizardFooter-warn-update-markup.ts b/packages/eslint-plugin-pf-codemods/src/rules/v6/wizardFooterWarnUpdateMarkup/wizardFooter-warn-update-markup.ts index 5741f38f6..dab342646 100644 --- a/packages/eslint-plugin-pf-codemods/src/rules/v6/wizardFooterWarnUpdateMarkup/wizardFooter-warn-update-markup.ts +++ b/packages/eslint-plugin-pf-codemods/src/rules/v6/wizardFooterWarnUpdateMarkup/wizardFooter-warn-update-markup.ts @@ -3,7 +3,7 @@ import { JSXElement } from "estree-jsx"; import { getFromPackage, getAttribute, - getAllChildElementsByName, + getAllChildJSXElementsByName, } from "../../helpers"; // https://github.com/patternfly/patternfly-react/pull/10378 @@ -29,10 +29,15 @@ module.exports = { ) { const wizardFooterProp = getAttribute(node, "footer"); const wizardSteps = wizardStepImport - ? getAllChildElementsByName(node, wizardStepImport.local.name) + ? getAllChildJSXElementsByName( + node, + wizardStepImport.local.name + ) : undefined; const allWizardStepsHaveFooter = wizardSteps - ? wizardSteps.every((step) => getAttribute(step, "footer")) + ? (wizardSteps as JSXElement[]).every((step) => + getAttribute(step, "footer") + ) : false; if (wizardFooterProp || allWizardStepsHaveFooter) {