This is an automated email from the ASF dual-hosted git repository.
jason810496 pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/airflow.git
The following commit(s) were added to refs/heads/main by this push:
new 8b2ef80dcde Fix "Dynamic require" error for CommonJS packages in
airflow-ts-pack (#75067)
8b2ef80dcde is described below
commit 8b2ef80dcde15d32d1a0ef5cae2b87dc13a3a6af
Author: Andrew Chang <[email protected]>
AuthorDate: Sun Oct 25 16:47:37 2026 +0900
Fix "Dynamic require" error for CommonJS packages in airflow-ts-pack
(#75067)
* Fix airflow-ts-pack for CommonJS packages using Node built-ins
airflow-ts-pack outputs an ESM bundle, and an ESM file has no
`require`. esbuild turns a CommonJS dependency's `require("fs")` into
a shim that throws `Dynamic require of "fs" is not supported` unless a
`require` is in scope. So any Dag importing such a package (yaml, pg,
axios, @aws-sdk/client-s3, ...) failed to pack, and users cannot pass
esbuild options to work around it.
* Move the require banner comment onto the esbuild option
---
ts-sdk/src/cli/pack.ts | 6 ++++++
ts-sdk/tests/cli/pack.test.ts | 31 +++++++++++++++++++++++++++++++
2 files changed, 37 insertions(+)
diff --git a/ts-sdk/src/cli/pack.ts b/ts-sdk/src/cli/pack.ts
index f1806909e0f..7eb0d108938 100644
--- a/ts-sdk/src/cli/pack.ts
+++ b/ts-sdk/src/cli/pack.ts
@@ -45,6 +45,9 @@ const BUNDLE_FILENAME = "bundle.min.mjs";
const STAGING_FILENAME = "bundle.pack-staging.mjs";
const MANIFEST_TIMEOUT_MS = 60_000;
const MANIFEST_MAX_BUFFER_BYTES = 64 * 1024 * 1024;
+const ESM_REQUIRE_BANNER =
+ 'import{createRequire as __airflowCreateRequire}from"node:module";' +
+ "const require=__airflowCreateRequire(import.meta.url);";
const USAGE = `Usage: airflow-ts-pack <entry> [--outdir <dir> | --outfile
<path>]
@@ -315,6 +318,9 @@ export async function runPack(argv: readonly string[]):
Promise<void> {
// that two modules both declare, so the name the SDK reads is pinned to
// the one the author wrote.
keepNames: true,
+ // esbuild's require shim in an ESM bundle throws `Dynamic require of
"process" is not
+ // supported` for a CommonJS dependency's Node built-in unless a
`require` is in scope.
+ banner: { js: ESM_REQUIRE_BANNER },
// Tags each author-owned file with its own path before its `new
Dag(...)`
// constructor runs, so the encoder gets one Dag-defining file per source
// region.
diff --git a/ts-sdk/tests/cli/pack.test.ts b/ts-sdk/tests/cli/pack.test.ts
index 7b428acaa44..0ff32ab6f83 100644
--- a/ts-sdk/tests/cli/pack.test.ts
+++ b/ts-sdk/tests/cli/pack.test.ts
@@ -765,6 +765,37 @@ describe("runPack", () => {
);
});
+ it("packs a CommonJS dependency that requires a Node built-in", async () => {
+ outdir = mkdtempSync(path.join(tmpdir(), "ts-pack-"));
+ const dependencyDir = path.join(outdir, "node_modules", "cjs-dependency");
+ mkdirSync(dependencyDir, { recursive: true });
+ writeFileSync(
+ path.join(dependencyDir, "package.json"),
+ JSON.stringify({ name: "cjs-dependency", main: "index.js" }),
+ );
+ writeFileSync(
+ path.join(dependencyDir, "index.js"),
+ 'require("process");\nexports.dagId = "cjs_dag";\n',
+ );
+ const entry = path.join(outdir, "cjs-entry.ts");
+ writeFileSync(
+ entry,
+ [
+ `import { Bundle, Dag } from ${JSON.stringify(SDK_INDEX)};`,
+ 'import { dagId } from "cjs-dependency";',
+ "const dag = new Dag(dagId);",
+ 'dag.task("extract", async () => undefined)();',
+ "await new Bundle(dag).serve();",
+ ].join("\n"),
+ );
+
+ await runPack([entry, "--outdir", outdir]);
+
+ expect(JSON.parse(readEmbeddedMetadata(path.join(outdir,
"bundle.min.mjs")))).toHaveProperty(
+ "dag_source_paths.cjs_dag",
+ );
+ });
+
it("packs only the Dags the served bundle holds", async () => {
outdir = mkdtempSync(path.join(tmpdir(), "ts-pack-"));
const entry = path.join(outdir, "forgotten-entry.ts");