Add source-first exports and SSR-safe packaging#143
Add source-first exports and SSR-safe packaging#143chrisvire wants to merge 5 commits intosillsdev:mainfrom
Conversation
33ebcc7 to
eee3c0b
Compare
| value={viewModel.searchString ?? ""} | ||
| oninput={onSearchInput} |
There was a problem hiding this comment.
🚩 Controlled input pattern replaces bind:value — subtle behavioral difference
The bind:value → value={...} + oninput={...} migration (lines 125-126, 192-193) changes from Svelte's native two-way binding to a controlled input pattern. This works correctly because SvelteFieldImpl's setter (field.svelte.ts:19-22) synchronously updates $state before triggering requestUpdate. However, Svelte's bind:value has special internal handling for cursor position preservation that the manual pattern does not. In practice, since the reactive update is synchronous, cursor jumping is unlikely, but it's worth noting this behavioral difference — especially for the search input where rapid typing is common.
Was this helpful? React with 👍 or 👎 to provide feedback.
| function safeCreateTagFromOrthography( | ||
| maybeOrthography: IOrthography | ||
| ): string | undefined { | ||
| const language = maybeOrthography?.language; | ||
|
|
||
| // During SSR/initial render, selectedLanguage can be partially populated. | ||
| // createTagFromOrthography expects language.scripts to be an array. | ||
| if (!language || !Array.isArray(language.scripts)) { | ||
| return undefined; | ||
| } | ||
|
|
||
| try { | ||
| return createTagFromOrthography(maybeOrthography); | ||
| } catch { | ||
| return undefined; | ||
| } | ||
| } |
There was a problem hiding this comment.
🚩 safeCreateTagFromOrthography guards are correct but asymmetric with controller usage
The safeCreateTagFromOrthography wrapper (lines 31-47) guards against SSR scenarios where language or language.scripts might not be properly initialized. This is sound: createTagFromOrthography at languageTagUtils.ts:323 accesses language?.scripts.length which would throw if language exists but scripts is not an array (optional chaining only protects against language being nullish, not scripts). However, it's worth noting that the controller's _updateTagPreview (language-chooser.ts:181) calls createTagFromOrthography directly without this guard. If SSR ever reaches the controller's code path, the same crash could occur there. The current guard only protects the Svelte component's $derived expression.
Was this helpful? React with 👍 or 👎 to provide feedback.
Summary
This PR updates
@ethnolib/language-chooser-svelte-daisyuito support source-first Svelte consumption (SvelteKit-friendly), while preserving dist fallbacks for non-Svelte consumers. It also adds SSR-safety protections and excludes demo/bootstrap code from published library artifacts.Changes
1) Source-first + fallback exports
Updated
components/language-chooser/svelte/language-chooser-svelte-daisyui/package.json:"svelte": "./index.ts""module": "./dist/index.js""main": "./dist/index.cjs"exportsmap for".":"svelte": "./index.ts""import": "./dist/index.js""require": "./dist/index.cjs""files": ["dist", "src/lib", "index.ts"]2) SSR safety checks
Updated
components/language-chooser/svelte/language-chooser-svelte-daisyui/src/lib/LanguageChooser.svelte:if (typeof window === "undefined") return;if (typeof window !== "undefined") { ... }This ensures browser globals are only used in browser contexts.
3) Keep demo/bootstrap out of library output
Updated
components/language-chooser/svelte/language-chooser-svelte-daisyui/tsconfig.lib.json:src/main.tssrc/App.sveltesrc/app.csssrc/lib/**/*.tssrc/lib/**/*.svelteindex.tsValidation
npx vite buildincomponents/language-chooser/svelte/language-chooser-svelte-daisyuidist/index.js--conditions=svelte->index.tsdist/index.cjsnpm pack --dry-rundoes not includesrc/main.tswindow/documentusage in library entry (components/language-chooser/svelte/language-chooser-svelte-daisyui/index.ts)Why this matters
sveltecondition.This change is