pierrejeambrun opened a new pull request, #73723:
URL: https://github.com/apache/airflow/pull/73723

   A bundle whose native Dags live in more than one file only carried its
   entrypoint's source in the `airflowSource` region. Airflow's Code tab
   would show the entrypoint for every Dag: the file for the ones declared
   there, and something unrelated for the ones declared in imported
   modules. Multi-Dag bundles were effectively single-source in the UI.
   
   ## What changes
   
   - **Each Dag's source file is embedded**, one per unique path. The
     bundle header's single `source` region becomes `sources: [{path,
     start, end, sha256}]`. Each region has its own `/*# airflowSource:<path> …
     #*/` block comment so the path is visible in the raw bundle too.
   - **Metadata gains `dag_source_paths: Record<dag_id, path>`** so a
     reader can pick the right source per Dag without guessing.
   - **`Dag`'s constructor records which file it ran in**. It reads a
     cross-realm global slot 
(`Symbol.for("airflow.ts-sdk.current-module-source")`)
     that `airflow-ts-pack`'s new onLoad plugin writes at the top of each
     author-owned source file. ES module hoisting is what makes the slot
     the current file for every top-level `new Dag(...)` call, so the
     constructor just reads it. `Function.prototype.toString` and stack
     parsing stay out. Same `Symbol.for` pattern the SDK already uses for
     the task-scope AsyncLocalStorage.
   - **Files that only supply utilities or types are not embedded.** Only
     the files whose `new Dag(...)` constructor ran end up in the source
     regions — matches Python's `dag.fileloc` behavior.
   - **Mixed-language bundles** (Python owns the Dag, TS supplies handlers)
     carry no source regions; `dag_source_paths` is empty. Their Python
     side is what displays in the UI.
   
   ## Reproducing before/after
   
   ```
   src/main.ts          # declares `orders_dag`, imports and registers 
reports_dag
   src/dags/reports.ts  # declares `reports_dag`
   ```
   
   Before: bundle carries only `main.ts` in the source region; `reports_dag`
   has no source for the Code tab.
   
   After: bundle carries both files as separate regions; metadata has
   `dag_source_paths: {orders_dag: "src/main.ts", reports_dag: 
"src/dags/reports.ts"}`.
   
   Verified end-to-end on a pack of that layout — both files land in the
   header's `sources` list with their own byte ranges and digests.
   
   ## Test coverage
   
   - `buildBundleManifest` records paths from the module-source slot.
   - Encoder: one region per file, path-tagged marker, empty case (no
     sources) for pure mixed-lang bundles.
   - Pack: multi-Dag bundle where two files declare Dags across an import
     boundary — asserts both sources are embedded and `dag_source_paths`
     maps each `dag_id` to its file.
   - Existing shebang test still passes: the plugin's slot-write goes
     after the shebang line so `#!/usr/bin/env node` stays valid.
   
   ## Not in scope
   
   - Server-side importer for `.min.mjs` bundles is future work; nothing
     reads `dag_source_paths` yet on the Airflow side. This PR only fixes
     the pack-time embedding shape so the data is present when the
     importer lands.
   
   ---
   
   ##### Was generative AI tooling used to co-author this PR?
   
   - [X] Yes — Claude Code (Opus 4.7)
   
   Generated-by: Claude Code (Opus 4.7) following [the 
guidelines](https://github.com/apache/airflow/blob/main/contributing-docs/05_pull_requests.rst#gen-ai-assisted-contributions)


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to