svelte 5.40.2 → 5.41.1
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/compiler/index.js +1 -1
- package/package.json +1 -1
- package/src/compiler/errors.js +11 -2
- package/src/compiler/phases/2-analyze/visitors/CallExpression.js +7 -0
- package/src/compiler/phases/2-analyze/visitors/EachBlock.js +5 -0
- package/src/compiler/phases/3-transform/client/transform-client.js +4 -1
- package/src/compiler/phases/3-transform/client/visitors/CallExpression.js +6 -0
- package/src/compiler/phases/3-transform/client/visitors/Fragment.js +7 -2
- package/src/compiler/phases/3-transform/client/visitors/LetDirective.js +21 -17
- package/src/compiler/phases/3-transform/client/visitors/RegularElement.js +1 -1
- package/src/compiler/phases/3-transform/client/visitors/SlotElement.js +1 -1
- package/src/compiler/phases/3-transform/client/visitors/SvelteFragment.js +1 -1
- package/src/compiler/phases/3-transform/client/visitors/shared/component.js +2 -2
- package/src/compiler/phases/3-transform/server/visitors/CallExpression.js +4 -0
- package/src/internal/client/dom/blocks/await.js +71 -137
- package/src/internal/client/dom/blocks/boundary.js +7 -19
- package/src/internal/client/dom/blocks/branches.js +185 -0
- package/src/internal/client/dom/blocks/if.js +28 -107
- package/src/internal/client/dom/blocks/key.js +12 -58
- package/src/internal/client/dom/blocks/snippet.js +6 -22
- package/src/internal/client/dom/blocks/svelte-component.js +7 -63
- package/src/internal/client/dom/blocks/svelte-element.js +34 -45
- package/src/internal/client/dom/elements/bindings/select.js +21 -0
- package/src/internal/client/index.js +1 -1
- package/src/internal/client/reactivity/async.js +24 -8
- package/src/internal/client/reactivity/batch.js +66 -24
- package/src/internal/client/reactivity/effects.js +20 -2
- package/src/utils.js +1 -0
- package/src/version.js +1 -1
- package/types/index.d.ts +12 -0
- package/types/index.d.ts.map +1 -1
package/package.json
CHANGED
package/src/compiler/errors.js
CHANGED
|
@@ -986,13 +986,13 @@ export function const_tag_invalid_placement(node) {
|
|
|
986
986
|
}
|
|
987
987
|
|
|
988
988
|
/**
|
|
989
|
-
* The `{@const %name% = ...}` declaration is not available in this snippet
|
|
989
|
+
* The `{@const %name% = ...}` declaration is not available in this snippet
|
|
990
990
|
* @param {null | number | NodeLike} node
|
|
991
991
|
* @param {string} name
|
|
992
992
|
* @returns {never}
|
|
993
993
|
*/
|
|
994
994
|
export function const_tag_invalid_reference(node, name) {
|
|
995
|
-
e(node, 'const_tag_invalid_reference', `The \`{@const ${name} = ...}\` declaration is not available in this snippet
|
|
995
|
+
e(node, 'const_tag_invalid_reference', `The \`{@const ${name} = ...}\` declaration is not available in this snippet\nhttps://svelte.dev/e/const_tag_invalid_reference`);
|
|
996
996
|
}
|
|
997
997
|
|
|
998
998
|
/**
|
|
@@ -1023,6 +1023,15 @@ export function directive_missing_name(node, type) {
|
|
|
1023
1023
|
e(node, 'directive_missing_name', `\`${type}\` name cannot be empty\nhttps://svelte.dev/e/directive_missing_name`);
|
|
1024
1024
|
}
|
|
1025
1025
|
|
|
1026
|
+
/**
|
|
1027
|
+
* An `{#each ...}` block without an `as` clause cannot have a key
|
|
1028
|
+
* @param {null | number | NodeLike} node
|
|
1029
|
+
* @returns {never}
|
|
1030
|
+
*/
|
|
1031
|
+
export function each_key_without_as(node) {
|
|
1032
|
+
e(node, 'each_key_without_as', `An \`{#each ...}\` block without an \`as\` clause cannot have a key\nhttps://svelte.dev/e/each_key_without_as`);
|
|
1033
|
+
}
|
|
1034
|
+
|
|
1026
1035
|
/**
|
|
1027
1036
|
* `</%name%>` attempted to close an element that was not open
|
|
1028
1037
|
* @param {null | number | NodeLike} node
|
|
@@ -226,6 +226,13 @@ export function CallExpression(node, context) {
|
|
|
226
226
|
break;
|
|
227
227
|
}
|
|
228
228
|
|
|
229
|
+
case '$state.eager':
|
|
230
|
+
if (node.arguments.length !== 1) {
|
|
231
|
+
e.rune_invalid_arguments_length(node, rune, 'exactly one argument');
|
|
232
|
+
}
|
|
233
|
+
|
|
234
|
+
break;
|
|
235
|
+
|
|
229
236
|
case '$state.snapshot':
|
|
230
237
|
if (node.arguments.length !== 1) {
|
|
231
238
|
e.rune_invalid_arguments_length(node, rune, 'exactly one argument');
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
/** @import { Expression } from 'estree' */
|
|
1
2
|
/** @import { AST, Binding } from '#compiler' */
|
|
2
3
|
/** @import { Context } from '../types' */
|
|
3
4
|
/** @import { Scope } from '../../scope' */
|
|
@@ -28,6 +29,10 @@ export function EachBlock(node, context) {
|
|
|
28
29
|
node.key.type !== 'Identifier' || !node.index || node.key.name !== node.index;
|
|
29
30
|
}
|
|
30
31
|
|
|
32
|
+
if (node.metadata.keyed && !node.context) {
|
|
33
|
+
e.each_key_without_as(/** @type {Expression} */ (node.key));
|
|
34
|
+
}
|
|
35
|
+
|
|
31
36
|
// evaluate expression in parent scope
|
|
32
37
|
context.visit(node.expression, {
|
|
33
38
|
...context.state,
|
|
@@ -172,6 +172,7 @@ export function client_component(analysis, options) {
|
|
|
172
172
|
// these are set inside the `Fragment` visitor, and cannot be used until then
|
|
173
173
|
init: /** @type {any} */ (null),
|
|
174
174
|
consts: /** @type {any} */ (null),
|
|
175
|
+
let_directives: /** @type {any} */ (null),
|
|
175
176
|
update: /** @type {any} */ (null),
|
|
176
177
|
after_update: /** @type {any} */ (null),
|
|
177
178
|
template: /** @type {any} */ (null),
|
|
@@ -384,7 +385,9 @@ export function client_component(analysis, options) {
|
|
|
384
385
|
.../** @type {ESTree.Statement[]} */ (template.body)
|
|
385
386
|
]);
|
|
386
387
|
|
|
387
|
-
component_block.body.push(
|
|
388
|
+
component_block.body.push(
|
|
389
|
+
b.stmt(b.call(`$.async_body`, b.id('$$anchor'), b.arrow([b.id('$$anchor')], body, true)))
|
|
390
|
+
);
|
|
388
391
|
} else {
|
|
389
392
|
component_block.body.push(
|
|
390
393
|
...state.instance_level_snippets,
|
|
@@ -49,6 +49,12 @@ export function CallExpression(node, context) {
|
|
|
49
49
|
return b.call('$.derived', rune === '$derived' ? b.thunk(fn) : fn);
|
|
50
50
|
}
|
|
51
51
|
|
|
52
|
+
case '$state.eager':
|
|
53
|
+
return b.call(
|
|
54
|
+
'$.eager',
|
|
55
|
+
b.thunk(/** @type {Expression} */ (context.visit(node.arguments[0])))
|
|
56
|
+
);
|
|
57
|
+
|
|
52
58
|
case '$state.snapshot':
|
|
53
59
|
return b.call(
|
|
54
60
|
'$.snapshot',
|
|
@@ -63,6 +63,7 @@ export function Fragment(node, context) {
|
|
|
63
63
|
...context.state,
|
|
64
64
|
init: [],
|
|
65
65
|
consts: [],
|
|
66
|
+
let_directives: [],
|
|
66
67
|
update: [],
|
|
67
68
|
after_update: [],
|
|
68
69
|
memoizer: new Memoizer(),
|
|
@@ -150,7 +151,7 @@ export function Fragment(node, context) {
|
|
|
150
151
|
}
|
|
151
152
|
}
|
|
152
153
|
|
|
153
|
-
body.push(...state.consts);
|
|
154
|
+
body.push(...state.let_directives, ...state.consts);
|
|
154
155
|
|
|
155
156
|
if (has_await) {
|
|
156
157
|
body.push(b.if(b.call('$.aborted'), b.return()));
|
|
@@ -177,7 +178,11 @@ export function Fragment(node, context) {
|
|
|
177
178
|
}
|
|
178
179
|
|
|
179
180
|
if (has_await) {
|
|
180
|
-
return b.block([
|
|
181
|
+
return b.block([
|
|
182
|
+
b.stmt(
|
|
183
|
+
b.call('$.async_body', b.id('$$anchor'), b.arrow([b.id('$$anchor')], b.block(body), true))
|
|
184
|
+
)
|
|
185
|
+
]);
|
|
181
186
|
} else {
|
|
182
187
|
return b.block(body);
|
|
183
188
|
}
|
|
@@ -21,22 +21,24 @@ export function LetDirective(node, context) {
|
|
|
21
21
|
};
|
|
22
22
|
}
|
|
23
23
|
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
b.
|
|
30
|
-
b.
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
24
|
+
context.state.let_directives.push(
|
|
25
|
+
b.const(
|
|
26
|
+
name,
|
|
27
|
+
b.call(
|
|
28
|
+
'$.derived',
|
|
29
|
+
b.thunk(
|
|
30
|
+
b.block([
|
|
31
|
+
b.let(
|
|
32
|
+
/** @type {Expression} */ (node.expression).type === 'ObjectExpression'
|
|
33
|
+
? // @ts-expect-error types don't match, but it can't contain spread elements and the structure is otherwise fine
|
|
34
|
+
b.object_pattern(node.expression.properties)
|
|
35
|
+
: // @ts-expect-error types don't match, but it can't contain spread elements and the structure is otherwise fine
|
|
36
|
+
b.array_pattern(node.expression.elements),
|
|
37
|
+
b.member(b.id('$$slotProps'), node.name)
|
|
38
|
+
),
|
|
39
|
+
b.return(b.object(bindings.map((binding) => b.init(binding.node.name, binding.node))))
|
|
40
|
+
])
|
|
41
|
+
)
|
|
40
42
|
)
|
|
41
43
|
)
|
|
42
44
|
);
|
|
@@ -46,6 +48,8 @@ export function LetDirective(node, context) {
|
|
|
46
48
|
read: (node) => b.call('$.get', node)
|
|
47
49
|
};
|
|
48
50
|
|
|
49
|
-
|
|
51
|
+
context.state.let_directives.push(
|
|
52
|
+
b.const(name, create_derived(context.state, b.member(b.id('$$slotProps'), node.name)))
|
|
53
|
+
);
|
|
50
54
|
}
|
|
51
55
|
}
|
|
@@ -106,7 +106,7 @@ export function RegularElement(node, context) {
|
|
|
106
106
|
|
|
107
107
|
case 'LetDirective':
|
|
108
108
|
// visit let directives before everything else, to set state
|
|
109
|
-
|
|
109
|
+
context.visit(attribute, { ...context.state, let_directives: lets });
|
|
110
110
|
break;
|
|
111
111
|
|
|
112
112
|
case 'OnDirective':
|
|
@@ -49,7 +49,7 @@ export function SlotElement(node, context) {
|
|
|
49
49
|
}
|
|
50
50
|
}
|
|
51
51
|
} else if (attribute.type === 'LetDirective') {
|
|
52
|
-
|
|
52
|
+
context.visit(attribute, { ...context.state, let_directives: lets });
|
|
53
53
|
}
|
|
54
54
|
}
|
|
55
55
|
|
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
export function SvelteFragment(node, context) {
|
|
10
10
|
for (const attribute of node.attributes) {
|
|
11
11
|
if (attribute.type === 'LetDirective') {
|
|
12
|
-
context.
|
|
12
|
+
context.visit(attribute);
|
|
13
13
|
}
|
|
14
14
|
}
|
|
15
15
|
|
|
@@ -101,7 +101,7 @@ export function build_component(node, component_name, context) {
|
|
|
101
101
|
if (slot_scope_applies_to_itself) {
|
|
102
102
|
for (const attribute of node.attributes) {
|
|
103
103
|
if (attribute.type === 'LetDirective') {
|
|
104
|
-
|
|
104
|
+
context.visit(attribute, { ...context.state, let_directives: lets });
|
|
105
105
|
}
|
|
106
106
|
}
|
|
107
107
|
}
|
|
@@ -109,7 +109,7 @@ export function build_component(node, component_name, context) {
|
|
|
109
109
|
for (const attribute of node.attributes) {
|
|
110
110
|
if (attribute.type === 'LetDirective') {
|
|
111
111
|
if (!slot_scope_applies_to_itself) {
|
|
112
|
-
|
|
112
|
+
context.visit(attribute, { ...states.default, let_directives: lets });
|
|
113
113
|
}
|
|
114
114
|
} else if (attribute.type === 'OnDirective') {
|
|
115
115
|
if (!attribute.expression) {
|
|
@@ -38,6 +38,10 @@ export function CallExpression(node, context) {
|
|
|
38
38
|
return b.call('$.derived', rune === '$derived' ? b.thunk(fn) : fn);
|
|
39
39
|
}
|
|
40
40
|
|
|
41
|
+
if (rune === '$state.eager') {
|
|
42
|
+
return node.arguments[0];
|
|
43
|
+
}
|
|
44
|
+
|
|
41
45
|
if (rune === '$state.snapshot') {
|
|
42
46
|
return b.call(
|
|
43
47
|
'$.snapshot',
|
|
@@ -1,12 +1,9 @@
|
|
|
1
|
-
/** @import {
|
|
2
|
-
import { DEV } from 'esm-env';
|
|
1
|
+
/** @import { Source, TemplateNode } from '#client' */
|
|
3
2
|
import { is_promise } from '../../../shared/utils.js';
|
|
4
|
-
import { block
|
|
3
|
+
import { block } from '../../reactivity/effects.js';
|
|
5
4
|
import { internal_set, mutable_source, source } from '../../reactivity/sources.js';
|
|
6
|
-
import { set_active_effect, set_active_reaction } from '../../runtime.js';
|
|
7
5
|
import {
|
|
8
6
|
hydrate_next,
|
|
9
|
-
hydrate_node,
|
|
10
7
|
hydrating,
|
|
11
8
|
skip_nodes,
|
|
12
9
|
set_hydrate_node,
|
|
@@ -14,15 +11,10 @@ import {
|
|
|
14
11
|
} from '../hydration.js';
|
|
15
12
|
import { queue_micro_task } from '../task.js';
|
|
16
13
|
import { HYDRATION_START_ELSE, UNINITIALIZED } from '../../../../constants.js';
|
|
17
|
-
import {
|
|
18
|
-
component_context,
|
|
19
|
-
dev_stack,
|
|
20
|
-
is_runes,
|
|
21
|
-
set_component_context,
|
|
22
|
-
set_dev_current_component_function,
|
|
23
|
-
set_dev_stack
|
|
24
|
-
} from '../../context.js';
|
|
14
|
+
import { is_runes } from '../../context.js';
|
|
25
15
|
import { flushSync, is_flushing_sync } from '../../reactivity/batch.js';
|
|
16
|
+
import { BranchManager } from './branches.js';
|
|
17
|
+
import { capture, unset_context } from '../../reactivity/async.js';
|
|
26
18
|
|
|
27
19
|
const PENDING = 0;
|
|
28
20
|
const THEN = 1;
|
|
@@ -33,7 +25,7 @@ const CATCH = 2;
|
|
|
33
25
|
/**
|
|
34
26
|
* @template V
|
|
35
27
|
* @param {TemplateNode} node
|
|
36
|
-
* @param {(() =>
|
|
28
|
+
* @param {(() => any)} get_input
|
|
37
29
|
* @param {null | ((anchor: Node) => void)} pending_fn
|
|
38
30
|
* @param {null | ((anchor: Node, value: Source<V>) => void)} then_fn
|
|
39
31
|
* @param {null | ((anchor: Node, error: unknown) => void)} catch_fn
|
|
@@ -44,149 +36,94 @@ export function await_block(node, get_input, pending_fn, then_fn, catch_fn) {
|
|
|
44
36
|
hydrate_next();
|
|
45
37
|
}
|
|
46
38
|
|
|
47
|
-
var anchor = node;
|
|
48
39
|
var runes = is_runes();
|
|
49
|
-
var active_component_context = component_context;
|
|
50
|
-
|
|
51
|
-
/** @type {any} */
|
|
52
|
-
var component_function = DEV ? component_context?.function : null;
|
|
53
|
-
var dev_original_stack = DEV ? dev_stack : null;
|
|
54
|
-
|
|
55
|
-
/** @type {V | Promise<V> | typeof UNINITIALIZED} */
|
|
56
|
-
var input = UNINITIALIZED;
|
|
57
|
-
|
|
58
|
-
/** @type {Effect | null} */
|
|
59
|
-
var pending_effect;
|
|
60
|
-
|
|
61
|
-
/** @type {Effect | null} */
|
|
62
|
-
var then_effect;
|
|
63
|
-
|
|
64
|
-
/** @type {Effect | null} */
|
|
65
|
-
var catch_effect;
|
|
66
|
-
|
|
67
|
-
var input_source = runes
|
|
68
|
-
? source(/** @type {V} */ (undefined))
|
|
69
|
-
: mutable_source(/** @type {V} */ (undefined), false, false);
|
|
70
|
-
var error_source = runes ? source(undefined) : mutable_source(undefined, false, false);
|
|
71
|
-
var resolved = false;
|
|
72
|
-
/**
|
|
73
|
-
* @param {AwaitState} state
|
|
74
|
-
* @param {boolean} restore
|
|
75
|
-
*/
|
|
76
|
-
function update(state, restore) {
|
|
77
|
-
resolved = true;
|
|
78
|
-
|
|
79
|
-
if (restore) {
|
|
80
|
-
set_active_effect(effect);
|
|
81
|
-
set_active_reaction(effect); // TODO do we need both?
|
|
82
|
-
set_component_context(active_component_context);
|
|
83
|
-
if (DEV) {
|
|
84
|
-
set_dev_current_component_function(component_function);
|
|
85
|
-
set_dev_stack(dev_original_stack);
|
|
86
|
-
}
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
try {
|
|
90
|
-
if (state === PENDING && pending_fn) {
|
|
91
|
-
if (pending_effect) resume_effect(pending_effect);
|
|
92
|
-
else pending_effect = branch(() => pending_fn(anchor));
|
|
93
|
-
}
|
|
94
|
-
|
|
95
|
-
if (state === THEN && then_fn) {
|
|
96
|
-
if (then_effect) resume_effect(then_effect);
|
|
97
|
-
else then_effect = branch(() => then_fn(anchor, input_source));
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
if (state === CATCH && catch_fn) {
|
|
101
|
-
if (catch_effect) resume_effect(catch_effect);
|
|
102
|
-
else catch_effect = branch(() => catch_fn(anchor, error_source));
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
if (state !== PENDING && pending_effect) {
|
|
106
|
-
pause_effect(pending_effect, () => (pending_effect = null));
|
|
107
|
-
}
|
|
108
|
-
|
|
109
|
-
if (state !== THEN && then_effect) {
|
|
110
|
-
pause_effect(then_effect, () => (then_effect = null));
|
|
111
|
-
}
|
|
112
|
-
|
|
113
|
-
if (state !== CATCH && catch_effect) {
|
|
114
|
-
pause_effect(catch_effect, () => (catch_effect = null));
|
|
115
|
-
}
|
|
116
|
-
} finally {
|
|
117
|
-
if (restore) {
|
|
118
|
-
if (DEV) {
|
|
119
|
-
set_dev_current_component_function(null);
|
|
120
|
-
set_dev_stack(null);
|
|
121
|
-
}
|
|
122
40
|
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
41
|
+
var v = /** @type {V} */ (UNINITIALIZED);
|
|
42
|
+
var value = runes ? source(v) : mutable_source(v, false, false);
|
|
43
|
+
var error = runes ? source(v) : mutable_source(v, false, false);
|
|
126
44
|
|
|
127
|
-
|
|
128
|
-
// resolves, which is unexpected behaviour (and somewhat irksome to test)
|
|
129
|
-
if (!is_flushing_sync) flushSync();
|
|
130
|
-
}
|
|
131
|
-
}
|
|
132
|
-
}
|
|
45
|
+
var branches = new BranchManager(node);
|
|
133
46
|
|
|
134
|
-
|
|
135
|
-
|
|
47
|
+
block(() => {
|
|
48
|
+
var input = get_input();
|
|
49
|
+
var destroyed = false;
|
|
136
50
|
|
|
137
51
|
/** Whether or not there was a hydration mismatch. Needs to be a `let` or else it isn't treeshaken out */
|
|
138
|
-
// @ts-ignore coercing `
|
|
139
|
-
let mismatch = hydrating && is_promise(input) === (
|
|
52
|
+
// @ts-ignore coercing `node` to a `Comment` causes TypeScript and Prettier to fight
|
|
53
|
+
let mismatch = hydrating && is_promise(input) === (node.data === HYDRATION_START_ELSE);
|
|
140
54
|
|
|
141
55
|
if (mismatch) {
|
|
142
56
|
// Hydration mismatch: remove everything inside the anchor and start fresh
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
set_hydrate_node(anchor);
|
|
57
|
+
set_hydrate_node(skip_nodes());
|
|
146
58
|
set_hydrating(false);
|
|
147
|
-
mismatch = true;
|
|
148
59
|
}
|
|
149
60
|
|
|
150
61
|
if (is_promise(input)) {
|
|
151
|
-
var
|
|
62
|
+
var restore = capture();
|
|
63
|
+
var resolved = false;
|
|
64
|
+
|
|
65
|
+
/**
|
|
66
|
+
* @param {() => void} fn
|
|
67
|
+
*/
|
|
68
|
+
const resolve = (fn) => {
|
|
69
|
+
if (destroyed) return;
|
|
70
|
+
|
|
71
|
+
resolved = true;
|
|
72
|
+
restore();
|
|
73
|
+
|
|
74
|
+
if (hydrating) {
|
|
75
|
+
// `restore()` could set `hydrating` to `true`, which we very much
|
|
76
|
+
// don't want — we want to restore everything _except_ this
|
|
77
|
+
set_hydrating(false);
|
|
78
|
+
}
|
|
152
79
|
|
|
153
|
-
|
|
80
|
+
try {
|
|
81
|
+
fn();
|
|
82
|
+
} finally {
|
|
83
|
+
unset_context();
|
|
154
84
|
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
if (
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
85
|
+
// without this, the DOM does not update until two ticks after the promise
|
|
86
|
+
// resolves, which is unexpected behaviour (and somewhat irksome to test)
|
|
87
|
+
if (!is_flushing_sync) flushSync();
|
|
88
|
+
}
|
|
89
|
+
};
|
|
90
|
+
|
|
91
|
+
input.then(
|
|
92
|
+
(v) => {
|
|
93
|
+
resolve(() => {
|
|
94
|
+
internal_set(value, v);
|
|
95
|
+
branches.ensure(THEN, then_fn && ((target) => then_fn(target, value)));
|
|
96
|
+
});
|
|
162
97
|
},
|
|
163
|
-
(
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
}
|
|
98
|
+
(e) => {
|
|
99
|
+
resolve(() => {
|
|
100
|
+
internal_set(error, e);
|
|
101
|
+
branches.ensure(THEN, catch_fn && ((target) => catch_fn(target, error)));
|
|
102
|
+
|
|
103
|
+
if (!catch_fn) {
|
|
104
|
+
// Rethrow the error if no catch block exists
|
|
105
|
+
throw error.v;
|
|
106
|
+
}
|
|
107
|
+
});
|
|
173
108
|
}
|
|
174
109
|
);
|
|
175
110
|
|
|
176
111
|
if (hydrating) {
|
|
177
|
-
|
|
178
|
-
pending_effect = branch(() => pending_fn(anchor));
|
|
179
|
-
}
|
|
112
|
+
branches.ensure(PENDING, pending_fn);
|
|
180
113
|
} else {
|
|
181
114
|
// Wait a microtask before checking if we should show the pending state as
|
|
182
|
-
// the promise might have resolved by
|
|
115
|
+
// the promise might have resolved by then
|
|
183
116
|
queue_micro_task(() => {
|
|
184
|
-
if (!resolved)
|
|
117
|
+
if (!resolved) {
|
|
118
|
+
resolve(() => {
|
|
119
|
+
branches.ensure(PENDING, pending_fn);
|
|
120
|
+
});
|
|
121
|
+
}
|
|
185
122
|
});
|
|
186
123
|
}
|
|
187
124
|
} else {
|
|
188
|
-
internal_set(
|
|
189
|
-
|
|
125
|
+
internal_set(value, input);
|
|
126
|
+
branches.ensure(THEN, then_fn && ((target) => then_fn(target, value)));
|
|
190
127
|
}
|
|
191
128
|
|
|
192
129
|
if (mismatch) {
|
|
@@ -194,11 +131,8 @@ export function await_block(node, get_input, pending_fn, then_fn, catch_fn) {
|
|
|
194
131
|
set_hydrating(true);
|
|
195
132
|
}
|
|
196
133
|
|
|
197
|
-
|
|
198
|
-
|
|
134
|
+
return () => {
|
|
135
|
+
destroyed = true;
|
|
136
|
+
};
|
|
199
137
|
});
|
|
200
|
-
|
|
201
|
-
if (hydrating) {
|
|
202
|
-
anchor = hydrate_node;
|
|
203
|
-
}
|
|
204
138
|
}
|
|
@@ -8,7 +8,13 @@ import {
|
|
|
8
8
|
import { HYDRATION_START_ELSE } from '../../../../constants.js';
|
|
9
9
|
import { component_context, set_component_context } from '../../context.js';
|
|
10
10
|
import { handle_error, invoke_error_boundary } from '../../error-handling.js';
|
|
11
|
-
import {
|
|
11
|
+
import {
|
|
12
|
+
block,
|
|
13
|
+
branch,
|
|
14
|
+
destroy_effect,
|
|
15
|
+
move_effect,
|
|
16
|
+
pause_effect
|
|
17
|
+
} from '../../reactivity/effects.js';
|
|
12
18
|
import {
|
|
13
19
|
active_effect,
|
|
14
20
|
active_reaction,
|
|
@@ -425,24 +431,6 @@ export class Boundary {
|
|
|
425
431
|
}
|
|
426
432
|
}
|
|
427
433
|
|
|
428
|
-
/**
|
|
429
|
-
*
|
|
430
|
-
* @param {Effect} effect
|
|
431
|
-
* @param {DocumentFragment} fragment
|
|
432
|
-
*/
|
|
433
|
-
function move_effect(effect, fragment) {
|
|
434
|
-
var node = effect.nodes_start;
|
|
435
|
-
var end = effect.nodes_end;
|
|
436
|
-
|
|
437
|
-
while (node !== null) {
|
|
438
|
-
/** @type {TemplateNode | null} */
|
|
439
|
-
var next = node === end ? null : /** @type {TemplateNode} */ (get_next_sibling(node));
|
|
440
|
-
|
|
441
|
-
fragment.append(node);
|
|
442
|
-
node = next;
|
|
443
|
-
}
|
|
444
|
-
}
|
|
445
|
-
|
|
446
434
|
export function get_boundary() {
|
|
447
435
|
return /** @type {Boundary} */ (/** @type {Effect} */ (active_effect).b);
|
|
448
436
|
}
|