ripple 0.2.189 → 0.2.190
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 +4 -4
- package/src/compiler/identifier-utils.js +75 -0
- package/src/compiler/phases/1-parse/index.js +64 -16
- package/src/compiler/phases/2-analyze/index.js +84 -8
- package/src/compiler/phases/2-analyze/prune.js +30 -12
- package/src/compiler/phases/3-transform/client/index.js +166 -33
- package/src/compiler/phases/3-transform/segments.js +51 -19
- package/src/compiler/phases/3-transform/server/index.js +93 -20
- package/src/compiler/types/index.d.ts +46 -23
- package/src/compiler/types/parse.d.ts +5 -0
- package/src/compiler/utils.js +4 -4
- package/src/utils/builders.js +3 -2
- package/tests/client/compiler/compiler.basic.test.ripple +11 -11
- package/types/index.d.ts +2 -2
- package/src/compiler/import-utils.js +0 -51
|
@@ -8,7 +8,6 @@
|
|
|
8
8
|
VisitorClientContext,
|
|
9
9
|
TransformClientState,
|
|
10
10
|
ScopeInterface,
|
|
11
|
-
Visitor,
|
|
12
11
|
Visitors
|
|
13
12
|
} from '#compiler';
|
|
14
13
|
*/
|
|
@@ -52,7 +51,12 @@ import {
|
|
|
52
51
|
determine_namespace_for_children,
|
|
53
52
|
index_to_key,
|
|
54
53
|
} from '../../../utils.js';
|
|
55
|
-
import {
|
|
54
|
+
import {
|
|
55
|
+
CSS_HASH_IDENTIFIER,
|
|
56
|
+
STYLE_IDENTIFIER,
|
|
57
|
+
SERVER_IDENTIFIER,
|
|
58
|
+
obfuscate_identifier,
|
|
59
|
+
} from '../../../identifier-utils.js';
|
|
56
60
|
import is_reference from 'is-reference';
|
|
57
61
|
import { object } from '../../../../utils/ast.js';
|
|
58
62
|
import { render_stylesheets } from '../stylesheet.js';
|
|
@@ -316,7 +320,7 @@ function visit_title_element(node, context) {
|
|
|
316
320
|
* @returns {string}
|
|
317
321
|
*/
|
|
318
322
|
function set_hidden_import_from_ripple(name, context) {
|
|
319
|
-
name =
|
|
323
|
+
name = obfuscate_identifier(name);
|
|
320
324
|
if (!context.state.imports.has(`import { ${name} } from 'ripple/compiler/internal/import'`)) {
|
|
321
325
|
context.state.imports.add(`import { ${name} } from 'ripple/compiler/internal/import'`);
|
|
322
326
|
}
|
|
@@ -359,7 +363,7 @@ const visitors = {
|
|
|
359
363
|
name: capitalized_name,
|
|
360
364
|
metadata: {
|
|
361
365
|
...node.metadata,
|
|
362
|
-
|
|
366
|
+
source_name: node.name,
|
|
363
367
|
is_capitalized: true,
|
|
364
368
|
},
|
|
365
369
|
};
|
|
@@ -395,12 +399,44 @@ const visitors = {
|
|
|
395
399
|
},
|
|
396
400
|
|
|
397
401
|
ServerIdentifier(node, context) {
|
|
398
|
-
|
|
402
|
+
const id = b.id(SERVER_IDENTIFIER);
|
|
403
|
+
id.metadata.source_name = '#server';
|
|
404
|
+
id.loc = node.loc;
|
|
405
|
+
return id;
|
|
406
|
+
},
|
|
407
|
+
|
|
408
|
+
StyleIdentifier(node, context) {
|
|
409
|
+
const id = b.id(STYLE_IDENTIFIER);
|
|
410
|
+
id.metadata.source_name = '#style';
|
|
411
|
+
id.loc = node.loc;
|
|
412
|
+
return id;
|
|
399
413
|
},
|
|
400
414
|
|
|
401
|
-
/** @type {Visitor<AST.ImportDeclaration, TransformClientState, AST.Node>} */
|
|
402
415
|
ImportDeclaration(node, context) {
|
|
403
|
-
|
|
416
|
+
const { state } = context;
|
|
417
|
+
|
|
418
|
+
if (!state.to_ts && node.importKind === 'type') {
|
|
419
|
+
return b.empty;
|
|
420
|
+
}
|
|
421
|
+
|
|
422
|
+
if (state.to_ts && state.inside_server_block) {
|
|
423
|
+
/** @type {AST.VariableDeclaration[]} */
|
|
424
|
+
const locals = state.server_block_locals;
|
|
425
|
+
for (const spec of node.specifiers) {
|
|
426
|
+
const original_name = spec.local.name;
|
|
427
|
+
const name = obfuscate_identifier(original_name);
|
|
428
|
+
if (
|
|
429
|
+
spec.type !== 'ImportSpecifier' ||
|
|
430
|
+
(spec.imported && /** @type {AST.Identifier} */ (spec.imported).name !== spec.local.name)
|
|
431
|
+
) {
|
|
432
|
+
spec.local.name = name;
|
|
433
|
+
} else {
|
|
434
|
+
spec.local = b.id(name);
|
|
435
|
+
}
|
|
436
|
+
spec.local.metadata.source_name = original_name;
|
|
437
|
+
locals.push(b.const(original_name, b.id(name)));
|
|
438
|
+
}
|
|
439
|
+
state.imports.add(node);
|
|
404
440
|
return b.empty;
|
|
405
441
|
}
|
|
406
442
|
|
|
@@ -408,8 +444,7 @@ const visitors = {
|
|
|
408
444
|
...node,
|
|
409
445
|
specifiers: node.specifiers
|
|
410
446
|
.filter(
|
|
411
|
-
(spec) =>
|
|
412
|
-
context.state.to_ts || /** @type {AST.ImportSpecifier} */ (spec).importKind !== 'type',
|
|
447
|
+
(spec) => state.to_ts || /** @type {AST.ImportSpecifier} */ (spec).importKind !== 'type',
|
|
413
448
|
)
|
|
414
449
|
.map((spec) => context.visit(spec)),
|
|
415
450
|
});
|
|
@@ -422,7 +457,6 @@ const visitors = {
|
|
|
422
457
|
return context.visit(/** @type {AST.Expression} */ (node.expression));
|
|
423
458
|
},
|
|
424
459
|
|
|
425
|
-
/** @type {Visitor<AST.CallExpression, TransformClientState, AST.Node>} */
|
|
426
460
|
CallExpression(node, context) {
|
|
427
461
|
if (!context.state.to_ts) {
|
|
428
462
|
delete node.typeArguments;
|
|
@@ -543,7 +577,7 @@ const visitors = {
|
|
|
543
577
|
const calleeId = b.id(alias);
|
|
544
578
|
calleeId.loc = callee.loc;
|
|
545
579
|
calleeId.metadata = {
|
|
546
|
-
|
|
580
|
+
source_name: callee.type === 'TrackedMapExpression' ? '#Map' : '#Set',
|
|
547
581
|
path: [...context.path],
|
|
548
582
|
};
|
|
549
583
|
/** @type {AST.NewExpression} */
|
|
@@ -648,7 +682,6 @@ const visitors = {
|
|
|
648
682
|
return b.call('_$_.get', /** @type {AST.Expression} */ (context.visit(node.argument)));
|
|
649
683
|
},
|
|
650
684
|
|
|
651
|
-
/** @type {Visitor<AST.MemberExpression, TransformClientState, AST.Node>} */
|
|
652
685
|
MemberExpression(node, context) {
|
|
653
686
|
if (context.state.metadata?.tracking === false) {
|
|
654
687
|
context.state.metadata.tracking = true;
|
|
@@ -712,7 +745,6 @@ const visitors = {
|
|
|
712
745
|
return context.next();
|
|
713
746
|
},
|
|
714
747
|
|
|
715
|
-
/** @type {Visitor<AST.VariableDeclarator, TransformClientState, AST.Node>} */
|
|
716
748
|
VariableDeclarator(node, context) {
|
|
717
749
|
// In TypeScript mode, capitalize identifiers that are used as dynamic components
|
|
718
750
|
if (context.state.to_ts) {
|
|
@@ -732,7 +764,7 @@ const visitors = {
|
|
|
732
764
|
name: capitalized_name,
|
|
733
765
|
metadata: {
|
|
734
766
|
...pattern.metadata,
|
|
735
|
-
|
|
767
|
+
source_name: pattern.name,
|
|
736
768
|
is_capitalized: true,
|
|
737
769
|
},
|
|
738
770
|
};
|
|
@@ -1588,6 +1620,37 @@ const visitors = {
|
|
|
1588
1620
|
let prop_statements;
|
|
1589
1621
|
const metadata = { await: false };
|
|
1590
1622
|
|
|
1623
|
+
/** @type {AST.Statement[]} */
|
|
1624
|
+
const style_statements = [];
|
|
1625
|
+
|
|
1626
|
+
/** @type {'const' | 'var'} */
|
|
1627
|
+
let var_method_type = 'var';
|
|
1628
|
+
if (context.state.to_ts) {
|
|
1629
|
+
var_method_type = 'const';
|
|
1630
|
+
}
|
|
1631
|
+
|
|
1632
|
+
if (node.css !== null && node.metadata.styleIdentifierPresent) {
|
|
1633
|
+
/** @type {AST.Property[]} */
|
|
1634
|
+
const properties = [];
|
|
1635
|
+
if (node.metadata.topScopedClasses && node.metadata.topScopedClasses.size > 0) {
|
|
1636
|
+
const hash = b[var_method_type](b.id(CSS_HASH_IDENTIFIER), b.literal(node.css.hash));
|
|
1637
|
+
style_statements.push(hash);
|
|
1638
|
+
for (const [className] of node.metadata.topScopedClasses) {
|
|
1639
|
+
properties.push(
|
|
1640
|
+
b.prop(
|
|
1641
|
+
'init',
|
|
1642
|
+
b.key(className),
|
|
1643
|
+
b.template(
|
|
1644
|
+
[b.quasi('', false), b.quasi(` ${className}`, true)],
|
|
1645
|
+
[b.id(CSS_HASH_IDENTIFIER)],
|
|
1646
|
+
),
|
|
1647
|
+
),
|
|
1648
|
+
);
|
|
1649
|
+
}
|
|
1650
|
+
}
|
|
1651
|
+
style_statements.push(b[var_method_type](b.id(STYLE_IDENTIFIER), b.object(properties)));
|
|
1652
|
+
}
|
|
1653
|
+
|
|
1591
1654
|
if (context.state.to_ts) {
|
|
1592
1655
|
const body_statements = [
|
|
1593
1656
|
...transform_body(node.body, {
|
|
@@ -1602,7 +1665,7 @@ const visitors = {
|
|
|
1602
1665
|
(param) =>
|
|
1603
1666
|
/** @type {AST.Pattern} */ (context.visit(param, { ...context.state, metadata })),
|
|
1604
1667
|
),
|
|
1605
|
-
b.block(body_statements),
|
|
1668
|
+
b.block([...style_statements, ...body_statements]),
|
|
1606
1669
|
);
|
|
1607
1670
|
// Mark that this function was originally a component
|
|
1608
1671
|
func.metadata = /** @type {AST.FunctionExpression['metadata']} */ ({
|
|
@@ -1645,6 +1708,7 @@ const visitors = {
|
|
|
1645
1708
|
? [b.id('__anchor'), props, b.id('__block')]
|
|
1646
1709
|
: [b.id('__anchor'), b.id('_'), b.id('__block')],
|
|
1647
1710
|
b.block([
|
|
1711
|
+
...style_statements,
|
|
1648
1712
|
...(prop_statements ?? []),
|
|
1649
1713
|
...(metadata.await
|
|
1650
1714
|
? [b.stmt(b.call('_$_.async', b.thunk(b.block(body_statements), true)))]
|
|
@@ -1998,6 +2062,17 @@ const visitors = {
|
|
|
1998
2062
|
return b.empty;
|
|
1999
2063
|
}
|
|
2000
2064
|
|
|
2065
|
+
if (context.state.to_ts && context.state.inside_server_block) {
|
|
2066
|
+
const declaration = node.declaration;
|
|
2067
|
+
|
|
2068
|
+
if (declaration && declaration.type === 'FunctionDeclaration') {
|
|
2069
|
+
return context.visit(declaration);
|
|
2070
|
+
} else {
|
|
2071
|
+
// TODO
|
|
2072
|
+
throw new Error('Not implemented');
|
|
2073
|
+
}
|
|
2074
|
+
}
|
|
2075
|
+
|
|
2001
2076
|
return context.next();
|
|
2002
2077
|
},
|
|
2003
2078
|
|
|
@@ -2101,15 +2176,64 @@ const visitors = {
|
|
|
2101
2176
|
},
|
|
2102
2177
|
|
|
2103
2178
|
ServerBlock(node, context) {
|
|
2179
|
+
if (context.state.to_ts) {
|
|
2180
|
+
// Convert Imports inside ServerBlock to local variables
|
|
2181
|
+
// ImportDeclaration() visitor will add imports to the top of the module
|
|
2182
|
+
/** @type {AST.VariableDeclaration[]} */
|
|
2183
|
+
const server_block_locals = [];
|
|
2184
|
+
|
|
2185
|
+
const block = /** @type {AST.BlockStatement} */ (
|
|
2186
|
+
context.visit(node.body, {
|
|
2187
|
+
...context.state,
|
|
2188
|
+
inside_server_block: true,
|
|
2189
|
+
server_block_locals,
|
|
2190
|
+
})
|
|
2191
|
+
);
|
|
2192
|
+
|
|
2193
|
+
/** @type {AST.Property[]} */
|
|
2194
|
+
const properties = [];
|
|
2195
|
+
|
|
2196
|
+
// Extract and preserve original function declarations
|
|
2197
|
+
for (const stmt of node.body.body) {
|
|
2198
|
+
if (
|
|
2199
|
+
stmt.type === 'ExportNamedDeclaration' &&
|
|
2200
|
+
stmt.declaration?.type === 'FunctionDeclaration' &&
|
|
2201
|
+
stmt.declaration.id
|
|
2202
|
+
) {
|
|
2203
|
+
// create new nodes to avoid same node.loc issue
|
|
2204
|
+
// that would result in double definitions
|
|
2205
|
+
const id = b.id(stmt.declaration.id.name);
|
|
2206
|
+
properties.push(b.prop('init', id, id, false, true));
|
|
2207
|
+
}
|
|
2208
|
+
}
|
|
2209
|
+
|
|
2210
|
+
const value = b.call(
|
|
2211
|
+
b.thunk(b.block([...server_block_locals, ...block.body, b.return(b.object(properties))])),
|
|
2212
|
+
);
|
|
2213
|
+
value.loc = node.loc;
|
|
2214
|
+
|
|
2215
|
+
const server_identifier = b.id(SERVER_IDENTIFIER);
|
|
2216
|
+
server_identifier.loc = node.loc;
|
|
2217
|
+
// Add source_name to properly map longer generated back to '#server'
|
|
2218
|
+
server_identifier.metadata.source_name = '#server';
|
|
2219
|
+
|
|
2220
|
+
const server_const = b.const(server_identifier, value);
|
|
2221
|
+
server_const.loc = node.loc;
|
|
2222
|
+
|
|
2223
|
+
return server_const;
|
|
2224
|
+
}
|
|
2225
|
+
|
|
2104
2226
|
const exports = node.metadata.exports;
|
|
2105
2227
|
|
|
2106
|
-
if (
|
|
2228
|
+
if (!context.state.serverIdentifierPresent) {
|
|
2229
|
+
// no point printing the client-side block if #server.func is not used
|
|
2107
2230
|
return b.empty;
|
|
2108
2231
|
}
|
|
2232
|
+
|
|
2109
2233
|
const file_path = context.state.filename;
|
|
2110
2234
|
|
|
2111
|
-
return b.
|
|
2112
|
-
|
|
2235
|
+
return b.var(
|
|
2236
|
+
SERVER_IDENTIFIER,
|
|
2113
2237
|
b.object(
|
|
2114
2238
|
/** @type {AST.ServerBlock['metadata']['exports']} */ (exports).map((name) => {
|
|
2115
2239
|
const func_path = file_path + '#' + name;
|
|
@@ -2130,7 +2254,6 @@ const visitors = {
|
|
|
2130
2254
|
);
|
|
2131
2255
|
},
|
|
2132
2256
|
|
|
2133
|
-
/** @type {Visitor<AST.Program, TransformClientState, AST.Node>} */
|
|
2134
2257
|
Program(node, context) {
|
|
2135
2258
|
/** @type {Array<AST.Statement | AST.Directive | AST.ModuleDeclaration>} */
|
|
2136
2259
|
const statements = [];
|
|
@@ -2318,9 +2441,9 @@ function transform_ts_child(node, context) {
|
|
|
2318
2441
|
end: node.id.loc.end,
|
|
2319
2442
|
};
|
|
2320
2443
|
// Add metadata if this was capitalized
|
|
2321
|
-
if (node.metadata?.ts_name && node.metadata?.
|
|
2444
|
+
if (node.metadata?.ts_name && node.metadata?.source_name) {
|
|
2322
2445
|
opening_name_element.metadata = {
|
|
2323
|
-
|
|
2446
|
+
source_name: node.metadata.source_name,
|
|
2324
2447
|
is_capitalized: true,
|
|
2325
2448
|
path: [...node.metadata.path],
|
|
2326
2449
|
};
|
|
@@ -2357,14 +2480,14 @@ function transform_ts_child(node, context) {
|
|
|
2357
2480
|
column:
|
|
2358
2481
|
closing_tag_start +
|
|
2359
2482
|
3 +
|
|
2360
|
-
(node.metadata?.
|
|
2483
|
+
(node.metadata?.source_name?.length ||
|
|
2361
2484
|
/** @type {string} */ (type_expression).length),
|
|
2362
2485
|
},
|
|
2363
2486
|
};
|
|
2364
2487
|
// Add metadata if this was capitalized
|
|
2365
|
-
if (node.metadata?.ts_name && node.metadata?.
|
|
2488
|
+
if (node.metadata?.ts_name && node.metadata?.source_name) {
|
|
2366
2489
|
closing_name_element.metadata = {
|
|
2367
|
-
|
|
2490
|
+
source_name: node.metadata.source_name,
|
|
2368
2491
|
is_capitalized: true,
|
|
2369
2492
|
path: [...node.metadata.path],
|
|
2370
2493
|
};
|
|
@@ -2399,8 +2522,7 @@ function transform_ts_child(node, context) {
|
|
|
2399
2522
|
// - '<' is at node.loc.end.column - type_expression.length - 3
|
|
2400
2523
|
// - '>' is at node.loc.end.column - 1
|
|
2401
2524
|
const tag_name_length = node.id.tracked
|
|
2402
|
-
? (node.metadata?.
|
|
2403
|
-
1 // +1 for '@'
|
|
2525
|
+
? (node.metadata?.source_name?.length || /** @type {string} */ (type_expression).length) + 1 // +1 for '@'
|
|
2404
2526
|
: /** @type {string} */ (type_expression).length;
|
|
2405
2527
|
|
|
2406
2528
|
jsxElement.closingElement.loc = {
|
|
@@ -2416,10 +2538,10 @@ function transform_ts_child(node, context) {
|
|
|
2416
2538
|
}
|
|
2417
2539
|
|
|
2418
2540
|
// Preserve metadata from Element node for mapping purposes
|
|
2419
|
-
if (node.metadata && (node.metadata.ts_name || node.metadata.
|
|
2541
|
+
if (node.metadata && (node.metadata.ts_name || node.metadata.source_name)) {
|
|
2420
2542
|
jsxElement.metadata = {
|
|
2421
2543
|
ts_name: node.metadata.ts_name,
|
|
2422
|
-
|
|
2544
|
+
source_name: node.metadata.source_name,
|
|
2423
2545
|
path: [...node.metadata.path],
|
|
2424
2546
|
};
|
|
2425
2547
|
}
|
|
@@ -2928,13 +3050,17 @@ function create_tsx_with_typescript_support() {
|
|
|
2928
3050
|
* @param {TransformClientContext} context
|
|
2929
3051
|
*/
|
|
2930
3052
|
const handle_function = (node, context) => {
|
|
3053
|
+
const loc = /** @type {AST.SourceLocation} */ (node.loc);
|
|
3054
|
+
|
|
2931
3055
|
if (node.async) {
|
|
3056
|
+
context.location(loc.start.line, loc.start.column);
|
|
2932
3057
|
context.write('async ');
|
|
3058
|
+
context.location(loc.start.line, loc.start.column + 6);
|
|
3059
|
+
context.write('function');
|
|
3060
|
+
} else {
|
|
3061
|
+
context.write('function', node);
|
|
2933
3062
|
}
|
|
2934
|
-
|
|
2935
|
-
// This creates a mapping from the source position (which may have 'component')
|
|
2936
|
-
// to the generated 'function' keyword
|
|
2937
|
-
context.write('function', node);
|
|
3063
|
+
|
|
2938
3064
|
if (node.generator) {
|
|
2939
3065
|
context.write('*');
|
|
2940
3066
|
}
|
|
@@ -3461,6 +3587,9 @@ export function transform_client(filename, source, analysis, to_ts, minify_css)
|
|
|
3461
3587
|
flush_node: null,
|
|
3462
3588
|
scope: analysis.scope,
|
|
3463
3589
|
scopes: analysis.scopes,
|
|
3590
|
+
inside_server_block: false,
|
|
3591
|
+
serverIdentifierPresent: analysis.metadata.serverIdentifierPresent,
|
|
3592
|
+
server_block_locals: [],
|
|
3464
3593
|
stylesheets: [],
|
|
3465
3594
|
to_ts,
|
|
3466
3595
|
filename,
|
|
@@ -3482,7 +3611,11 @@ export function transform_client(filename, source, analysis, to_ts, minify_css)
|
|
|
3482
3611
|
}
|
|
3483
3612
|
|
|
3484
3613
|
for (const import_node of state.imports) {
|
|
3485
|
-
|
|
3614
|
+
if (typeof import_node === 'string') {
|
|
3615
|
+
program.body.unshift(b.stmt(b.id(import_node)));
|
|
3616
|
+
} else {
|
|
3617
|
+
program.body.unshift(import_node);
|
|
3618
|
+
}
|
|
3486
3619
|
}
|
|
3487
3620
|
|
|
3488
3621
|
if (state.events.size > 0) {
|
|
@@ -354,18 +354,11 @@ export function convert_source_map_to_mappings(
|
|
|
354
354
|
// Only create mappings for identifiers with location info (from source)
|
|
355
355
|
// Synthesized identifiers (created by builders) don't have .loc and are skipped
|
|
356
356
|
if (node.name && node.loc) {
|
|
357
|
-
// Check if this identifier
|
|
358
|
-
if
|
|
357
|
+
// Check if this identifier was changed in metadata (e.g., #Map -> TrackedMap)
|
|
358
|
+
// Or if it was capitalized during transformation
|
|
359
|
+
if (node.metadata?.source_name) {
|
|
359
360
|
tokens.push({
|
|
360
|
-
source: node.metadata.
|
|
361
|
-
generated: node.name,
|
|
362
|
-
loc: node.loc,
|
|
363
|
-
});
|
|
364
|
-
} else if (node.metadata?.is_capitalized) {
|
|
365
|
-
// This identifier was capitalized during transformation
|
|
366
|
-
// Map the original lowercase name to the capitalized generated name
|
|
367
|
-
tokens.push({
|
|
368
|
-
source: node.metadata.original_name,
|
|
361
|
+
source: node.metadata.source_name,
|
|
369
362
|
generated: node.name,
|
|
370
363
|
loc: node.loc,
|
|
371
364
|
});
|
|
@@ -391,7 +384,7 @@ export function convert_source_map_to_mappings(
|
|
|
391
384
|
if (node.loc && node.name) {
|
|
392
385
|
if (node.metadata?.is_capitalized) {
|
|
393
386
|
tokens.push({
|
|
394
|
-
source: node.metadata.
|
|
387
|
+
source: node.metadata.source_name,
|
|
395
388
|
generated: node.name,
|
|
396
389
|
loc: node.loc,
|
|
397
390
|
});
|
|
@@ -657,7 +650,7 @@ export function convert_source_map_to_mappings(
|
|
|
657
650
|
);
|
|
658
651
|
if (closingNameNode.metadata?.is_capitalized) {
|
|
659
652
|
tokens.push({
|
|
660
|
-
source: closingNameNode.metadata.
|
|
653
|
+
source: closingNameNode.metadata.source_name,
|
|
661
654
|
generated: closingNameNode.name,
|
|
662
655
|
loc: closingNameNode.loc,
|
|
663
656
|
});
|
|
@@ -679,16 +672,35 @@ export function convert_source_map_to_mappings(
|
|
|
679
672
|
// Add function/component keyword token
|
|
680
673
|
if (node.type === 'FunctionDeclaration' || node.type === 'FunctionExpression') {
|
|
681
674
|
const node_fn = /** @type (typeof node) & AST.NodeWithLocation */ (node);
|
|
682
|
-
const
|
|
683
|
-
|
|
675
|
+
const source_func_keyword = node.metadata?.was_component ? 'component' : 'function';
|
|
676
|
+
let start_col = node_fn.loc.start.column;
|
|
677
|
+
const async_keyword = 'async';
|
|
678
|
+
|
|
679
|
+
// We explicitly mapped async and function in esrap
|
|
680
|
+
if (node_fn.async) {
|
|
681
|
+
tokens.push({
|
|
682
|
+
source: async_keyword,
|
|
683
|
+
generated: async_keyword,
|
|
684
|
+
loc: {
|
|
685
|
+
start: { line: node_fn.loc.start.line, column: start_col },
|
|
686
|
+
end: {
|
|
687
|
+
line: node_fn.loc.start.line,
|
|
688
|
+
column: start_col + async_keyword.length,
|
|
689
|
+
},
|
|
690
|
+
},
|
|
691
|
+
});
|
|
692
|
+
|
|
693
|
+
start_col += async_keyword.length + 1; // +1 for space
|
|
694
|
+
}
|
|
695
|
+
|
|
684
696
|
tokens.push({
|
|
685
|
-
source:
|
|
697
|
+
source: source_func_keyword,
|
|
686
698
|
generated: 'function',
|
|
687
699
|
loc: {
|
|
688
|
-
start: { line: node_fn.loc.start.line, column:
|
|
700
|
+
start: { line: node_fn.loc.start.line, column: start_col },
|
|
689
701
|
end: {
|
|
690
702
|
line: node_fn.loc.start.line,
|
|
691
|
-
column:
|
|
703
|
+
column: start_col + source_func_keyword.length,
|
|
692
704
|
},
|
|
693
705
|
},
|
|
694
706
|
});
|
|
@@ -887,7 +899,27 @@ export function convert_source_map_to_mappings(
|
|
|
887
899
|
if (node.object) {
|
|
888
900
|
visit(node.object);
|
|
889
901
|
}
|
|
890
|
-
if (
|
|
902
|
+
if (node.computed && node.property && node.loc) {
|
|
903
|
+
// Need to cover the whole computed property ['something'] or obj[expr]:
|
|
904
|
+
// Add a mapping for the closing bracket ']'
|
|
905
|
+
// ESRap sourcemap includes the opening bracket '[' in the property loc,
|
|
906
|
+
// but for the closing bracket it also includes what comes after it
|
|
907
|
+
// so we never get the mapping that covers just the computed property.
|
|
908
|
+
tokens.push({
|
|
909
|
+
source: ']',
|
|
910
|
+
generated: ']',
|
|
911
|
+
loc: {
|
|
912
|
+
start: {
|
|
913
|
+
line: node.loc.end.line,
|
|
914
|
+
column: node.loc.end.column - 1,
|
|
915
|
+
},
|
|
916
|
+
end: node.loc.end,
|
|
917
|
+
},
|
|
918
|
+
});
|
|
919
|
+
|
|
920
|
+
// Also visit the property for its own mapping
|
|
921
|
+
visit(node.property);
|
|
922
|
+
} else if (!node.computed && node.property) {
|
|
891
923
|
visit(node.property);
|
|
892
924
|
}
|
|
893
925
|
return;
|
|
@@ -30,6 +30,11 @@ import { escape } from '../../../../utils/escaping.js';
|
|
|
30
30
|
import { is_event_attribute } from '../../../../utils/events.js';
|
|
31
31
|
import { render_stylesheets } from '../stylesheet.js';
|
|
32
32
|
import { createHash } from 'node:crypto';
|
|
33
|
+
import {
|
|
34
|
+
STYLE_IDENTIFIER,
|
|
35
|
+
CSS_HASH_IDENTIFIER,
|
|
36
|
+
obfuscate_identifier,
|
|
37
|
+
} from '../../../identifier-utils.js';
|
|
33
38
|
|
|
34
39
|
/**
|
|
35
40
|
* @param {AST.Node[]} children
|
|
@@ -127,22 +132,47 @@ const visitors = {
|
|
|
127
132
|
}
|
|
128
133
|
|
|
129
134
|
const metadata = { await: false };
|
|
130
|
-
|
|
135
|
+
|
|
136
|
+
/** @type {AST.Statement[]} */
|
|
137
|
+
const body_statements = [];
|
|
138
|
+
|
|
139
|
+
if (node.css !== null) {
|
|
140
|
+
const hash_id = b.id(CSS_HASH_IDENTIFIER);
|
|
141
|
+
const hash = b.var(hash_id, b.literal(node.css.hash));
|
|
142
|
+
context.state.stylesheets.push(node.css);
|
|
143
|
+
|
|
144
|
+
// Register CSS hash during rendering
|
|
145
|
+
body_statements.push(
|
|
146
|
+
hash,
|
|
147
|
+
b.stmt(b.call(b.member(b.id('__output'), b.id('register_css')), hash_id)),
|
|
148
|
+
);
|
|
149
|
+
|
|
150
|
+
if (node.metadata.styleIdentifierPresent) {
|
|
151
|
+
/** @type {AST.Property[]} */
|
|
152
|
+
const properties = [];
|
|
153
|
+
if (node.metadata.topScopedClasses && node.metadata.topScopedClasses.size > 0) {
|
|
154
|
+
for (const [className] of node.metadata.topScopedClasses) {
|
|
155
|
+
properties.push(
|
|
156
|
+
b.prop(
|
|
157
|
+
'init',
|
|
158
|
+
b.key(className),
|
|
159
|
+
b.template([b.quasi('', false), b.quasi(` ${className}`, true)], [hash_id]),
|
|
160
|
+
),
|
|
161
|
+
);
|
|
162
|
+
}
|
|
163
|
+
}
|
|
164
|
+
body_statements.push(b.var(b.id(STYLE_IDENTIFIER), b.object(properties)));
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
body_statements.push(
|
|
131
169
|
b.stmt(b.call('_$_.push_component')),
|
|
132
170
|
...transform_body(node.body, {
|
|
133
171
|
...context,
|
|
134
172
|
state: { ...context.state, component: node, metadata },
|
|
135
173
|
}),
|
|
136
174
|
b.stmt(b.call('_$_.pop_component')),
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
if (node.css !== null && node.css) {
|
|
140
|
-
context.state.stylesheets.push(node.css);
|
|
141
|
-
// Register CSS hash during rendering
|
|
142
|
-
body_statements.unshift(
|
|
143
|
-
b.stmt(b.call(b.member(b.id('__output'), b.id('register_css')), b.literal(node.css.hash))),
|
|
144
|
-
);
|
|
145
|
-
}
|
|
175
|
+
);
|
|
146
176
|
|
|
147
177
|
let component_fn = b.function(
|
|
148
178
|
node.id,
|
|
@@ -617,6 +647,7 @@ const visitors = {
|
|
|
617
647
|
}
|
|
618
648
|
}
|
|
619
649
|
},
|
|
650
|
+
|
|
620
651
|
SwitchStatement(node, context) {
|
|
621
652
|
if (!is_inside_component(context)) {
|
|
622
653
|
return context.next();
|
|
@@ -811,9 +842,31 @@ const visitors = {
|
|
|
811
842
|
return b.id('_$_server_$_');
|
|
812
843
|
},
|
|
813
844
|
|
|
814
|
-
|
|
845
|
+
StyleIdentifier(node, context) {
|
|
846
|
+
return b.id(STYLE_IDENTIFIER);
|
|
847
|
+
},
|
|
848
|
+
|
|
815
849
|
ImportDeclaration(node, context) {
|
|
816
|
-
|
|
850
|
+
const { state } = context;
|
|
851
|
+
|
|
852
|
+
if (!state.to_ts && node.importKind === 'type') {
|
|
853
|
+
return b.empty;
|
|
854
|
+
}
|
|
855
|
+
|
|
856
|
+
if (state.inside_server_block) {
|
|
857
|
+
if (!node.specifiers.length) {
|
|
858
|
+
return b.empty;
|
|
859
|
+
}
|
|
860
|
+
|
|
861
|
+
/** @type {AST.VariableDeclaration[]} */
|
|
862
|
+
const locals = state.server_block_locals;
|
|
863
|
+
for (const spec of node.specifiers) {
|
|
864
|
+
const original_name = spec.local.name;
|
|
865
|
+
const name = obfuscate_identifier(original_name);
|
|
866
|
+
spec.local = b.id(name);
|
|
867
|
+
locals.push(b.const(original_name, b.id(name)));
|
|
868
|
+
}
|
|
869
|
+
state.imports.add(node);
|
|
817
870
|
return b.empty;
|
|
818
871
|
}
|
|
819
872
|
|
|
@@ -915,8 +968,7 @@ const visitors = {
|
|
|
915
968
|
|
|
916
969
|
AwaitExpression(node, context) {
|
|
917
970
|
const { state } = context;
|
|
918
|
-
|
|
919
|
-
state.inside_server_block = true;
|
|
971
|
+
|
|
920
972
|
if (state.to_ts) {
|
|
921
973
|
return context.next();
|
|
922
974
|
}
|
|
@@ -1007,13 +1059,27 @@ const visitors = {
|
|
|
1007
1059
|
ServerBlock(node, context) {
|
|
1008
1060
|
const exports = node.metadata.exports;
|
|
1009
1061
|
|
|
1062
|
+
// Convert Imports inside ServerBlock to local variables
|
|
1063
|
+
// ImportDeclaration() visitor will add imports to the top of the module
|
|
1064
|
+
/** @type {AST.VariableDeclaration[]} */
|
|
1065
|
+
const server_block_locals = [];
|
|
1066
|
+
|
|
1067
|
+
const block = /** @type {AST.BlockStatement} */ (
|
|
1068
|
+
context.visit(node.body, {
|
|
1069
|
+
...context.state,
|
|
1070
|
+
inside_server_block: true,
|
|
1071
|
+
server_block_locals,
|
|
1072
|
+
})
|
|
1073
|
+
);
|
|
1074
|
+
|
|
1010
1075
|
if (exports.length === 0) {
|
|
1011
|
-
return
|
|
1076
|
+
return {
|
|
1077
|
+
...block,
|
|
1078
|
+
body: [...server_block_locals, ...block.body],
|
|
1079
|
+
};
|
|
1012
1080
|
}
|
|
1081
|
+
|
|
1013
1082
|
const file_path = context.state.filename;
|
|
1014
|
-
const block = /** @type {AST.BlockStatement} */ (
|
|
1015
|
-
context.visit(node.body, { ...context.state, inside_server_block: true })
|
|
1016
|
-
);
|
|
1017
1083
|
const rpc_modules = globalThis.rpc_modules;
|
|
1018
1084
|
|
|
1019
1085
|
if (rpc_modules) {
|
|
@@ -1032,6 +1098,7 @@ const visitors = {
|
|
|
1032
1098
|
b.thunk(
|
|
1033
1099
|
b.block([
|
|
1034
1100
|
b.var('_$_server_$_', b.object([])),
|
|
1101
|
+
...server_block_locals,
|
|
1035
1102
|
...block.body,
|
|
1036
1103
|
b.return(b.id('_$_server_$_')),
|
|
1037
1104
|
]),
|
|
@@ -1059,9 +1126,11 @@ export function transform_server(filename, source, analysis, minify_css) {
|
|
|
1059
1126
|
init: null,
|
|
1060
1127
|
scope: analysis.scope,
|
|
1061
1128
|
scopes: analysis.scopes,
|
|
1129
|
+
serverIdentifierPresent: analysis.metadata.serverIdentifierPresent,
|
|
1062
1130
|
stylesheets: [],
|
|
1063
1131
|
component_metadata,
|
|
1064
1132
|
inside_server_block: false,
|
|
1133
|
+
server_block_locals: [],
|
|
1065
1134
|
filename,
|
|
1066
1135
|
namespace: 'html',
|
|
1067
1136
|
// TODO: should we remove all `to_ts` usages we use the client rendering for that?
|
|
@@ -1071,7 +1140,7 @@ export function transform_server(filename, source, analysis, minify_css) {
|
|
|
1071
1140
|
|
|
1072
1141
|
state.imports.add(`import * as _$_ from 'ripple/internal/server'`);
|
|
1073
1142
|
|
|
1074
|
-
const program = walk(analysis.ast, { ...state }, visitors);
|
|
1143
|
+
const program = /** @type {AST.Program} */ (walk(analysis.ast, { ...state }, visitors));
|
|
1075
1144
|
|
|
1076
1145
|
const css = render_stylesheets(state.stylesheets, minify_css);
|
|
1077
1146
|
|
|
@@ -1090,7 +1159,11 @@ export function transform_server(filename, source, analysis, minify_css) {
|
|
|
1090
1159
|
|
|
1091
1160
|
// Add async property to component functions
|
|
1092
1161
|
for (const import_node of state.imports) {
|
|
1093
|
-
|
|
1162
|
+
if (typeof import_node === 'string') {
|
|
1163
|
+
program.body.unshift(b.stmt(b.id(import_node)));
|
|
1164
|
+
} else {
|
|
1165
|
+
program.body.unshift(import_node);
|
|
1166
|
+
}
|
|
1094
1167
|
}
|
|
1095
1168
|
|
|
1096
1169
|
const js = print(program, /** @type {Visitors<AST.Node, TransformServerState>} */ (ts()), {
|