Skip to content

CI: Build examples in parallel on pull requests#15

Open
krodak wants to merge 6 commits into
mainfrom
kr/ci-parallel-examples
Open

CI: Build examples in parallel on pull requests#15
krodak wants to merge 6 commits into
mainfrom
kr/ci-parallel-examples

Conversation

@krodak

@krodak krodak commented Jun 23, 2026

Copy link
Copy Markdown
Collaborator

Overview

build-examples builds every example sequentially in a single job and takes ~57 minutes. Each example is its own SwiftPM package that recompiles JavaScriptKit and swift-syntax from scratch with no sharing between them, so the cost is dominated by repeating that swift-syntax compile back-to-back.

Two improvements, in two commits:

1. Build examples in parallel on pull requests. A matrix build-example runs one job per example concurrently, with an aggregate build-examples job gating on the matrix so the existing required status check of that name keeps working unchanged. main keeps the single build-examples-deploy job (full release build) plus the GitHub Pages deploy, so published artifacts are identical. Examples are built in release to match the deploy path, and each matrix step runs build.sh from the example directory via working-directory (mirroring Utilities/build-examples.sh).

2. Cache each example's .build. Keyed on the workflow file and the example's Package.resolved. On a warm cache the matrix jobs skip recompiling swift-syntax, which is the bulk of a cold example build.

Timing comparison (per-example matrix wall-clock)

setup per example examples wall-clock
today (single sequential job) ~57 min
parallel, no cache ~10 min ~10 min
parallel, cold cache (miss + save) ~10-12 min ~12 min
parallel, warm cache (hit) ~1-2 min ~2 min

Typical PRs change source, not Package.resolved or the workflow, so they hit the warm path: ~57 min → ~2 min. Cold runs (first run, or when deps/workflow change) pay a small cache-save overhead. GitHub's 10 GB cache budget is shared across the six example .build caches, so heavy eviction would fall back to cold runs.

No measurements were taken on the main deploy job; it is unchanged.

Question

I kept the required status check working by adding an aggregate build-examples job that depends on the matrix, so the required context name is unchanged and branch protection needs no edits. The alternative would be to drop the aggregate and make the per-example build-example (<name>) checks required instead. I assumed keeping the current build-examples name and required-check setup as-is is preferable - happy to switch to per-example required checks if you'd rather.

dependabot Bot and others added 5 commits June 22, 2026 17:47
Bumps [actions/checkout](https://github.com/actions/checkout) from 6 to 7.
- [Release notes](https://github.com/actions/checkout/releases)
- [Changelog](https://github.com/actions/checkout/blob/main/CHANGELOG.md)
- [Commits](actions/checkout@v6...v7)

---
updated-dependencies:
- dependency-name: actions/checkout
  dependency-version: '7'
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
The `declare global { namespace ... }` class stub rendered every method
without `static` and filtered properties to instance-only, so a `@JS static
func` on a namespaced class was typed as an instance method and a `@JS
static var` was omitted from the generated `.d.ts`.

This was a type-only defect: the emitted JavaScript already exposes these
members statically (and the class's namespace export entry types them
correctly), so only TypeScript consumers were affected. Split static and
instance members in this path: emit static methods with `static` and
include static properties.

This has been incorrect since the global namespace class stub was
introduced, not a regression. The `Namespaces.Global` snapshot already
exercises a namespaced class with `static func`/`static var` but had
recorded the wrong output, so it is updated to the corrected declarations.
…e-static-members

BridgeJS: Emit static members in declare global class declarations
Propagate Swift `///` and `/** */` documentation on exported declarations
into the generated TypeScript declarations as JSDoc, so editors surface
hover docs for the bridged API.

The exporter now captures the leading doc comment for functions, classes,
methods, properties, constructors, structs, and enums into the skeleton,
and the linker renders it as a single JSDoc block. The Swift DocC field
list is mapped as the inverse of the TS2Swift importer: the leading
description becomes the JSDoc body, `- Parameters:`/`- Parameter x:` become
`@param`, `- Returns:` becomes `@returns`, and `- Throws:` becomes
`@throws`. Existing default-value annotations are merged into the same
block so a parameter never emits two comment blocks; declarations without
doc comments produce byte-identical output to before.
…c-comments

BridgeJS: Include Swift doc comments in generated d.ts
@krodak krodak force-pushed the kr/ci-parallel-examples branch 5 times, most recently from 166377f to e7295b6 Compare June 23, 2026 16:09
The `build-examples` job built all examples sequentially in a single job,
taking ~57 minutes - each example is its own SwiftPM package that recompiles
JavaScriptKit and swift-syntax from scratch, with no sharing between them.

Split the job by event:

- Pull requests fan out a matrix `build-examples` with one job per example,
  built in parallel. Wall-clock drops to that of the slowest single example
  (~10 min). Each example now reports as a separate `build-examples (<name>)`
  check, so the required status checks need updating (see PR description).
- `main` keeps the full release build of all examples plus the GitHub Pages
  deploy (`build-examples-deploy`), so published artifacts are unchanged.

Examples are built in release to match the deploy path, keeping the only
behavioral change the parallelism. Each matrix step runs `build.sh` from the
example directory (via `working-directory`), mirroring
Utilities/build-examples.sh.
@krodak krodak force-pushed the kr/ci-parallel-examples branch 2 times, most recently from 28773c1 to 219a115 Compare June 23, 2026 17:11
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant