Skip to content

Commit 82cb515

Browse files
committed
parallelize await expressions in instance
1 parent b138c60 commit 82cb515

File tree

4 files changed

+64
-15
lines changed

4 files changed

+64
-15
lines changed

packages/svelte/src/compiler/phases/3-transform/client/types.d.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -90,10 +90,10 @@ export interface ComponentClientTransformState extends ClientTransformState {
9090

9191
export interface ParallelizedChunk {
9292
declarators: Array<{
93-
id: Pattern;
93+
id: Pattern | null;
9494
init: Expression;
9595
}>;
96-
kind: VariableDeclaration['kind'];
96+
kind: VariableDeclaration['kind'] | null;
9797
/** index in instance body */
9898
position: number;
9999
bindings: Binding[];

packages/svelte/src/compiler/phases/3-transform/client/visitors/ExpressionStatement.js

Lines changed: 38 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,16 @@
1-
/** @import { Expression, ExpressionStatement } from 'estree' */
2-
/** @import { ComponentContext } from '../types' */
1+
/** @import { Expression, ExpressionStatement, Node, Program } from 'estree' */
2+
/** @import { ComponentContext, ParallelizedChunk } from '../types' */
33
import * as b from '#compiler/builders';
44
import { get_rune } from '../../../scope.js';
5+
import { can_be_parallelized } from '../utils.js';
56

67
/**
78
* @param {ExpressionStatement} node
89
* @param {ComponentContext} context
910
*/
1011
export function ExpressionStatement(node, context) {
12+
const parent = /** @type {Node} */ (context.path.at(-1));
13+
const position = /** @type {Program} */ (parent).body?.indexOf?.(node);
1114
if (node.expression.type === 'CallExpression') {
1215
const rune = get_rune(node.expression, context.state.scope);
1316

@@ -25,6 +28,39 @@ export function ExpressionStatement(node, context) {
2528
return b.empty;
2629
}
2730
}
31+
if (
32+
node.expression.type === 'AwaitExpression' &&
33+
context.state.analysis.instance?.scope === context.state.scope
34+
) {
35+
const current_chunk = context.state.current_parallelized_chunk;
36+
const parallelize = can_be_parallelized(
37+
node.expression.argument,
38+
context.state.scope,
39+
context.state.analysis,
40+
current_chunk?.bindings ?? []
41+
);
42+
if (parallelize) {
43+
const declarator = {
44+
id: null,
45+
init: /** @type {Expression} */ (context.visit(node.expression))
46+
};
47+
if (current_chunk) {
48+
current_chunk.declarators.push(declarator);
49+
current_chunk.position = position;
50+
} else {
51+
/** @type {ParallelizedChunk} */
52+
const chunk = {
53+
kind: null,
54+
declarators: [declarator],
55+
position,
56+
bindings: []
57+
};
58+
context.state.current_parallelized_chunk = chunk;
59+
context.state.parallelized_chunks.push(chunk);
60+
}
61+
return;
62+
}
63+
}
2864

2965
context.next();
3066
}

packages/svelte/src/compiler/phases/3-transform/client/visitors/Program.js

Lines changed: 17 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -148,20 +148,28 @@ export function Program(node, context) {
148148
for (const chunk of context.state.parallelized_chunks) {
149149
if (chunk.declarators.length === 1) {
150150
const declarator = chunk.declarators[0];
151-
body.splice(
152-
chunk.position + offset,
153-
0,
154-
b.declaration(chunk.kind, [
155-
b.declarator(declarator.id, b.call(b.await(b.call('$.save', declarator.init))))
156-
])
157-
);
151+
if (declarator.id === null || chunk.kind === null) {
152+
body.splice(
153+
chunk.position + offset,
154+
0,
155+
b.stmt(b.call(b.await(b.call('$.save', declarator.init))))
156+
);
157+
} else {
158+
body.splice(
159+
chunk.position + offset,
160+
0,
161+
b.declaration(chunk.kind, [
162+
b.declarator(declarator.id, b.call(b.await(b.call('$.save', declarator.init))))
163+
])
164+
);
165+
}
158166
} else {
159167
const pattern = b.array_pattern(chunk.declarators.map(({ id }) => id));
160-
const init = b.call(`$.all`, ...chunk.declarators.map(({ init }) => init));
168+
const init = b.call('$.all', ...chunk.declarators.map(({ init }) => init));
161169
body.splice(
162170
chunk.position + offset,
163171
0,
164-
b.declaration(chunk.kind, [b.declarator(pattern, b.await(init))])
172+
b.declaration(chunk.kind ?? 'const', [b.declarator(pattern, b.await(init))])
165173
);
166174
}
167175
offset++;

packages/svelte/src/compiler/phases/3-transform/client/visitors/VariableDeclaration.js

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -69,10 +69,14 @@ export function VariableDeclaration(node, context) {
6969
id,
7070
init: /** @type {Expression} */ (visited_init)
7171
};
72-
if (current_chunk && current_chunk.kind === node.kind) {
72+
if (
73+
current_chunk &&
74+
(current_chunk.kind === node.kind || current_chunk.kind === null)
75+
) {
7376
current_chunk.declarators.push(_declarator);
7477
current_chunk.bindings.push(...bindings);
7578
current_chunk.position = /** @type {Program} */ (parent).body.indexOf(node);
79+
current_chunk.kind = node.kind;
7680
} else {
7781
/** @type {ParallelizedChunk} */
7882
const chunk = {
@@ -370,10 +374,11 @@ export function VariableDeclaration(node, context) {
370374
id,
371375
init: /** @type {Expression} */ (init)
372376
}));
373-
if (current_chunk && current_chunk.kind === node.kind) {
377+
if (current_chunk && (current_chunk.kind === node.kind || current_chunk.kind === null)) {
374378
current_chunk.declarators.push(...declarators);
375379
current_chunk.bindings.push(...bindings);
376380
current_chunk.position = position;
381+
current_chunk.kind = node.kind;
377382
} else {
378383
/** @type {ParallelizedChunk} */
379384
const chunk = {

0 commit comments

Comments
 (0)