UNPKG

@storybook/codemod

Version:

A collection of codemod scripts written with JSCodeshift

147 lines (143 loc) • 5.42 kB
import CJS_COMPAT_NODE_URL_9smq7eu765a from 'node:url'; import CJS_COMPAT_NODE_PATH_9smq7eu765a from 'node:path'; import CJS_COMPAT_NODE_MODULE_9smq7eu765a from "node:module"; var __filename = CJS_COMPAT_NODE_URL_9smq7eu765a.fileURLToPath(import.meta.url); var __dirname = CJS_COMPAT_NODE_PATH_9smq7eu765a.dirname(__filename); var require = CJS_COMPAT_NODE_MODULE_9smq7eu765a.createRequire(import.meta.url); // ------------------------------------------------------------ // end of CJS compatibility banner, injected by Storybook's esbuild configuration // ------------------------------------------------------------ import { __name } from "../_node-chunks/chunk-HVEWKEW6.js"; // src/transforms/find-implicit-spies.ts import { core as babel, types as t } from "storybook/internal/babel"; import { loadCsf } from "storybook/internal/csf-tools"; function findImplicitSpies(path, file, keys) { path.traverse({ Identifier: /* @__PURE__ */ __name((identifier) => { if (!keys.includes(identifier.node.name) && /^on[A-Z].*/.test(identifier.node.name)) { console.warn(identifier.buildCodeFrameError(`${file} Possible implicit spy found`).message); } }, "Identifier") }); } __name(findImplicitSpies, "findImplicitSpies"); function getAnnotationKeys(file, storyName, annotationName) { const argKeys = []; file.path.traverse({ // CSF2 play function Story.args = AssignmentExpression: /* @__PURE__ */ __name((path) => { const left = path.get("left"); if (!left.isMemberExpression()) { return; } const object = left.get("object"); if (!(object.isIdentifier() && object.node.name === storyName)) { return; } const property = left.get("property"); const right = path.get("right"); if (property.isIdentifier() && property.node.name === annotationName && right.isObjectExpression()) { argKeys.push( ...right.node.properties.flatMap( (value) => t.isObjectProperty(value) && t.isIdentifier(value.key) ? [value.key.name] : [] ) ); } }, "AssignmentExpression"), // CSF3 const Story = {args: () => {} }; VariableDeclarator: /* @__PURE__ */ __name((path) => { const id = path.get("id"); const init = path.get("init"); if (!(id.isIdentifier() && id.node.name === storyName) || !init.isObjectExpression()) { return; } const args = init.get("properties").flatMap((it) => it.isObjectProperty() ? [it] : []).find((it) => { const argKey = it.get("key"); return argKey.isIdentifier() && argKey.node.name === annotationName; }); if (!args) { return; } const argsValue = args.get("value"); if (!argsValue || !argsValue.isObjectExpression()) { return; } argKeys.push( ...argsValue.node.properties.flatMap( (value) => t.isObjectProperty(value) && t.isIdentifier(value.key) ? [value.key.name] : [] ) ); }, "VariableDeclarator") }); return argKeys; } __name(getAnnotationKeys, "getAnnotationKeys"); var getObjectExpressionKeys = /* @__PURE__ */ __name((node) => { return t.isObjectExpression(node) ? node.properties.flatMap( (value) => t.isObjectProperty(value) && t.isIdentifier(value.key) ? [value.key.name] : [] ) : []; }, "getObjectExpressionKeys"); async function transform(info) { const csf = loadCsf(info.source, { makeTitle: /* @__PURE__ */ __name((title) => title, "makeTitle") }); const fileNode = csf._ast; const file = new babel.File( { filename: info.path }, { code: info.source, ast: fileNode } ); csf.parse(); const metaKeys = [ ...getObjectExpressionKeys(csf._metaAnnotations.args), ...getObjectExpressionKeys(csf._metaAnnotations.argTypes) ]; Object.values(csf.stories).forEach(({ name }) => { if (!name) { return; } const allKeys = [ ...metaKeys, ...getAnnotationKeys(file, name, "args"), ...getAnnotationKeys(file, name, "argTypes") ]; file.path.traverse({ // CSF2 play function Story.play = AssignmentExpression: /* @__PURE__ */ __name((path) => { const left = path.get("left"); if (!left.isMemberExpression()) { return; } const object = left.get("object"); if (!(object.isIdentifier() && object.node.name === name)) { return; } const property = left.get("property"); if (property.isIdentifier() && property.node.name === "play") { findImplicitSpies(path, info.path, allKeys); } }, "AssignmentExpression"), // CSF3 play function: const Story = {play: () => {} }; VariableDeclarator: /* @__PURE__ */ __name((path) => { const id = path.get("id"); const init = path.get("init"); if (!(id.isIdentifier() && id.node.name === name) || !init.isObjectExpression()) { return; } const play = init.get("properties").flatMap((it) => it.isObjectProperty() ? [it] : []).find((it) => { const argKey = it.get("key"); return argKey.isIdentifier() && argKey.node.name === "play"; }); if (play) { findImplicitSpies(play, info.path, allKeys); } }, "VariableDeclarator") }); }); return; } __name(transform, "transform"); var parser = "tsx"; export { transform as default, parser };