ripple 0.2.68 → 0.2.69
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/package.json +1 -1
- package/src/compiler/phases/1-parse/index.js +131 -0
- package/src/compiler/phases/2-analyze/index.js +17 -11
- package/src/compiler/phases/3-transform/index.js +78 -31
- package/src/compiler/scope.js +403 -397
- package/src/compiler/utils.js +16 -0
- package/src/constants.js +4 -0
- package/src/runtime/array.js +33 -24
- package/src/runtime/internal/client/for.js +69 -31
- package/src/runtime/internal/client/render.js +9 -3
- package/src/runtime/internal/client/template.js +51 -5
- package/tests/__snapshots__/basic.test.ripple.snap +18 -0
- package/tests/__snapshots__/for.test.ripple.snap +78 -0
- package/tests/basic.test.ripple +15 -0
- package/tests/for.test.ripple +32 -2
- package/tests/svg.test.ripple +282 -0
package/package.json
CHANGED
|
@@ -192,6 +192,135 @@ function RipplePlugin(config) {
|
|
|
192
192
|
return super.parseExportDefaultDeclaration();
|
|
193
193
|
}
|
|
194
194
|
|
|
195
|
+
parseForStatement(node) {
|
|
196
|
+
this.next()
|
|
197
|
+
let awaitAt = (this.options.ecmaVersion >= 9 && this.canAwait && this.eatContextual("await")) ? this.lastTokStart : -1
|
|
198
|
+
this.labels.push({kind: "loop"})
|
|
199
|
+
this.enterScope(0)
|
|
200
|
+
this.expect(tt.parenL)
|
|
201
|
+
|
|
202
|
+
if (this.type === tt.semi) {
|
|
203
|
+
if (awaitAt > -1) this.unexpected(awaitAt)
|
|
204
|
+
return this.parseFor(node, null)
|
|
205
|
+
}
|
|
206
|
+
|
|
207
|
+
let isLet = this.isLet()
|
|
208
|
+
if (this.type === tt._var || this.type === tt._const || isLet) {
|
|
209
|
+
let init = this.startNode(), kind = isLet ? "let" : this.value
|
|
210
|
+
this.next()
|
|
211
|
+
this.parseVar(init, true, kind)
|
|
212
|
+
this.finishNode(init, "VariableDeclaration")
|
|
213
|
+
return this.parseForAfterInitWithIndex(node, init, awaitAt)
|
|
214
|
+
}
|
|
215
|
+
|
|
216
|
+
// Handle other cases like using declarations if they exist
|
|
217
|
+
let startsWithLet = this.isContextual("let"), isForOf = false
|
|
218
|
+
let usingKind = (this.isUsing && this.isUsing(true)) ? "using" : (this.isAwaitUsing && this.isAwaitUsing(true)) ? "await using" : null
|
|
219
|
+
if (usingKind) {
|
|
220
|
+
let init = this.startNode()
|
|
221
|
+
this.next()
|
|
222
|
+
if (usingKind === "await using") {
|
|
223
|
+
if (!this.canAwait) {
|
|
224
|
+
this.raise(this.start, "Await using cannot appear outside of async function")
|
|
225
|
+
}
|
|
226
|
+
this.next()
|
|
227
|
+
}
|
|
228
|
+
this.parseVar(init, true, usingKind)
|
|
229
|
+
this.finishNode(init, "VariableDeclaration")
|
|
230
|
+
return this.parseForAfterInitWithIndex(node, init, awaitAt)
|
|
231
|
+
}
|
|
232
|
+
|
|
233
|
+
let containsEsc = this.containsEsc
|
|
234
|
+
let refDestructuringErrors = {}
|
|
235
|
+
let initPos = this.start
|
|
236
|
+
let init = awaitAt > -1
|
|
237
|
+
? this.parseExprSubscripts(refDestructuringErrors, "await")
|
|
238
|
+
: this.parseExpression(true, refDestructuringErrors)
|
|
239
|
+
|
|
240
|
+
if (this.type === tt._in || (isForOf = this.options.ecmaVersion >= 6 && this.isContextual("of"))) {
|
|
241
|
+
if (awaitAt > -1) { // implies `ecmaVersion >= 9`
|
|
242
|
+
if (this.type === tt._in) this.unexpected(awaitAt)
|
|
243
|
+
node.await = true
|
|
244
|
+
} else if (isForOf && this.options.ecmaVersion >= 8) {
|
|
245
|
+
if (init.start === initPos && !containsEsc && init.type === "Identifier" && init.name === "async") this.unexpected()
|
|
246
|
+
else if (this.options.ecmaVersion >= 9) node.await = false
|
|
247
|
+
}
|
|
248
|
+
if (startsWithLet && isForOf) this.raise(init.start, "The left-hand side of a for-of loop may not start with 'let'.")
|
|
249
|
+
this.toAssignable(init, false, refDestructuringErrors)
|
|
250
|
+
this.checkLValPattern(init)
|
|
251
|
+
return this.parseForInWithIndex(node, init)
|
|
252
|
+
} else {
|
|
253
|
+
this.checkExpressionErrors(refDestructuringErrors, true)
|
|
254
|
+
}
|
|
255
|
+
|
|
256
|
+
if (awaitAt > -1) this.unexpected(awaitAt)
|
|
257
|
+
return this.parseFor(node, init)
|
|
258
|
+
}
|
|
259
|
+
|
|
260
|
+
parseForAfterInitWithIndex(node, init, awaitAt) {
|
|
261
|
+
if ((this.type === tt._in || (this.options.ecmaVersion >= 6 && this.isContextual("of"))) && init.declarations.length === 1) {
|
|
262
|
+
if (this.options.ecmaVersion >= 9) {
|
|
263
|
+
if (this.type === tt._in) {
|
|
264
|
+
if (awaitAt > -1) this.unexpected(awaitAt)
|
|
265
|
+
} else node.await = awaitAt > -1
|
|
266
|
+
}
|
|
267
|
+
return this.parseForInWithIndex(node, init)
|
|
268
|
+
}
|
|
269
|
+
if (awaitAt > -1) this.unexpected(awaitAt)
|
|
270
|
+
return this.parseFor(node, init)
|
|
271
|
+
}
|
|
272
|
+
|
|
273
|
+
parseForInWithIndex(node, init) {
|
|
274
|
+
const isForIn = this.type === tt._in
|
|
275
|
+
this.next()
|
|
276
|
+
|
|
277
|
+
if (
|
|
278
|
+
init.type === "VariableDeclaration" &&
|
|
279
|
+
init.declarations[0].init != null &&
|
|
280
|
+
(
|
|
281
|
+
!isForIn ||
|
|
282
|
+
this.options.ecmaVersion < 8 ||
|
|
283
|
+
this.strict ||
|
|
284
|
+
init.kind !== "var" ||
|
|
285
|
+
init.declarations[0].id.type !== "Identifier"
|
|
286
|
+
)
|
|
287
|
+
) {
|
|
288
|
+
this.raise(
|
|
289
|
+
init.start,
|
|
290
|
+
`${isForIn ? "for-in" : "for-of"} loop variable declaration may not have an initializer`
|
|
291
|
+
)
|
|
292
|
+
}
|
|
293
|
+
|
|
294
|
+
node.left = init
|
|
295
|
+
node.right = isForIn ? this.parseExpression() : this.parseMaybeAssign()
|
|
296
|
+
|
|
297
|
+
// Check for our extended syntax: "; index varName"
|
|
298
|
+
if (!isForIn && this.type === tt.semi) {
|
|
299
|
+
this.next() // consume ';'
|
|
300
|
+
|
|
301
|
+
if (this.isContextual('index')) {
|
|
302
|
+
this.next() // consume 'index'
|
|
303
|
+
|
|
304
|
+
if (this.type === tt.name) {
|
|
305
|
+
node.index = this.parseIdent()
|
|
306
|
+
} else {
|
|
307
|
+
this.raise(this.start, 'Expected identifier after "index" keyword')
|
|
308
|
+
}
|
|
309
|
+
} else {
|
|
310
|
+
this.raise(this.start, 'Expected "index" keyword after semicolon in for-of loop')
|
|
311
|
+
}
|
|
312
|
+
} else if (!isForIn) {
|
|
313
|
+
// Set index to null for standard for-of loops
|
|
314
|
+
node.index = null
|
|
315
|
+
}
|
|
316
|
+
|
|
317
|
+
this.expect(tt.parenR)
|
|
318
|
+
node.body = this.parseStatement("for")
|
|
319
|
+
this.exitScope()
|
|
320
|
+
this.labels.pop()
|
|
321
|
+
return this.finishNode(node, isForIn ? "ForInStatement" : "ForOfStatement")
|
|
322
|
+
}
|
|
323
|
+
|
|
195
324
|
shouldParseExportStatement() {
|
|
196
325
|
if (super.shouldParseExportStatement()) {
|
|
197
326
|
return true;
|
|
@@ -791,6 +920,8 @@ function RipplePlugin(config) {
|
|
|
791
920
|
return node;
|
|
792
921
|
}
|
|
793
922
|
|
|
923
|
+
|
|
924
|
+
|
|
794
925
|
if (this.type.label === '@') {
|
|
795
926
|
// Try to parse as an expression statement first using tryParse
|
|
796
927
|
// This allows us to handle Ripple @ syntax like @count++ without
|
|
@@ -5,7 +5,7 @@ import {
|
|
|
5
5
|
get_delegated_event,
|
|
6
6
|
is_element_dom_element,
|
|
7
7
|
is_inside_component,
|
|
8
|
-
|
|
8
|
+
is_ripple_track_call,
|
|
9
9
|
is_void_element,
|
|
10
10
|
} from '../../utils.js';
|
|
11
11
|
import { extract_paths } from '../../../utils/ast.js';
|
|
@@ -139,16 +139,7 @@ const visitors = {
|
|
|
139
139
|
CallExpression(node, context) {
|
|
140
140
|
const callee = node.callee;
|
|
141
141
|
|
|
142
|
-
if (
|
|
143
|
-
context.state.function_depth === 0 &&
|
|
144
|
-
((callee.type === 'Identifier' && callee.name === 'track') ||
|
|
145
|
-
(callee.type === 'MemberExpression' &&
|
|
146
|
-
callee.object.type === 'Identifier' &&
|
|
147
|
-
callee.property.type === 'Identifier' &&
|
|
148
|
-
callee.property.name === 'track' &&
|
|
149
|
-
!callee.computed)) &&
|
|
150
|
-
is_ripple_import(callee, context)
|
|
151
|
-
) {
|
|
142
|
+
if (context.state.function_depth === 0 && is_ripple_track_call(callee, context)) {
|
|
152
143
|
error(
|
|
153
144
|
'`track` can only be used within a reactive context, such as a component, function or class that is used or created from a component',
|
|
154
145
|
context.state.analysis.module.filename,
|
|
@@ -278,6 +269,21 @@ const visitors = {
|
|
|
278
269
|
return context.next();
|
|
279
270
|
}
|
|
280
271
|
|
|
272
|
+
if (node.index) {
|
|
273
|
+
const state = context.state;
|
|
274
|
+
const scope = state.scopes.get(node);
|
|
275
|
+
const binding = scope.get(node.index.name);
|
|
276
|
+
binding.kind = 'index'
|
|
277
|
+
|
|
278
|
+
if (binding !== null) {
|
|
279
|
+
binding.transform = {
|
|
280
|
+
read: (node) => {
|
|
281
|
+
return b.call('_$_.get', node)
|
|
282
|
+
},
|
|
283
|
+
};
|
|
284
|
+
}
|
|
285
|
+
}
|
|
286
|
+
|
|
281
287
|
node.metadata = {
|
|
282
288
|
has_template: false,
|
|
283
289
|
};
|
|
@@ -3,7 +3,13 @@ import path from 'node:path';
|
|
|
3
3
|
import { print } from 'esrap';
|
|
4
4
|
import tsx from 'esrap/languages/tsx';
|
|
5
5
|
import * as b from '../../../utils/builders.js';
|
|
6
|
-
import {
|
|
6
|
+
import {
|
|
7
|
+
IS_CONTROLLED,
|
|
8
|
+
IS_INDEXED,
|
|
9
|
+
TEMPLATE_FRAGMENT,
|
|
10
|
+
TEMPLATE_SVG_NAMESPACE,
|
|
11
|
+
TEMPLATE_MATHML_NAMESPACE,
|
|
12
|
+
} from '../../../constants.js';
|
|
7
13
|
import { sanitize_template_string } from '../../../utils/sanitize_template_string.js';
|
|
8
14
|
import {
|
|
9
15
|
build_hoisted_params,
|
|
@@ -13,7 +19,6 @@ import {
|
|
|
13
19
|
escape_html,
|
|
14
20
|
is_boolean_attribute,
|
|
15
21
|
is_dom_property,
|
|
16
|
-
is_ripple_import,
|
|
17
22
|
is_declared_function_within_component,
|
|
18
23
|
is_inside_call_expression,
|
|
19
24
|
is_value_static,
|
|
@@ -21,6 +26,7 @@ import {
|
|
|
21
26
|
is_component_level_function,
|
|
22
27
|
is_element_dom_element,
|
|
23
28
|
is_top_level_await,
|
|
29
|
+
is_ripple_track_call,
|
|
24
30
|
} from '../../utils.js';
|
|
25
31
|
import is_reference from 'is-reference';
|
|
26
32
|
import { object } from '../../../utils/ast.js';
|
|
@@ -104,6 +110,22 @@ function build_getter(node, context) {
|
|
|
104
110
|
return node;
|
|
105
111
|
}
|
|
106
112
|
|
|
113
|
+
function determine_namespace_for_children(element_name, current_namespace) {
|
|
114
|
+
if (element_name === 'foreignObject') {
|
|
115
|
+
return 'html';
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
if (element_name === 'svg') {
|
|
119
|
+
return 'svg';
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
if (element_name === 'math') {
|
|
123
|
+
return 'mathml';
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
return current_namespace;
|
|
127
|
+
}
|
|
128
|
+
|
|
107
129
|
const visitors = {
|
|
108
130
|
_: function set_scope(node, { next, state }) {
|
|
109
131
|
const scope = state.scopes.get(node);
|
|
@@ -128,7 +150,10 @@ const visitors = {
|
|
|
128
150
|
if (
|
|
129
151
|
(context.state.metadata?.tracking === false ||
|
|
130
152
|
(parent.type !== 'AssignmentExpression' && parent.type !== 'UpdateExpression')) &&
|
|
131
|
-
(node.tracked ||
|
|
153
|
+
(node.tracked ||
|
|
154
|
+
binding?.kind === 'prop' ||
|
|
155
|
+
binding?.kind === 'index' ||
|
|
156
|
+
binding?.kind === 'prop_fallback') &&
|
|
132
157
|
binding?.node !== node
|
|
133
158
|
) {
|
|
134
159
|
if (context.state.metadata?.tracking === false) {
|
|
@@ -165,16 +190,7 @@ const visitors = {
|
|
|
165
190
|
context.state.metadata.tracking = true;
|
|
166
191
|
}
|
|
167
192
|
|
|
168
|
-
if (
|
|
169
|
-
!context.state.to_ts &&
|
|
170
|
-
((callee.type === 'Identifier' && callee.name === 'track') ||
|
|
171
|
-
(callee.type === 'MemberExpression' &&
|
|
172
|
-
callee.object.type === 'Identifier' &&
|
|
173
|
-
callee.property.type === 'Identifier' &&
|
|
174
|
-
callee.property.name === 'track' &&
|
|
175
|
-
!callee.computed)) &&
|
|
176
|
-
is_ripple_import(callee, context)
|
|
177
|
-
) {
|
|
193
|
+
if (!context.state.to_ts && is_ripple_track_call(callee, context)) {
|
|
178
194
|
if (node.arguments.length === 0) {
|
|
179
195
|
node.arguments.push(b.void0);
|
|
180
196
|
}
|
|
@@ -427,6 +443,10 @@ const visitors = {
|
|
|
427
443
|
const is_spreading = node.attributes.some((attr) => attr.type === 'SpreadAttribute');
|
|
428
444
|
const spread_attributes = is_spreading ? [] : null;
|
|
429
445
|
|
|
446
|
+
const child_namespace = is_dom_element
|
|
447
|
+
? determine_namespace_for_children(node.id.name, state.namespace)
|
|
448
|
+
: state.namespace;
|
|
449
|
+
|
|
430
450
|
const handle_static_attr = (name, value) => {
|
|
431
451
|
const attr_value = b.literal(
|
|
432
452
|
` ${name}${
|
|
@@ -629,12 +649,16 @@ const visitors = {
|
|
|
629
649
|
if (node.metadata.scoped && state.component.css) {
|
|
630
650
|
expression = b.binary('+', b.literal(state.component.css.hash + ' '), expression);
|
|
631
651
|
}
|
|
632
|
-
const is_html = context.state.metadata.namespace === 'html' && node.id.name !== 'svg'
|
|
652
|
+
const is_html = context.state.metadata.namespace === 'html' && node.id.name !== 'svg';
|
|
633
653
|
|
|
634
|
-
if (metadata.tracking) {
|
|
635
|
-
local_updates.push(
|
|
654
|
+
if (class_attribute.name.name === '$class' || metadata.tracking) {
|
|
655
|
+
local_updates.push(
|
|
656
|
+
b.stmt(b.call('_$_.set_class', id, expression, undefined, b.literal(is_html))),
|
|
657
|
+
);
|
|
636
658
|
} else {
|
|
637
|
-
state.init.push(
|
|
659
|
+
state.init.push(
|
|
660
|
+
b.stmt(b.call('_$_.set_class', id, expression, undefined, b.literal(is_html))),
|
|
661
|
+
);
|
|
638
662
|
}
|
|
639
663
|
}
|
|
640
664
|
} else if (node.metadata.scoped && state.component.css) {
|
|
@@ -658,7 +682,7 @@ const visitors = {
|
|
|
658
682
|
if (!is_void) {
|
|
659
683
|
transform_children(node.children, {
|
|
660
684
|
visit,
|
|
661
|
-
state: { ...state, init, update },
|
|
685
|
+
state: { ...state, init, update, namespace: child_namespace },
|
|
662
686
|
root: false,
|
|
663
687
|
});
|
|
664
688
|
state.template.push(`</${node.id.name}>`);
|
|
@@ -769,7 +793,7 @@ const visitors = {
|
|
|
769
793
|
for (const child of node.children) {
|
|
770
794
|
if (child.type === 'Component') {
|
|
771
795
|
const id = child.id;
|
|
772
|
-
props.push(b.prop('init', id, visit(child, state)));
|
|
796
|
+
props.push(b.prop('init', id, visit(child, { ...state, namespace: child_namespace })));
|
|
773
797
|
} else {
|
|
774
798
|
children_filtered.push(child);
|
|
775
799
|
}
|
|
@@ -780,6 +804,7 @@ const visitors = {
|
|
|
780
804
|
const children = visit(b.component(b.id('children'), [], children_filtered), {
|
|
781
805
|
...context.state,
|
|
782
806
|
scope: component_scope,
|
|
807
|
+
namespace: child_namespace,
|
|
783
808
|
});
|
|
784
809
|
|
|
785
810
|
if (children_prop) {
|
|
@@ -1001,6 +1026,12 @@ const visitors = {
|
|
|
1001
1026
|
return;
|
|
1002
1027
|
}
|
|
1003
1028
|
const is_controlled = node.is_controlled;
|
|
1029
|
+
const index = node.index;
|
|
1030
|
+
let flags = is_controlled ? IS_CONTROLLED : 0;
|
|
1031
|
+
|
|
1032
|
+
if (index !== null) {
|
|
1033
|
+
flags |= IS_INDEXED;
|
|
1034
|
+
}
|
|
1004
1035
|
|
|
1005
1036
|
// do only if not controller
|
|
1006
1037
|
if (!is_controlled) {
|
|
@@ -1018,15 +1049,15 @@ const visitors = {
|
|
|
1018
1049
|
id,
|
|
1019
1050
|
b.thunk(context.visit(node.right)),
|
|
1020
1051
|
b.arrow(
|
|
1021
|
-
[b.id('__anchor'), pattern],
|
|
1052
|
+
index ? [b.id('__anchor'), pattern, index] : [b.id('__anchor'), pattern],
|
|
1022
1053
|
b.block(
|
|
1023
1054
|
transform_body(node.body.body, {
|
|
1024
1055
|
...context,
|
|
1025
|
-
state: { ...context.state, scope: body_scope },
|
|
1056
|
+
state: { ...context.state, scope: body_scope, namespace: context.state.namespace },
|
|
1026
1057
|
}),
|
|
1027
1058
|
),
|
|
1028
1059
|
),
|
|
1029
|
-
b.literal(
|
|
1060
|
+
b.literal(flags),
|
|
1030
1061
|
),
|
|
1031
1062
|
),
|
|
1032
1063
|
);
|
|
@@ -1470,9 +1501,15 @@ function transform_children(children, context) {
|
|
|
1470
1501
|
|
|
1471
1502
|
if (child.type === 'Text' && prev_child?.type === 'Text') {
|
|
1472
1503
|
if (child.expression.type === 'Literal' && prev_child.expression.type === 'Literal') {
|
|
1473
|
-
prev_child.expression = b.literal(
|
|
1504
|
+
prev_child.expression = b.literal(
|
|
1505
|
+
prev_child.expression.value + String(child.expression.value),
|
|
1506
|
+
);
|
|
1474
1507
|
} else {
|
|
1475
|
-
prev_child.expression = b.binary(
|
|
1508
|
+
prev_child.expression = b.binary(
|
|
1509
|
+
'+',
|
|
1510
|
+
prev_child.expression,
|
|
1511
|
+
b.call('String', child.expression),
|
|
1512
|
+
);
|
|
1476
1513
|
}
|
|
1477
1514
|
normalized.splice(i, 1);
|
|
1478
1515
|
}
|
|
@@ -1540,7 +1577,7 @@ function transform_children(children, context) {
|
|
|
1540
1577
|
prev = flush_node;
|
|
1541
1578
|
|
|
1542
1579
|
if (node.type === 'Element') {
|
|
1543
|
-
visit(node, { ...state, flush_node });
|
|
1580
|
+
visit(node, { ...state, flush_node, namespace: state.namespace });
|
|
1544
1581
|
} else if (node.type === 'Text') {
|
|
1545
1582
|
const metadata = { tracking: false, await: false };
|
|
1546
1583
|
const expression = visit(node.expression, { ...state, metadata });
|
|
@@ -1576,26 +1613,33 @@ function transform_children(children, context) {
|
|
|
1576
1613
|
} else if (node.type === 'ForOfStatement') {
|
|
1577
1614
|
const is_controlled = normalized.length === 1;
|
|
1578
1615
|
node.is_controlled = is_controlled;
|
|
1579
|
-
visit(node, { ...state, flush_node });
|
|
1616
|
+
visit(node, { ...state, flush_node, namespace: state.namespace });
|
|
1580
1617
|
} else if (node.type === 'IfStatement') {
|
|
1581
1618
|
const is_controlled = normalized.length === 1;
|
|
1582
1619
|
node.is_controlled = is_controlled;
|
|
1583
|
-
visit(node, { ...state, flush_node });
|
|
1620
|
+
visit(node, { ...state, flush_node, namespace: state.namespace });
|
|
1584
1621
|
} else if (node.type === 'TryStatement') {
|
|
1585
1622
|
const is_controlled = normalized.length === 1;
|
|
1586
1623
|
node.is_controlled = is_controlled;
|
|
1587
|
-
visit(node, { ...state, flush_node });
|
|
1624
|
+
visit(node, { ...state, flush_node, namespace: state.namespace });
|
|
1588
1625
|
} else {
|
|
1589
1626
|
debugger;
|
|
1590
1627
|
}
|
|
1591
1628
|
}
|
|
1592
1629
|
}
|
|
1593
1630
|
|
|
1631
|
+
const template_namespace = state.namespace || 'html';
|
|
1632
|
+
|
|
1594
1633
|
if (root && initial !== null && template_id !== null) {
|
|
1595
|
-
|
|
1634
|
+
let flags = is_fragment ? TEMPLATE_FRAGMENT : 0;
|
|
1635
|
+
if (template_namespace === 'svg') {
|
|
1636
|
+
flags |= TEMPLATE_SVG_NAMESPACE;
|
|
1637
|
+
} else if (template_namespace === 'mathml') {
|
|
1638
|
+
flags |= TEMPLATE_MATHML_NAMESPACE;
|
|
1639
|
+
}
|
|
1596
1640
|
state.final.push(b.stmt(b.call('_$_.append', b.id('__anchor'), initial)));
|
|
1597
1641
|
state.hoisted.push(
|
|
1598
|
-
b.var(template_id, b.call('_$_.template', join_template(state.template), flags)),
|
|
1642
|
+
b.var(template_id, b.call('_$_.template', join_template(state.template), b.literal(flags))),
|
|
1599
1643
|
);
|
|
1600
1644
|
}
|
|
1601
1645
|
}
|
|
@@ -1609,6 +1653,7 @@ function transform_body(body, { visit, state }) {
|
|
|
1609
1653
|
update: [],
|
|
1610
1654
|
final: [],
|
|
1611
1655
|
metadata: state.metadata,
|
|
1656
|
+
namespace: state.namespace || 'html', // Preserve namespace context
|
|
1612
1657
|
};
|
|
1613
1658
|
|
|
1614
1659
|
transform_children(body, { visit, state: body_state, root: true });
|
|
@@ -1637,7 +1682,9 @@ export function transform(filename, source, analysis, to_ts) {
|
|
|
1637
1682
|
to_ts,
|
|
1638
1683
|
};
|
|
1639
1684
|
|
|
1640
|
-
const program = /** @type {ESTree.Program} */ (
|
|
1685
|
+
const program = /** @type {ESTree.Program} */ (
|
|
1686
|
+
walk(analysis.ast, { ...state, namespace: 'html' }, visitors)
|
|
1687
|
+
);
|
|
1641
1688
|
|
|
1642
1689
|
for (const hoisted of state.hoisted) {
|
|
1643
1690
|
program.body.unshift(hoisted);
|