Skip to content

Make the notebook site cross-origin isolated on GitHub Pages (KOKKOS works deployed)#90

Merged
andeplane merged 1 commit into
masterfrom
notebook-coi-sw
Jul 9, 2026
Merged

Make the notebook site cross-origin isolated on GitHub Pages (KOKKOS works deployed)#90
andeplane merged 1 commit into
masterfrom
notebook-coi-sw

Conversation

@andeplane

Copy link
Copy Markdown
Collaborator

Why

basics/04 on the deployed site prints cross-origin isolated: False and falls back to the single-threaded build — even though the Pages workflow builds and ships the real KOKKOS wasm. GitHub Pages can't send COOP/COEP, and the plain coi-serviceworker shim can't be used under /notebook/ because JupyterLite's own service worker must own the scope (the contents API — and our DriveFS mount — ride on it).

How

Fold the coi-serviceworker logic into JupyterLite's own service worker (the approach proposed upstream in jupyterlite#1409, implemented site-side until a supported flag exists):

  • coi_patch.py (run by build.sh after jupyter lite build) wraps maybeFromCache — the function that answers every plain GET the worker intercepts (documents, assets, cross-origin fetches) — so responses carry Cross-Origin-Embedder-Policy: require-corp, Cross-Origin-Opener-Policy: same-origin, and Cross-Origin-Resource-Policy: cross-origin.
  • Each app page gets a bootstrap that reloads once when the service worker first takes control, so the document is also served with the headers. A sessionStorage guard makes a reload loop impossible; if isolation still fails, notebooks fall back to single-threaded exactly as before. Returning visitors with the old worker get the update + one reload automatically (the worker uses skipWaiting + clients.claim).
  • The patch hard-asserts on the pinned jupyterlite-core 0.8.0 service-worker internals — a version bump fails the build loudly instead of silently shipping a non-isolated site.

Verified (headless browser against a plain http.server, no headers)

  • crossOriginIsolated flips to true after exactly one reload; SharedArrayBuffer available.
  • basics/04: "cross-origin isolated: True, KOKKOS package available: True", benchmark 6.3 M atom-steps/s vs 2.6 M single-threaded (~2.4× at t 4).
  • md-basics/02's "go big" cell runs its 10,000-atom KOKKOS path.
  • DriveFS file workflows unaffected under the new headers: index, basics/02, basics/05, md-basics/05 all pass (contents API through the patched worker, piplite, matplotlib, pyodide CDN under require-corp).

Docs (README, examples/notebook/README, NOTEBOOK_TUTORIALS) and the two notebooks that described the old limitation are updated.

🤖 Generated with Claude Code

The KOKKOS multithreaded wasm was shipped to the notebook site but never
usable there: SharedArrayBuffer needs COOP/COEP headers, static hosting
can't send them, and the usual coi-serviceworker shim can't be installed
because JupyterLite's own service worker owns the scope (the contents
API — and our DriveFS mount — depend on it).

Fold the coi-serviceworker logic into JupyterLite's service worker
instead: build.sh now runs coi_patch.py, which wraps maybeFromCache (the
function serving every plain GET the worker intercepts) so responses
carry COOP/COEP/CORP, and injects a bootstrap into the app pages that
reloads once when the worker takes control so the document itself gets
the headers. A sessionStorage guard prevents reload loops; without
isolation everything falls back to single-threaded as before. The patch
asserts on the pinned jupyterlite-core's service-worker internals so a
version bump fails the build loudly (upstream feature request:
jupyterlite/jupyterlite#1409).

Verified headlessly against a plain http.server with no headers:
crossOriginIsolated flips to true after one reload; basics/04 reports
the KOKKOS build available and benchmarks 6.3 M atom-steps/s vs 2.6 M
single-threaded (~2.4x at t 4); the DriveFS file workflows (basics/02,
basics/05, md-basics/05), piplite, matplotlib and the pyodide CDN all
work under require-corp; md-basics/02's "go big" cell now runs its
10k-atom KOKKOS path.

Docs and the two notebooks that described the old limitation updated.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@andeplane andeplane merged commit 47daf5a into master Jul 9, 2026
3 checks passed
@andeplane andeplane deleted the notebook-coi-sw branch July 9, 2026 06:03
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