UNPKG

everything-dev

Version:

A consolidated product package for building Module Federation apps with oRPC APIs.

1 lines • 14.4 kB
{"version":3,"file":"retire-zephyr.cjs","names":["Effect","fileExists","readText","writeText","listFiles"],"sources":["../../../../../src/services/scaffold/upgrade-audit/steps/retire-zephyr.ts"],"sourcesContent":["import { Effect } from \"effect\";\nimport { fileExists, listFiles, readText, writeText } from \"../fs\";\nimport type { StepResult } from \"./author-config\";\n\n/**\n * Strips ZephyrCloud deploy wiring from a v1 child tree. v2 deploys run\n * through the `bos deploy` train (build → bundle upload to the R2-backed\n * store → FastKV publish → image → Railway); the per-build Zephyr hooks\n * and their `reportDeployResult` writes into `bos.config.json` are v1-only\n * machinery. The production URLs currently in the authored descriptor come\n * from the last v1 Zephyr deploys and are replaced by the first v2 deploy.\n *\n * Handles three shapes:\n * - ui/rsbuild.config.ts: statement blocks\n * `if (shouldDeploy) { plugins.push(withZephyr({ ... })); }`\n * plus the now-unused integrity import and bos-config path const.\n * - api/plugins rspack configs: conditional default export\n * `export default shouldDeploy ? withZephyr({ ... }) : baseConfig`\n * unwrapped to `export default baseConfig`.\n * - package.json deps: `zephyr-rsbuild-plugin` / `zephyr-rspack-plugin`\n * removed from every workspace package.json and the root catalog.\n *\n * `shouldDeploy` itself is kept where it still gates non-Zephyr behavior\n * (e.g. `devtool: shouldDeploy ? false : \"source-map\"`).\n */\n\nconst ZEPHYR_DEPS = [\"zephyr-rsbuild-plugin\", \"zephyr-rspack-plugin\"] as const;\n\n/** Extracts a balanced-brace block starting at `openIdx` (on \"{\"). */\nconst extractBlock = (source: string, openIdx: number): string | null => {\n let depth = 0;\n for (let i = openIdx; i < source.length; i++) {\n const ch = source[i];\n if (ch === \"{\") depth++;\n else if (ch === \"}\") {\n depth--;\n if (depth === 0) return source.slice(openIdx, i + 1);\n }\n }\n return null;\n};\n\n/** Removes whole `if (shouldDeploy) { ... withZephyr ... }` statement blocks. */\nconst removeZephyrIfBlocks = (source: string): { next: string; removed: number } => {\n let next = source;\n let removed = 0;\n for (;;) {\n const ifStart = next.indexOf(\"if (shouldDeploy)\");\n if (ifStart === -1) break;\n const blockOpen = next.indexOf(\"{\", ifStart);\n if (blockOpen === -1) break;\n const block = extractBlock(next, blockOpen);\n if (block === null || !block.includes(\"withZephyr\")) break;\n let end = blockOpen + block.length;\n if (next[end] === \"\\n\") end += 1;\n next = (next.slice(0, ifStart) + next.slice(end)).replace(/\\n{3,}/g, \"\\n\\n\");\n removed += 1;\n }\n return { next, removed };\n};\n\n/**\n * Unwraps `export default shouldDeploy ? withZephyr({ ... }) : BASE;` to\n * `export default BASE;`. Locates the ternary colon after the withZephyr\n * call closes (never inside the args object, where `key:` pairs live).\n */\nconst unwrapZephyrTernary = (source: string): { next: string; unwrapped: boolean } => {\n const marker = source.indexOf(\"export default shouldDeploy\");\n if (marker === -1) return { next: source, unwrapped: false };\n const withIdx = source.indexOf(\"withZephyr(\", marker);\n if (withIdx === -1) return { next: source, unwrapped: false };\n const callOpen = source.indexOf(\"{\", withIdx);\n if (callOpen === -1) return { next: source, unwrapped: false };\n const args = extractBlock(source, callOpen);\n if (args === null) return { next: source, unwrapped: false };\n const closeParen = source.indexOf(\")\", callOpen + args.length);\n if (closeParen === -1) return { next: source, unwrapped: false };\n const colonIdx = source.indexOf(\":\", closeParen);\n if (colonIdx === -1) return { next: source, unwrapped: false };\n const semiIdx = source.indexOf(\";\", colonIdx);\n if (semiIdx === -1) return { next: source, unwrapped: false };\n const base = source.slice(colonIdx + 1, semiIdx).trim();\n if (!base || base.includes(\"withZephyr\")) return { next: source, unwrapped: false };\n return {\n next: `${source.slice(0, marker)}export default ${base};${source.slice(semiIdx + 1)}`,\n unwrapped: true,\n };\n};\n\nconst stripUnusedImports = (source: string, path: string, notes: string[]): string => {\n let next = source;\n\n const zephyrImport = next.match(\n /import\\s*\\{\\s*withZephyr\\s*\\}\\s*from\\s*\"zephyr-(?:rsbuild|rspack)-plugin\";\\n/,\n );\n if (zephyrImport && !next.replace(zephyrImport[0], \"\").includes(\"withZephyr\")) {\n next = next.replace(zephyrImport[0], \"\");\n notes.push(`${path}: removed the withZephyr import`);\n }\n\n const integrityImport = next.match(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*\"everything-dev\\/integrity\";\\n/,\n );\n if (integrityImport) {\n const names = integrityImport[1]\n .split(\",\")\n .map((n) => n.trim().replace(/\\s+as\\s+\\S+/, \"\"))\n .filter(Boolean);\n const withoutImport = next.replace(integrityImport[0], \"\");\n const allUnused = names.every((name) => !withoutImport.includes(name));\n if (allUnused) {\n next = next.replace(integrityImport[0], \"\");\n notes.push(`${path}: removed the unused everything-dev/integrity import`);\n }\n }\n\n // Drop the shouldDeploy declaration when nothing references it anymore.\n const declMatch = next.match(/const shouldDeploy = process\\.env\\.DEPLOY === \"true\";\\n/);\n if (declMatch && !next.replace(declMatch[0], \"\").includes(\"shouldDeploy\")) {\n next = next.replace(declMatch[0], \"\");\n notes.push(`${path}: removed the unused shouldDeploy declaration`);\n }\n\n // Drop the bos.config.json path helper — reportDeployResult wrote there,\n // and bos.config.json itself is retired by the v2 authored descriptor.\n const bosPathMatch = next.match(/const uiBosConfigPath = [^\\n]*;\\n/);\n if (bosPathMatch && !next.replace(bosPathMatch[0], \"\").includes(\"uiBosConfigPath\")) {\n next = next.replace(bosPathMatch[0], \"\");\n notes.push(`${path}: removed the unused uiBosConfigPath declaration`);\n }\n\n return next.replace(/\\n{3,}/g, \"\\n\\n\");\n};\n\nconst rewriteBuildConfig = (\n projectDir: string,\n path: string,\n dryRun: boolean,\n notes: string[],\n): Effect.Effect<boolean, Error> =>\n Effect.gen(function* () {\n const exists = yield* fileExists(projectDir, path);\n if (!exists) {\n notes.push(`${path} absent — skipped`);\n return false;\n }\n const source = yield* readText(projectDir, path);\n if (!source.includes(\"withZephyr\")) {\n notes.push(`${path}: no Zephyr wiring — left untouched`);\n return false;\n }\n\n let next = source;\n\n const ifBlocks = removeZephyrIfBlocks(next);\n next = ifBlocks.next;\n if (ifBlocks.removed > 0) {\n notes.push(`${path}: removed ${ifBlocks.removed} withZephyr deploy block(s)`);\n }\n\n const ternary = unwrapZephyrTernary(next);\n next = ternary.next;\n if (ternary.unwrapped) {\n notes.push(`${path}: unwrapped the shouldDeploy ? withZephyr(...) : base default export`);\n }\n\n next = stripUnusedImports(next, path, notes);\n\n if (next !== source && !dryRun) yield* writeText(projectDir, path, next);\n return next !== source;\n });\n\nconst stripZephyrDeps = (\n projectDir: string,\n dryRun: boolean,\n notes: string[],\n): Effect.Effect<string[], Error> =>\n Effect.gen(function* () {\n const changed: string[] = [];\n const pkgPaths = yield* listFiles(\n projectDir,\n \"{package.json,ui/package.json,api/package.json,plugins/*/package.json}\",\n );\n for (const pkgPath of pkgPaths) {\n const source = yield* readText(projectDir, pkgPath);\n const pkg = JSON.parse(source) as {\n dependencies?: Record<string, string>;\n devDependencies?: Record<string, string>;\n workspaces?: { catalog?: Record<string, string> };\n };\n let modified = false;\n for (const dep of ZEPHYR_DEPS) {\n for (const field of [\"dependencies\", \"devDependencies\"] as const) {\n if (pkg[field] && dep in pkg[field]) {\n delete pkg[field][dep];\n modified = true;\n notes.push(`${pkgPath}: removed ${dep} from ${field}`);\n }\n }\n }\n if (pkg.workspaces?.catalog) {\n for (const dep of ZEPHYR_DEPS) {\n if (dep in pkg.workspaces.catalog) {\n delete pkg.workspaces.catalog[dep];\n modified = true;\n notes.push(`${pkgPath}: removed ${dep} from the catalog`);\n }\n }\n }\n if (modified) {\n if (!dryRun) {\n yield* writeText(projectDir, pkgPath, `${JSON.stringify(pkg, null, 2)}\\n`);\n }\n changed.push(pkgPath);\n }\n }\n return changed;\n });\n\nexport const retireZephyr = (\n projectDir: string,\n dryRun: boolean,\n): Effect.Effect<StepResult, Error> =>\n Effect.gen(function* () {\n const writes: string[] = [];\n const notes: string[] = [\n \"v2 deploys run through the bos deploy train (bundle upload + FastKV publish + image + Railway) — Zephyr wiring is retired\",\n \"production URLs in the authored descriptor are from the last v1 Zephyr deploy; the first v2 deploy replaces them\",\n ];\n\n const configs = [\"ui/rsbuild.config.ts\", \"api/rspack.config.js\"];\n const pluginConfigs = yield* listFiles(projectDir, \"plugins/*/rspack.config.js\");\n for (const path of [...configs, ...pluginConfigs]) {\n const changed = yield* rewriteBuildConfig(projectDir, path, dryRun, notes);\n if (changed) writes.push(path);\n }\n\n const depChanges = yield* stripZephyrDeps(projectDir, dryRun, notes);\n writes.push(...depChanges);\n\n if (writes.length === 0) {\n notes.push(\"no Zephyr wiring found — nothing to retire\");\n }\n\n return { writes, deletes: [], notes };\n });\n"],"mappings":"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"}