From 1c4db3d341bb7bd8a4d4a88989e9c3026707d2c7 Mon Sep 17 00:00:00 2001 From: Rich Harris Date: Mon, 27 Jan 2025 21:22:39 -0500 Subject: [PATCH] hoist functions, use names to make stuff a little clearer --- .../internal/client/dom/blocks/boundary.js | 135 ++++++++++-------- 1 file changed, 73 insertions(+), 62 deletions(-) diff --git a/packages/svelte/src/internal/client/dom/blocks/boundary.js b/packages/svelte/src/internal/client/dom/blocks/boundary.js index aa8af3a71c..976c1eb772 100644 --- a/packages/svelte/src/internal/client/dom/blocks/boundary.js +++ b/packages/svelte/src/internal/client/dom/blocks/boundary.js @@ -83,7 +83,10 @@ export function boundary(node, props, boundary_fn) { var hydrate_open = hydrate_node; var is_creating_fallback = false; - var render_snippet = (/** @type { () => void } */ snippet_fn) => { + /** + * @param {() => void} snippet_fn + */ + function render_snippet(snippet_fn) { with_boundary(boundary, () => { is_creating_fallback = true; @@ -98,69 +101,87 @@ export function boundary(node, props, boundary_fn) { reset_is_throwing_error(); is_creating_fallback = false; }); - }; + } + + function suspend() { + if (async_effect || !boundary_effect) { + return; + } + + var effect = boundary_effect; + async_effect = boundary_effect; + + pause_effect( + async_effect, + () => { + /** @type {TemplateNode | null} */ + var node = effect.nodes_start; + var end = effect.nodes_end; + async_fragment = document.createDocumentFragment(); + + while (node !== null) { + /** @type {TemplateNode | null} */ + var sibling = + node === end ? null : /** @type {TemplateNode} */ (get_next_sibling(node)); + + node.remove(); + async_fragment.append(node); + node = sibling; + } + }, + false + ); + + const pending = props.pending; + + if (pending) { + render_snippet(() => { + pending(anchor); + }); + } + } + + function unsuspend() { + if (!async_effect) { + return; + } + + if (boundary_effect) { + destroy_effect(boundary_effect); + } + + boundary_effect = async_effect; + async_effect = null; + anchor.before(/** @type {DocumentFragment} */ (async_fragment)); + resume_effect(boundary_effect); + } + + function reset() { + pause_effect(boundary_effect); + + with_boundary(boundary, () => { + is_creating_fallback = false; + boundary_effect = branch(() => boundary_fn(anchor)); + reset_is_throwing_error(); + }); + } // @ts-ignore We re-use the effect's fn property to avoid allocation of an additional field boundary.fn = (/** @type {unknown} */ input) => { - let pending = /** @type {(anchor: Node) => void} */ (props.pending); - if (input === ASYNC_INCREMENT) { if (async_count++ === 0) { - queue_boundary_micro_task(() => { - if (async_effect || !boundary_effect) { - return; - } - - var effect = boundary_effect; - async_effect = boundary_effect; - - pause_effect( - async_effect, - () => { - /** @type {TemplateNode | null} */ - var node = effect.nodes_start; - var end = effect.nodes_end; - async_fragment = document.createDocumentFragment(); - - while (node !== null) { - /** @type {TemplateNode | null} */ - var sibling = - node === end ? null : /** @type {TemplateNode} */ (get_next_sibling(node)); - - node.remove(); - async_fragment.append(node); - node = sibling; - } - }, - false - ); - - render_snippet(() => { - pending(anchor); - }); - }); + queue_boundary_micro_task(suspend); } - return true; + return; } if (input === ASYNC_DECREMENT) { if (--async_count === 0) { - queue_boundary_micro_task(() => { - if (!async_effect) { - return; - } - if (boundary_effect) { - destroy_effect(boundary_effect); - } - boundary_effect = async_effect; - async_effect = null; - anchor.before(/** @type {DocumentFragment} */ (async_fragment)); - resume_effect(boundary_effect); - }); + queue_boundary_micro_task(unsuspend); } - return true; + return; } var error = input; @@ -169,20 +190,10 @@ export function boundary(node, props, boundary_fn) { // If we have nothing to capture the error, or if we hit an error while // rendering the fallback, re-throw for another boundary to handle - if ((!onerror && !failed) || is_creating_fallback) { + if (is_creating_fallback || (!onerror && !failed)) { throw error; } - var reset = () => { - pause_effect(boundary_effect); - - with_boundary(boundary, () => { - is_creating_fallback = false; - boundary_effect = branch(() => boundary_fn(anchor)); - reset_is_throwing_error(); - }); - }; - onerror?.(error, reset); if (boundary_effect) {