@fictjs/runtime 0.0.15 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/advanced.cjs +8 -8
- package/dist/advanced.d.cts +3 -3
- package/dist/advanced.d.ts +3 -3
- package/dist/advanced.js +3 -3
- package/dist/{chunk-GJTYOFMO.cjs → chunk-527QSKFM.cjs} +16 -16
- package/dist/{chunk-GJTYOFMO.cjs.map → chunk-527QSKFM.cjs.map} +1 -1
- package/dist/{chunk-RY4WDS6R.js → chunk-5KXEEQUO.js} +115 -20
- package/dist/chunk-5KXEEQUO.js.map +1 -0
- package/dist/{chunk-624QY53A.cjs → chunk-BSUMPMKX.cjs} +7 -7
- package/dist/chunk-BSUMPMKX.cjs.map +1 -0
- package/dist/{chunk-IUZXKAAY.js → chunk-FG3M7EBL.js} +2 -2
- package/dist/{chunk-PMF6MWEV.cjs → chunk-J74L7UYP.cjs} +128 -33
- package/dist/chunk-J74L7UYP.cjs.map +1 -0
- package/dist/{chunk-F3AIYQB7.js → chunk-QV5GOCR5.js} +3 -3
- package/dist/chunk-QV5GOCR5.js.map +1 -0
- package/dist/{context-B7UYnfzM.d.ts → context-4woHo7-L.d.ts} +1 -1
- package/dist/{context-UXySaqI_.d.cts → context-9gFXOdJl.d.cts} +1 -1
- package/dist/{effect-Auji1rz9.d.cts → effect-ClARNUCc.d.cts} +23 -2
- package/dist/{effect-Auji1rz9.d.ts → effect-ClARNUCc.d.ts} +23 -2
- package/dist/index.cjs +51 -54
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +4 -4
- package/dist/index.d.ts +4 -4
- package/dist/index.dev.js +96 -28
- package/dist/index.dev.js.map +1 -1
- package/dist/index.js +10 -13
- package/dist/index.js.map +1 -1
- package/dist/internal.cjs +44 -35
- package/dist/internal.cjs.map +1 -1
- package/dist/internal.d.cts +9 -4
- package/dist/internal.d.ts +9 -4
- package/dist/internal.js +12 -3
- package/dist/internal.js.map +1 -1
- package/dist/jsx-runtime.d.cts +671 -0
- package/dist/jsx-runtime.d.ts +671 -0
- package/dist/{props-ES0Ag_Wd.d.ts → props-CBwuh35e.d.cts} +13 -6
- package/dist/{props-CrOMYbLv.d.cts → props-DAyeRPwH.d.ts} +13 -6
- package/dist/{scope-S6eAzBJZ.d.ts → scope-DvgMquEy.d.ts} +1 -1
- package/dist/{scope-DKYzWfTn.d.cts → scope-xmdo6lVU.d.cts} +1 -1
- package/package.json +1 -1
- package/src/binding.ts +62 -8
- package/src/constants.ts +2 -3
- package/src/dev-entry.ts +22 -0
- package/src/effect.ts +9 -2
- package/src/lifecycle.ts +24 -6
- package/src/list-helpers.ts +14 -3
- package/src/props.ts +29 -3
- package/src/scope.ts +1 -1
- package/src/signal.ts +43 -4
- package/src/suspense.ts +17 -13
- package/dist/chunk-624QY53A.cjs.map +0 -1
- package/dist/chunk-F3AIYQB7.js.map +0 -1
- package/dist/chunk-PMF6MWEV.cjs.map +0 -1
- package/dist/chunk-RY4WDS6R.js.map +0 -1
- /package/dist/{chunk-IUZXKAAY.js.map → chunk-FG3M7EBL.js.map} +0 -0
package/dist/index.js
CHANGED
|
@@ -2,7 +2,7 @@ import {
|
|
|
2
2
|
createContext,
|
|
3
3
|
hasContext,
|
|
4
4
|
useContext
|
|
5
|
-
} from "./chunk-
|
|
5
|
+
} from "./chunk-FG3M7EBL.js";
|
|
6
6
|
import {
|
|
7
7
|
Fragment,
|
|
8
8
|
batch2 as batch,
|
|
@@ -34,7 +34,7 @@ import {
|
|
|
34
34
|
untrack2 as untrack,
|
|
35
35
|
useDeferredValue,
|
|
36
36
|
useTransition
|
|
37
|
-
} from "./chunk-
|
|
37
|
+
} from "./chunk-5KXEEQUO.js";
|
|
38
38
|
|
|
39
39
|
// src/ref.ts
|
|
40
40
|
function createRef() {
|
|
@@ -153,10 +153,6 @@ function Suspense(props) {
|
|
|
153
153
|
let epoch = 0;
|
|
154
154
|
const hostRoot = getCurrentRoot();
|
|
155
155
|
const toFallback = (err) => typeof props.fallback === "function" ? props.fallback(err) : props.fallback;
|
|
156
|
-
const switchView = (view) => {
|
|
157
|
-
currentView(view);
|
|
158
|
-
renderView(view);
|
|
159
|
-
};
|
|
160
156
|
const renderView = (view) => {
|
|
161
157
|
if (cleanup) {
|
|
162
158
|
cleanup();
|
|
@@ -175,7 +171,7 @@ function Suspense(props) {
|
|
|
175
171
|
try {
|
|
176
172
|
const output = createElement(view);
|
|
177
173
|
nodes = toNodeArray(output);
|
|
178
|
-
const suspendedAttempt = nodes.length > 0 && nodes.every((node) => node instanceof Comment && node.data === "fict:suspend");
|
|
174
|
+
const suspendedAttempt = root.suspended || nodes.length > 0 && nodes.every((node) => node instanceof Comment && node.data === "fict:suspend");
|
|
179
175
|
if (suspendedAttempt) {
|
|
180
176
|
popRoot(prev);
|
|
181
177
|
destroyRoot(root);
|
|
@@ -216,7 +212,8 @@ function Suspense(props) {
|
|
|
216
212
|
registerSuspenseHandler((token) => {
|
|
217
213
|
const tokenEpoch = epoch;
|
|
218
214
|
pending(pending() + 1);
|
|
219
|
-
|
|
215
|
+
currentView(toFallback());
|
|
216
|
+
renderView(toFallback());
|
|
220
217
|
const thenable = token.then ? token : isThenable(token) ? token : null;
|
|
221
218
|
if (thenable) {
|
|
222
219
|
thenable.then(
|
|
@@ -227,7 +224,8 @@ function Suspense(props) {
|
|
|
227
224
|
const newPending = Math.max(0, pending() - 1);
|
|
228
225
|
pending(newPending);
|
|
229
226
|
if (newPending === 0) {
|
|
230
|
-
|
|
227
|
+
currentView(props.children ?? null);
|
|
228
|
+
renderView(props.children ?? null);
|
|
231
229
|
onResolveMaybe();
|
|
232
230
|
}
|
|
233
231
|
},
|
|
@@ -247,9 +245,7 @@ function Suspense(props) {
|
|
|
247
245
|
}
|
|
248
246
|
return false;
|
|
249
247
|
});
|
|
250
|
-
|
|
251
|
-
renderView(currentView());
|
|
252
|
-
});
|
|
248
|
+
renderView(props.children ?? null);
|
|
253
249
|
if (props.resetKeys !== void 0) {
|
|
254
250
|
const isGetter = typeof props.resetKeys === "function" && props.resetKeys.length === 0;
|
|
255
251
|
const getter = isGetter ? props.resetKeys : void 0;
|
|
@@ -260,7 +256,8 @@ function Suspense(props) {
|
|
|
260
256
|
prev = next;
|
|
261
257
|
epoch++;
|
|
262
258
|
pending(0);
|
|
263
|
-
|
|
259
|
+
currentView(props.children ?? null);
|
|
260
|
+
renderView(props.children ?? null);
|
|
264
261
|
}
|
|
265
262
|
});
|
|
266
263
|
}
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/ref.ts","../src/error-boundary.ts","../src/suspense.ts"],"sourcesContent":["import type { RefObject } from './types'\n\n/**\n * Create a ref object for DOM element references.\n *\n * @returns A ref object with a `current` property initialized to `null`\n *\n * @example\n * ```tsx\n * import { createRef } from 'fict'\n *\n * function Component() {\n * const inputRef = createRef<HTMLInputElement>()\n *\n * $effect(() => {\n * inputRef.current?.focus()\n * })\n *\n * return <input ref={inputRef} />\n * }\n * ```\n */\nexport function createRef<T extends Element = HTMLElement>(): RefObject<T> {\n return { current: null }\n}\n","import { createElement } from './dom'\nimport { createEffect } from './effect'\nimport {\n createRootContext,\n destroyRoot,\n flushOnMount,\n getCurrentRoot,\n pushRoot,\n popRoot,\n registerErrorHandler,\n} from './lifecycle'\nimport { insertNodesBefore, removeNodes, toNodeArray } from './node-ops'\nimport { createSignal } from './signal'\nimport type { BaseProps, FictNode } from './types'\n\ninterface ErrorBoundaryProps extends BaseProps {\n fallback: FictNode | ((err: unknown) => FictNode)\n onError?: (err: unknown) => void\n resetKeys?: unknown | (() => unknown)\n}\n\nexport function ErrorBoundary(props: ErrorBoundaryProps): FictNode {\n const fragment = document.createDocumentFragment()\n const marker = document.createComment('fict:error-boundary')\n fragment.appendChild(marker)\n\n const currentView = createSignal<FictNode | null>(props.children ?? null)\n const hostRoot = getCurrentRoot()\n\n let cleanup: (() => void) | undefined\n let activeNodes: Node[] = []\n let renderingFallback = false\n\n const toView = (err: unknown | null): FictNode | null => {\n if (err != null) {\n return typeof props.fallback === 'function'\n ? (props.fallback as (e: unknown) => FictNode)(err)\n : props.fallback\n }\n return props.children ?? null\n }\n\n const renderValue = (value: FictNode | null) => {\n if (cleanup) {\n cleanup()\n cleanup = undefined\n }\n if (activeNodes.length) {\n removeNodes(activeNodes)\n activeNodes = []\n }\n\n if (value == null || value === false) {\n return\n }\n\n const root = createRootContext(hostRoot)\n const prev = pushRoot(root)\n let nodes: Node[] = []\n try {\n const output = createElement(value)\n nodes = toNodeArray(output)\n const parentNode = marker.parentNode as (ParentNode & Node) | null\n if (parentNode) {\n insertNodesBefore(parentNode, nodes, marker)\n }\n } catch (err) {\n popRoot(prev)\n flushOnMount(root)\n destroyRoot(root)\n // Fall back immediately on render errors, avoid infinite recursion\n if (renderingFallback) {\n throw err\n }\n // nested errors. If fallback rendering also throws, we should NOT reset\n // the flag until we're sure no more recursion is happening.\n renderingFallback = true\n try {\n renderValue(toView(err))\n // Only reset if successful - if renderValue threw, we want to keep\n // renderingFallback = true to prevent infinite recursion\n renderingFallback = false\n props.onError?.(err)\n } catch (fallbackErr) {\n // Fallback rendering failed - keep renderingFallback = true\n // to prevent further attempts, then rethrow\n // If fallback fails, report both errors\n props.onError?.(err)\n throw fallbackErr\n }\n return\n }\n popRoot(prev)\n flushOnMount(root)\n\n cleanup = () => {\n destroyRoot(root)\n removeNodes(nodes)\n }\n activeNodes = nodes\n }\n\n createEffect(() => {\n const value = currentView()\n renderValue(value)\n })\n\n registerErrorHandler(err => {\n renderValue(toView(err))\n props.onError?.(err)\n return true\n })\n\n if (props.resetKeys !== undefined) {\n const isGetter =\n typeof props.resetKeys === 'function' && (props.resetKeys as () => unknown).length === 0\n const getter = isGetter ? (props.resetKeys as () => unknown) : undefined\n let prev = isGetter ? getter!() : props.resetKeys\n createEffect(() => {\n const next = getter ? getter() : props.resetKeys\n if (prev !== next) {\n prev = next\n renderValue(toView(null))\n }\n })\n }\n\n return fragment\n}\n","import { createElement } from './dom'\nimport { createEffect } from './effect'\nimport {\n createRootContext,\n destroyRoot,\n flushOnMount,\n getCurrentRoot,\n handleError,\n pushRoot,\n popRoot,\n registerSuspenseHandler,\n} from './lifecycle'\nimport { insertNodesBefore, removeNodes, toNodeArray } from './node-ops'\nimport { createSignal } from './signal'\nimport type { BaseProps, FictNode, SuspenseToken } from './types'\n\nexport interface SuspenseProps extends BaseProps {\n fallback: FictNode | ((err?: unknown) => FictNode)\n onResolve?: () => void\n onReject?: (err: unknown) => void\n resetKeys?: unknown | (() => unknown)\n}\n\nexport interface SuspenseHandle {\n token: SuspenseToken\n resolve: () => void\n reject: (err: unknown) => void\n}\n\nexport function createSuspenseToken(): SuspenseHandle {\n let resolve!: () => void\n let reject!: (err: unknown) => void\n const promise = new Promise<void>((res, rej) => {\n resolve = res\n reject = rej\n })\n return {\n token: {\n then: promise.then.bind(promise),\n },\n resolve,\n reject,\n }\n}\n\nconst isThenable = (value: unknown): value is PromiseLike<unknown> =>\n typeof value === 'object' &&\n value !== null &&\n typeof (value as PromiseLike<unknown>).then === 'function'\n\nexport function Suspense(props: SuspenseProps): FictNode {\n const currentView = createSignal<FictNode | null>(props.children ?? null)\n const pending = createSignal(0)\n let resolvedOnce = false\n let epoch = 0\n const hostRoot = getCurrentRoot()\n\n const toFallback = (err?: unknown) =>\n typeof props.fallback === 'function'\n ? (props.fallback as (e?: unknown) => FictNode)(err)\n : props.fallback\n\n const switchView = (view: FictNode | null) => {\n currentView(view)\n renderView(view)\n }\n\n const renderView = (view: FictNode | null) => {\n if (cleanup) {\n cleanup()\n cleanup = undefined\n }\n if (activeNodes.length) {\n removeNodes(activeNodes)\n activeNodes = []\n }\n\n if (view == null || view === false) {\n return\n }\n\n const root = createRootContext(hostRoot)\n const prev = pushRoot(root)\n let nodes: Node[] = []\n try {\n const output = createElement(view)\n nodes = toNodeArray(output)\n // Suspended view: child threw a suspense token and was handled upstream.\n // Avoid replacing existing fallback content; tear down this attempt.\n const suspendedAttempt =\n nodes.length > 0 &&\n nodes.every(node => node instanceof Comment && (node as Comment).data === 'fict:suspend')\n if (suspendedAttempt) {\n popRoot(prev)\n destroyRoot(root)\n return\n }\n const parentNode = marker.parentNode as (ParentNode & Node) | null\n if (parentNode) {\n insertNodesBefore(parentNode, nodes, marker)\n }\n } catch (err) {\n popRoot(prev)\n flushOnMount(root)\n destroyRoot(root)\n if (!handleError(err, { source: 'render' }, hostRoot)) {\n throw err\n }\n return\n }\n popRoot(prev)\n flushOnMount(root)\n\n cleanup = () => {\n destroyRoot(root)\n removeNodes(nodes)\n }\n activeNodes = nodes\n }\n\n const fragment = document.createDocumentFragment()\n const marker = document.createComment('fict:suspense')\n fragment.appendChild(marker)\n let cleanup: (() => void) | undefined\n let activeNodes: Node[] = []\n\n const onResolveMaybe = () => {\n if (!resolvedOnce) {\n resolvedOnce = true\n props.onResolve?.()\n }\n }\n\n registerSuspenseHandler(token => {\n const tokenEpoch = epoch\n pending(pending() + 1)\n switchView(toFallback())\n\n const thenable = (token as SuspenseToken).then\n ? (token as SuspenseToken)\n : isThenable(token)\n ? token\n : null\n\n if (thenable) {\n thenable.then(\n () => {\n // This prevents stale token resolutions from affecting state after\n // a reset. The order is important: check epoch first, then update state.\n if (epoch !== tokenEpoch) {\n // Token is stale (from before a reset), ignore it completely\n return\n }\n // Use Math.max as a defensive measure - pending should never go below 0,\n // but this protects against edge cases where a token might resolve twice\n // or after the component has been reset.\n const newPending = Math.max(0, pending() - 1)\n pending(newPending)\n if (newPending === 0) {\n switchView(props.children ?? null)\n onResolveMaybe()\n }\n },\n err => {\n // Same epoch check - ignore stale tokens\n if (epoch !== tokenEpoch) {\n return\n }\n const newPending = Math.max(0, pending() - 1)\n pending(newPending)\n props.onReject?.(err)\n if (!handleError(err, { source: 'render' }, hostRoot)) {\n throw err\n }\n },\n )\n return true\n }\n\n return false\n })\n\n createEffect(() => {\n renderView(currentView())\n })\n\n if (props.resetKeys !== undefined) {\n const isGetter =\n typeof props.resetKeys === 'function' && (props.resetKeys as () => unknown).length === 0\n const getter = isGetter ? (props.resetKeys as () => unknown) : undefined\n let prev = isGetter ? getter!() : props.resetKeys\n createEffect(() => {\n const next = getter ? getter() : props.resetKeys\n if (prev !== next) {\n prev = next\n epoch++\n pending(0)\n switchView(props.children ?? null)\n }\n })\n }\n\n return fragment\n}\n"],"mappings":"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","names":[]}
|
|
1
|
+
{"version":3,"sources":["../src/ref.ts","../src/error-boundary.ts","../src/suspense.ts"],"sourcesContent":["import type { RefObject } from './types'\n\n/**\n * Create a ref object for DOM element references.\n *\n * @returns A ref object with a `current` property initialized to `null`\n *\n * @example\n * ```tsx\n * import { createRef } from 'fict'\n *\n * function Component() {\n * const inputRef = createRef<HTMLInputElement>()\n *\n * $effect(() => {\n * inputRef.current?.focus()\n * })\n *\n * return <input ref={inputRef} />\n * }\n * ```\n */\nexport function createRef<T extends Element = HTMLElement>(): RefObject<T> {\n return { current: null }\n}\n","import { createElement } from './dom'\nimport { createEffect } from './effect'\nimport {\n createRootContext,\n destroyRoot,\n flushOnMount,\n getCurrentRoot,\n pushRoot,\n popRoot,\n registerErrorHandler,\n} from './lifecycle'\nimport { insertNodesBefore, removeNodes, toNodeArray } from './node-ops'\nimport { createSignal } from './signal'\nimport type { BaseProps, FictNode } from './types'\n\ninterface ErrorBoundaryProps extends BaseProps {\n fallback: FictNode | ((err: unknown) => FictNode)\n onError?: (err: unknown) => void\n resetKeys?: unknown | (() => unknown)\n}\n\nexport function ErrorBoundary(props: ErrorBoundaryProps): FictNode {\n const fragment = document.createDocumentFragment()\n const marker = document.createComment('fict:error-boundary')\n fragment.appendChild(marker)\n\n const currentView = createSignal<FictNode | null>(props.children ?? null)\n const hostRoot = getCurrentRoot()\n\n let cleanup: (() => void) | undefined\n let activeNodes: Node[] = []\n let renderingFallback = false\n\n const toView = (err: unknown | null): FictNode | null => {\n if (err != null) {\n return typeof props.fallback === 'function'\n ? (props.fallback as (e: unknown) => FictNode)(err)\n : props.fallback\n }\n return props.children ?? null\n }\n\n const renderValue = (value: FictNode | null) => {\n if (cleanup) {\n cleanup()\n cleanup = undefined\n }\n if (activeNodes.length) {\n removeNodes(activeNodes)\n activeNodes = []\n }\n\n if (value == null || value === false) {\n return\n }\n\n const root = createRootContext(hostRoot)\n const prev = pushRoot(root)\n let nodes: Node[] = []\n try {\n const output = createElement(value)\n nodes = toNodeArray(output)\n const parentNode = marker.parentNode as (ParentNode & Node) | null\n if (parentNode) {\n insertNodesBefore(parentNode, nodes, marker)\n }\n } catch (err) {\n popRoot(prev)\n flushOnMount(root)\n destroyRoot(root)\n // Fall back immediately on render errors, avoid infinite recursion\n if (renderingFallback) {\n throw err\n }\n // nested errors. If fallback rendering also throws, we should NOT reset\n // the flag until we're sure no more recursion is happening.\n renderingFallback = true\n try {\n renderValue(toView(err))\n // Only reset if successful - if renderValue threw, we want to keep\n // renderingFallback = true to prevent infinite recursion\n renderingFallback = false\n props.onError?.(err)\n } catch (fallbackErr) {\n // Fallback rendering failed - keep renderingFallback = true\n // to prevent further attempts, then rethrow\n // If fallback fails, report both errors\n props.onError?.(err)\n throw fallbackErr\n }\n return\n }\n popRoot(prev)\n flushOnMount(root)\n\n cleanup = () => {\n destroyRoot(root)\n removeNodes(nodes)\n }\n activeNodes = nodes\n }\n\n createEffect(() => {\n const value = currentView()\n renderValue(value)\n })\n\n registerErrorHandler(err => {\n renderValue(toView(err))\n props.onError?.(err)\n return true\n })\n\n if (props.resetKeys !== undefined) {\n const isGetter =\n typeof props.resetKeys === 'function' && (props.resetKeys as () => unknown).length === 0\n const getter = isGetter ? (props.resetKeys as () => unknown) : undefined\n let prev = isGetter ? getter!() : props.resetKeys\n createEffect(() => {\n const next = getter ? getter() : props.resetKeys\n if (prev !== next) {\n prev = next\n renderValue(toView(null))\n }\n })\n }\n\n return fragment\n}\n","import { createElement } from './dom'\nimport { createEffect } from './effect'\nimport {\n createRootContext,\n destroyRoot,\n flushOnMount,\n getCurrentRoot,\n handleError,\n pushRoot,\n popRoot,\n registerSuspenseHandler,\n} from './lifecycle'\nimport { insertNodesBefore, removeNodes, toNodeArray } from './node-ops'\nimport { createSignal } from './signal'\nimport type { BaseProps, FictNode, SuspenseToken } from './types'\n\nexport interface SuspenseProps extends BaseProps {\n fallback: FictNode | ((err?: unknown) => FictNode)\n onResolve?: () => void\n onReject?: (err: unknown) => void\n resetKeys?: unknown | (() => unknown)\n}\n\nexport interface SuspenseHandle {\n token: SuspenseToken\n resolve: () => void\n reject: (err: unknown) => void\n}\n\nexport function createSuspenseToken(): SuspenseHandle {\n let resolve!: () => void\n let reject!: (err: unknown) => void\n const promise = new Promise<void>((res, rej) => {\n resolve = res\n reject = rej\n })\n return {\n token: {\n then: promise.then.bind(promise),\n },\n resolve,\n reject,\n }\n}\n\nconst isThenable = (value: unknown): value is PromiseLike<unknown> =>\n typeof value === 'object' &&\n value !== null &&\n typeof (value as PromiseLike<unknown>).then === 'function'\n\nexport function Suspense(props: SuspenseProps): FictNode {\n const currentView = createSignal<FictNode | null>(props.children ?? null)\n const pending = createSignal(0)\n let resolvedOnce = false\n let epoch = 0\n const hostRoot = getCurrentRoot()\n\n const toFallback = (err?: unknown) =>\n typeof props.fallback === 'function'\n ? (props.fallback as (e?: unknown) => FictNode)(err)\n : props.fallback\n\n const renderView = (view: FictNode | null) => {\n if (cleanup) {\n cleanup()\n cleanup = undefined\n }\n if (activeNodes.length) {\n removeNodes(activeNodes)\n activeNodes = []\n }\n\n if (view == null || view === false) {\n return\n }\n\n const root = createRootContext(hostRoot)\n const prev = pushRoot(root)\n let nodes: Node[] = []\n try {\n const output = createElement(view)\n nodes = toNodeArray(output)\n // Suspended view: child threw a suspense token and was handled upstream.\n // Avoid replacing existing fallback content; tear down this attempt.\n const suspendedAttempt =\n root.suspended ||\n (nodes.length > 0 &&\n nodes.every(node => node instanceof Comment && (node as Comment).data === 'fict:suspend'))\n if (suspendedAttempt) {\n popRoot(prev)\n destroyRoot(root)\n return\n }\n const parentNode = marker.parentNode as (ParentNode & Node) | null\n if (parentNode) {\n insertNodesBefore(parentNode, nodes, marker)\n }\n } catch (err) {\n popRoot(prev)\n flushOnMount(root)\n destroyRoot(root)\n if (!handleError(err, { source: 'render' }, hostRoot)) {\n throw err\n }\n return\n }\n popRoot(prev)\n flushOnMount(root)\n\n cleanup = () => {\n destroyRoot(root)\n removeNodes(nodes)\n }\n activeNodes = nodes\n }\n\n const fragment = document.createDocumentFragment()\n const marker = document.createComment('fict:suspense')\n fragment.appendChild(marker)\n let cleanup: (() => void) | undefined\n let activeNodes: Node[] = []\n\n const onResolveMaybe = () => {\n if (!resolvedOnce) {\n resolvedOnce = true\n props.onResolve?.()\n }\n }\n\n registerSuspenseHandler(token => {\n const tokenEpoch = epoch\n pending(pending() + 1)\n // Directly render fallback instead of using switchView to avoid\n // triggering the effect which would cause duplicate renders\n currentView(toFallback())\n renderView(toFallback())\n\n const thenable = (token as SuspenseToken).then\n ? (token as SuspenseToken)\n : isThenable(token)\n ? token\n : null\n\n if (thenable) {\n thenable.then(\n () => {\n // This prevents stale token resolutions from affecting state after\n // a reset. The order is important: check epoch first, then update state.\n if (epoch !== tokenEpoch) {\n // Token is stale (from before a reset), ignore it completely\n return\n }\n // Use Math.max as a defensive measure - pending should never go below 0,\n // but this protects against edge cases where a token might resolve twice\n // or after the component has been reset.\n const newPending = Math.max(0, pending() - 1)\n pending(newPending)\n if (newPending === 0) {\n // Directly render children instead of using switchView\n currentView(props.children ?? null)\n renderView(props.children ?? null)\n onResolveMaybe()\n }\n },\n err => {\n // Same epoch check - ignore stale tokens\n if (epoch !== tokenEpoch) {\n return\n }\n const newPending = Math.max(0, pending() - 1)\n pending(newPending)\n props.onReject?.(err)\n if (!handleError(err, { source: 'render' }, hostRoot)) {\n throw err\n }\n },\n )\n return true\n }\n\n return false\n })\n\n // Initial render - render children directly\n // Note: This will be called synchronously during component creation.\n // If children suspend, the handler above will be called and switch to fallback.\n renderView(props.children ?? null)\n\n if (props.resetKeys !== undefined) {\n const isGetter =\n typeof props.resetKeys === 'function' && (props.resetKeys as () => unknown).length === 0\n const getter = isGetter ? (props.resetKeys as () => unknown) : undefined\n let prev = isGetter ? getter!() : props.resetKeys\n createEffect(() => {\n const next = getter ? getter() : props.resetKeys\n if (prev !== next) {\n prev = next\n epoch++\n pending(0)\n // Directly render children instead of using switchView\n currentView(props.children ?? null)\n renderView(props.children ?? null)\n }\n })\n }\n\n return fragment\n}\n"],"mappings":"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","names":[]}
|
package/dist/internal.cjs
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";Object.defineProperty(exports, "__esModule", {value: true}); function _nullishCoalesce(lhs, rhsFn) { if (lhs != null) { return lhs; } else { return rhsFn(); } } function _optionalChain(ops) { let lastAccessLHS = undefined; let value = ops[0]; let i = 1; while (i < ops.length) { const op = ops[i]; const fn = ops[i + 1]; i += 2; if ((op === 'optionalAccess' || op === 'optionalCall') && value == null) { return undefined; } if (op === 'access' || op === 'optionalAccess') { lastAccessLHS = value; value = fn(value); } else if (op === 'call' || op === 'optionalCall') { value = fn((...args) => value.call(lastAccessLHS, ...args)); lastAccessLHS = undefined; } } return value; }
|
|
2
2
|
|
|
3
|
-
var
|
|
3
|
+
var _chunkBSUMPMKXcjs = require('./chunk-BSUMPMKX.cjs');
|
|
4
4
|
|
|
5
5
|
|
|
6
6
|
|
|
@@ -66,7 +66,7 @@ var _chunk624QY53Acjs = require('./chunk-624QY53A.cjs');
|
|
|
66
66
|
|
|
67
67
|
|
|
68
68
|
|
|
69
|
-
var
|
|
69
|
+
var _chunkJ74L7UYPcjs = require('./chunk-J74L7UYP.cjs');
|
|
70
70
|
|
|
71
71
|
// src/store.ts
|
|
72
72
|
var PROXY = Symbol("fict:store-proxy");
|
|
@@ -76,7 +76,7 @@ function createStore(initialValue) {
|
|
|
76
76
|
const unwrapped = unwrap2(initialValue);
|
|
77
77
|
const wrapped = wrap(unwrapped);
|
|
78
78
|
function setStore(fn) {
|
|
79
|
-
|
|
79
|
+
_chunkJ74L7UYPcjs.batch.call(void 0, () => {
|
|
80
80
|
const result = fn(wrapped);
|
|
81
81
|
if (result !== void 0) {
|
|
82
82
|
reconcile(wrapped, result);
|
|
@@ -157,7 +157,7 @@ function track(target, prop2) {
|
|
|
157
157
|
let s = signals.get(prop2);
|
|
158
158
|
if (!s) {
|
|
159
159
|
const initial = prop2 === ITERATE_KEY ? Reflect.ownKeys(target).length : getLastValue(target, prop2);
|
|
160
|
-
s =
|
|
160
|
+
s = _chunkJ74L7UYPcjs.signal.call(void 0, initial);
|
|
161
161
|
signals.set(prop2, s);
|
|
162
162
|
}
|
|
163
163
|
s();
|
|
@@ -308,6 +308,13 @@ function moveNodesBefore(parent, nodes, anchor) {
|
|
|
308
308
|
try {
|
|
309
309
|
const clone = parent.ownerDocument.importNode(node, true);
|
|
310
310
|
parent.insertBefore(clone, anchor);
|
|
311
|
+
nodes[i] = clone;
|
|
312
|
+
if (isDev) {
|
|
313
|
+
console.warn(
|
|
314
|
+
`[fict] Node cloning fallback triggered during list reordering. This may indicate cross-document node insertion. The node reference has been updated to the clone.`
|
|
315
|
+
);
|
|
316
|
+
}
|
|
317
|
+
anchor = clone;
|
|
311
318
|
continue;
|
|
312
319
|
} catch (e2) {
|
|
313
320
|
}
|
|
@@ -322,7 +329,7 @@ var MAX_SAFE_VERSION = 9007199254740991;
|
|
|
322
329
|
function createVersionedSignalAccessor(initialValue) {
|
|
323
330
|
let current = initialValue;
|
|
324
331
|
let version = 0;
|
|
325
|
-
const track2 =
|
|
332
|
+
const track2 = _chunkJ74L7UYPcjs.signal.call(void 0, version);
|
|
326
333
|
function accessor(value) {
|
|
327
334
|
if (arguments.length === 0) {
|
|
328
335
|
track2();
|
|
@@ -339,7 +346,7 @@ function createKeyedListContainer() {
|
|
|
339
346
|
const endMarker = document.createComment("fict:list:end");
|
|
340
347
|
const dispose = () => {
|
|
341
348
|
for (const block of container.blocks.values()) {
|
|
342
|
-
|
|
349
|
+
_chunkJ74L7UYPcjs.destroyRoot.call(void 0, block.root);
|
|
343
350
|
}
|
|
344
351
|
container.blocks.clear();
|
|
345
352
|
container.nextBlocks.clear();
|
|
@@ -378,32 +385,32 @@ function createKeyedListContainer() {
|
|
|
378
385
|
}
|
|
379
386
|
function createKeyedBlock(key, item, index, render, needsIndex = true, hostRoot) {
|
|
380
387
|
const itemSig = createVersionedSignalAccessor(item);
|
|
381
|
-
const indexSig = needsIndex ?
|
|
388
|
+
const indexSig = needsIndex ? _chunkJ74L7UYPcjs.signal.call(void 0, index) : ((next) => {
|
|
382
389
|
if (arguments.length === 0) return index;
|
|
383
390
|
index = next;
|
|
384
391
|
return index;
|
|
385
392
|
});
|
|
386
|
-
const root =
|
|
387
|
-
const prevRoot =
|
|
393
|
+
const root = _chunkJ74L7UYPcjs.createRootContext.call(void 0, hostRoot);
|
|
394
|
+
const prevRoot = _chunkJ74L7UYPcjs.pushRoot.call(void 0, root);
|
|
388
395
|
let nodes = [];
|
|
389
396
|
let scopeDispose;
|
|
390
|
-
const prevSub =
|
|
397
|
+
const prevSub = _chunkJ74L7UYPcjs.setActiveSub.call(void 0, void 0);
|
|
391
398
|
try {
|
|
392
|
-
scopeDispose =
|
|
399
|
+
scopeDispose = _chunkJ74L7UYPcjs.effectScope.call(void 0, () => {
|
|
393
400
|
const rendered = render(itemSig, indexSig, key);
|
|
394
401
|
if (rendered instanceof Node || Array.isArray(rendered) && rendered.every((n) => n instanceof Node)) {
|
|
395
|
-
nodes =
|
|
402
|
+
nodes = _chunkJ74L7UYPcjs.toNodeArray.call(void 0, rendered);
|
|
396
403
|
} else {
|
|
397
|
-
const element =
|
|
398
|
-
nodes =
|
|
404
|
+
const element = _chunkJ74L7UYPcjs.createElement.call(void 0, rendered);
|
|
405
|
+
nodes = _chunkJ74L7UYPcjs.toNodeArray.call(void 0, element);
|
|
399
406
|
}
|
|
400
407
|
});
|
|
401
408
|
if (scopeDispose) {
|
|
402
409
|
root.cleanups.push(scopeDispose);
|
|
403
410
|
}
|
|
404
411
|
} finally {
|
|
405
|
-
|
|
406
|
-
|
|
412
|
+
_chunkJ74L7UYPcjs.setActiveSub.call(void 0, prevSub);
|
|
413
|
+
_chunkJ74L7UYPcjs.popRoot.call(void 0, prevRoot);
|
|
407
414
|
}
|
|
408
415
|
return {
|
|
409
416
|
key,
|
|
@@ -509,7 +516,7 @@ function createKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
509
516
|
}
|
|
510
517
|
function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
511
518
|
const container = createKeyedListContainer();
|
|
512
|
-
const hostRoot =
|
|
519
|
+
const hostRoot = _chunkJ74L7UYPcjs.getCurrentRoot.call(void 0, );
|
|
513
520
|
const fragment = document.createDocumentFragment();
|
|
514
521
|
fragment.append(container.startMarker, container.endMarker);
|
|
515
522
|
let disposed = false;
|
|
@@ -521,7 +528,9 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
521
528
|
const endParent = container.endMarker.parentNode;
|
|
522
529
|
const startParent = container.startMarker.parentNode;
|
|
523
530
|
if (endParent && startParent && endParent === startParent && endParent.nodeType !== 11) {
|
|
524
|
-
|
|
531
|
+
const parentNode = endParent;
|
|
532
|
+
if ("isConnected" in parentNode && !parentNode.isConnected) return null;
|
|
533
|
+
return parentNode;
|
|
525
534
|
}
|
|
526
535
|
return null;
|
|
527
536
|
};
|
|
@@ -529,7 +538,7 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
529
538
|
if (disposed) return;
|
|
530
539
|
const parent = getConnectedParent();
|
|
531
540
|
if (!parent) return;
|
|
532
|
-
|
|
541
|
+
_chunkJ74L7UYPcjs.batch2.call(void 0, () => {
|
|
533
542
|
const oldBlocks = container.blocks;
|
|
534
543
|
const newBlocks = container.nextBlocks;
|
|
535
544
|
const prevOrderedBlocks = container.orderedBlocks;
|
|
@@ -539,7 +548,7 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
539
548
|
if (newItems.length === 0) {
|
|
540
549
|
if (oldBlocks.size > 0) {
|
|
541
550
|
for (const block of oldBlocks.values()) {
|
|
542
|
-
|
|
551
|
+
_chunkJ74L7UYPcjs.destroyRoot.call(void 0, block.root);
|
|
543
552
|
}
|
|
544
553
|
const range = document.createRange();
|
|
545
554
|
range.setStartAfter(container.startMarker);
|
|
@@ -620,8 +629,8 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
620
629
|
`[fict] Duplicate key "${String(key)}" detected in list rendering. Each item should have a unique key. The previous item with this key will be replaced.`
|
|
621
630
|
);
|
|
622
631
|
}
|
|
623
|
-
|
|
624
|
-
|
|
632
|
+
_chunkJ74L7UYPcjs.destroyRoot.call(void 0, existingBlock.root);
|
|
633
|
+
_chunkJ74L7UYPcjs.removeNodes.call(void 0, existingBlock.nodes);
|
|
625
634
|
}
|
|
626
635
|
block = createKeyedBlock(key, item, index, renderItem, needsIndex, hostRoot);
|
|
627
636
|
createdBlocks.push(block);
|
|
@@ -634,8 +643,8 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
634
643
|
hasDuplicateKey = true;
|
|
635
644
|
const prior = nextOrderedBlocks[position];
|
|
636
645
|
if (prior && prior !== resolvedBlock) {
|
|
637
|
-
|
|
638
|
-
|
|
646
|
+
_chunkJ74L7UYPcjs.destroyRoot.call(void 0, prior.root);
|
|
647
|
+
_chunkJ74L7UYPcjs.removeNodes.call(void 0, prior.nodes);
|
|
639
648
|
}
|
|
640
649
|
nextOrderedBlocks[position] = resolvedBlock;
|
|
641
650
|
} else {
|
|
@@ -673,7 +682,7 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
673
682
|
}
|
|
674
683
|
}
|
|
675
684
|
if (appendedNodes.length > 0) {
|
|
676
|
-
|
|
685
|
+
_chunkJ74L7UYPcjs.insertNodesBefore.call(void 0, parent, appendedNodes, container.endMarker);
|
|
677
686
|
const currentNodes = container.currentNodes;
|
|
678
687
|
currentNodes.pop();
|
|
679
688
|
for (let i = 0; i < appendedNodes.length; i++) {
|
|
@@ -687,15 +696,15 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
687
696
|
container.nextOrderedBlocks = prevOrderedBlocks;
|
|
688
697
|
for (const block of createdBlocks) {
|
|
689
698
|
if (newBlocks.get(block.key) === block) {
|
|
690
|
-
|
|
699
|
+
_chunkJ74L7UYPcjs.flushOnMount.call(void 0, block.root);
|
|
691
700
|
}
|
|
692
701
|
}
|
|
693
702
|
return;
|
|
694
703
|
}
|
|
695
704
|
if (oldBlocks.size > 0) {
|
|
696
705
|
for (const block of oldBlocks.values()) {
|
|
697
|
-
|
|
698
|
-
|
|
706
|
+
_chunkJ74L7UYPcjs.destroyRoot.call(void 0, block.root);
|
|
707
|
+
_chunkJ74L7UYPcjs.removeNodes.call(void 0, block.nodes);
|
|
699
708
|
}
|
|
700
709
|
oldBlocks.clear();
|
|
701
710
|
}
|
|
@@ -754,7 +763,7 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
754
763
|
container.nextOrderedBlocks = prevOrderedBlocks;
|
|
755
764
|
for (const block of createdBlocks) {
|
|
756
765
|
if (newBlocks.get(block.key) === block) {
|
|
757
|
-
|
|
766
|
+
_chunkJ74L7UYPcjs.flushOnMount.call(void 0, block.root);
|
|
758
767
|
}
|
|
759
768
|
}
|
|
760
769
|
});
|
|
@@ -768,15 +777,15 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
768
777
|
const parent = getConnectedParent();
|
|
769
778
|
if (!parent) return false;
|
|
770
779
|
const start = () => {
|
|
771
|
-
effectDispose =
|
|
780
|
+
effectDispose = _chunkJ74L7UYPcjs.createRenderEffect.call(void 0, performDiff);
|
|
772
781
|
effectStarted = true;
|
|
773
782
|
};
|
|
774
783
|
if (hostRoot) {
|
|
775
|
-
const prev =
|
|
784
|
+
const prev = _chunkJ74L7UYPcjs.pushRoot.call(void 0, hostRoot);
|
|
776
785
|
try {
|
|
777
786
|
start();
|
|
778
787
|
} finally {
|
|
779
|
-
|
|
788
|
+
_chunkJ74L7UYPcjs.popRoot.call(void 0, prev);
|
|
780
789
|
}
|
|
781
790
|
} else {
|
|
782
791
|
start();
|
|
@@ -790,7 +799,7 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
790
799
|
if (getConnectedParent()) {
|
|
791
800
|
disconnectObserver();
|
|
792
801
|
if (ensureEffectStarted()) {
|
|
793
|
-
|
|
802
|
+
_chunkJ74L7UYPcjs.flush.call(void 0, );
|
|
794
803
|
}
|
|
795
804
|
}
|
|
796
805
|
});
|
|
@@ -824,7 +833,7 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
824
833
|
if (disposed) return;
|
|
825
834
|
scheduleStart();
|
|
826
835
|
if (ensureEffectStarted()) {
|
|
827
|
-
|
|
836
|
+
_chunkJ74L7UYPcjs.flush.call(void 0, );
|
|
828
837
|
} else {
|
|
829
838
|
waitForConnection();
|
|
830
839
|
}
|
|
@@ -897,5 +906,5 @@ function createFineGrainedKeyedList(getItems, keyFn, renderItem, needsIndex) {
|
|
|
897
906
|
|
|
898
907
|
|
|
899
908
|
|
|
900
|
-
exports.Aliases =
|
|
909
|
+
exports.Aliases = _chunkJ74L7UYPcjs.Aliases; exports.BooleanAttributes = _chunkJ74L7UYPcjs.BooleanAttributes; exports.ChildProperties = _chunkJ74L7UYPcjs.ChildProperties; exports.DelegatedEvents = _chunkJ74L7UYPcjs.DelegatedEvents; exports.Fragment = _chunkJ74L7UYPcjs.Fragment; exports.Properties = _chunkJ74L7UYPcjs.Properties; exports.SVGElements = _chunkJ74L7UYPcjs.SVGElements; exports.SVGNamespace = _chunkJ74L7UYPcjs.SVGNamespace; exports.UnitlessStyles = _chunkJ74L7UYPcjs.UnitlessStyles; exports.__fictPopContext = _chunkJ74L7UYPcjs.__fictPopContext; exports.__fictProp = _chunkJ74L7UYPcjs.__fictProp; exports.__fictPropsRest = _chunkJ74L7UYPcjs.__fictPropsRest; exports.__fictPushContext = _chunkJ74L7UYPcjs.__fictPushContext; exports.__fictRender = _chunkJ74L7UYPcjs.__fictRender; exports.__fictResetContext = _chunkJ74L7UYPcjs.__fictResetContext; exports.__fictUseContext = _chunkJ74L7UYPcjs.__fictUseContext; exports.__fictUseEffect = _chunkJ74L7UYPcjs.__fictUseEffect; exports.__fictUseMemo = _chunkJ74L7UYPcjs.__fictUseMemo; exports.__fictUseSignal = _chunkJ74L7UYPcjs.__fictUseSignal; exports.addEventListener = _chunkJ74L7UYPcjs.addEventListener; exports.assign = _chunkJ74L7UYPcjs.assign; exports.bindAttribute = _chunkJ74L7UYPcjs.bindAttribute; exports.bindClass = _chunkJ74L7UYPcjs.bindClass; exports.bindEvent = _chunkJ74L7UYPcjs.bindEvent; exports.bindProperty = _chunkJ74L7UYPcjs.bindProperty; exports.bindRef = _chunkJ74L7UYPcjs.bindRef; exports.bindStyle = _chunkJ74L7UYPcjs.bindStyle; exports.bindText = _chunkJ74L7UYPcjs.bindText; exports.callEventHandler = _chunkJ74L7UYPcjs.callEventHandler; exports.classList = _chunkJ74L7UYPcjs.classList; exports.clearDelegatedEvents = _chunkJ74L7UYPcjs.clearDelegatedEvents; exports.createConditional = _chunkJ74L7UYPcjs.createConditional; exports.createEffect = _chunkJ74L7UYPcjs.createEffect; exports.createElement = _chunkJ74L7UYPcjs.createElement; exports.createKeyedList = createKeyedList; exports.createMemo = _chunkJ74L7UYPcjs.createMemo; exports.createPortal = _chunkJ74L7UYPcjs.createPortal; exports.createPropsProxy = _chunkJ74L7UYPcjs.createPropsProxy; exports.createRenderEffect = _chunkJ74L7UYPcjs.createRenderEffect; exports.createSelector = _chunkJ74L7UYPcjs.createSelector; exports.createSignal = _chunkJ74L7UYPcjs.signal; exports.createStore = createStore; exports.delegateEvents = _chunkJ74L7UYPcjs.delegateEvents; exports.getPropAlias = _chunkJ74L7UYPcjs.getPropAlias; exports.insert = _chunkJ74L7UYPcjs.insert; exports.insertNodesBefore = _chunkJ74L7UYPcjs.insertNodesBefore; exports.isNodeBetweenMarkers = isNodeBetweenMarkers; exports.isReactive = _chunkJ74L7UYPcjs.isReactive; exports.mergeProps = _chunkJ74L7UYPcjs.mergeProps; exports.moveNodesBefore = moveNodesBefore; exports.onDestroy = _chunkJ74L7UYPcjs.onDestroy; exports.prop = _chunkJ74L7UYPcjs.prop; exports.reconcileArrays = reconcileArrays; exports.removeNodes = _chunkJ74L7UYPcjs.removeNodes; exports.runInScope = _chunkBSUMPMKXcjs.runInScope; exports.spread = _chunkJ74L7UYPcjs.spread; exports.template = _chunkJ74L7UYPcjs.template; exports.toNodeArray = _chunkJ74L7UYPcjs.toNodeArray; exports.unwrap = _chunkJ74L7UYPcjs.unwrap;
|
|
901
910
|
//# sourceMappingURL=internal.cjs.map
|