SylvaLivingWorldScene: bundled font 404s via CORS in its own sandboxed iframe (sourceUrl/assetBaseUrl not exposed)

#39 · open · 0 comments

View on GitHub ↗

jazrs1

**Package version:** `@designcodeio/[email protected]` (also reproduces on `1.0.0`, `0.3.0`) ## What's happening `SylvaLivingWorldScene` renders its content in a **sandboxed iframe**: `sandbox="allow-scripts"`, with no `allow-same-origin`. That makes the iframe a null-origin document. The scene's own `inner-green-3d.html` declares: ```css @font-face{ font-family:'Lexend'; src:url('inner-green-assets/lexend-latin.woff2') format('woff2'); ... } ``` a root-relative fetch. From a null-origin iframe, that's a cross-origin request no matter what host actually serves it — and Chrome/WebKit require CORS approval specifically for cross-origin `@font-face` loads (unlike images or scripts, which can load `no-cors`). Console: ``` Access to font at 'https://<host>/inner-green-assets/lexend-latin.woff2' from origin 'null' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource. ``` ## The documented workaround doesn't apply to this component The README says: > Components that render full HTML documents expect their runtime files at the same root-relative URLs used by the ThreeUI preview. Copy the needed files from `node_modules/@designcodeio/threeui/lib-dist/assets/` into your app's public directory, **or override the component's `sourceUrl` or `assetBaseUrl` prop where available.** `SylvaLivingWorldSceneProps` is exactly: ```ts type SylvaLivingWorldSceneProps = { variant?: "living-green"; className?: string; style?: CSSProperties; }; ``` No `sourceUrl`, no `assetBaseUrl`. So the "override the prop" half of the documented fix isn't available for this component — only the "copy the file into your public dir" half is, and even that's insufficient on its own (see below). ## Copying the file isn't sufficient either I copied `lexend-latin.woff2` to the exact expected path in my app's `public/` dir. The font still failed to load with the same CORS error, because the request's `Origin` header is `null` (from the sandbox) and my server (a stock Next.js dev/prod server) doesn't send `Access-Control-Allow-Origin` for static files by default. The actual fix required adding an explicit CORS header for that path in my app's server config: ```ts // next.config.ts async headers() { return [{ source: "/inner-green-assets/:path*", headers: [{ key: "Access-Control-Allow-Origin", value: "*" }], }]; } ``` That's a non-obvious requirement that follows directly from the `allow-scripts`-only sandbox choice, and it isn't mentioned anywhere in the README's asset-path guidance. ## Ask Either (or both): 1. Expose `sourceUrl`/`assetBaseUrl` on `SylvaLivingWorldScene` (and any other "full HTML document" component that's missing it), matching what the README already documents as the intended override. 2. Document the CORS-header requirement explicitly wherever the "copy the file into public/" guidance appears, since it's not enough by itself given the sandbox. Note: fixing this did **not** resolve the branch/foliage geometry never appearing (filed separately as #38) — that reproduces identically with or without this font loading successfully. Filing this as its own issue since it's a real, independent gap.

Comments