svelte2tsx 0.6.1 → 0.6.2
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/index.js +430 -2121
- package/index.mjs +430 -2121
- package/package.json +1 -1
- package/svelte-jsx.d.ts +5 -3
- package/svelte-shims.d.ts +0 -33
package/index.js
CHANGED
|
@@ -1281,7 +1281,7 @@ function parseAttributes(str, start) {
|
|
|
1281
1281
|
});
|
|
1282
1282
|
return attrs;
|
|
1283
1283
|
}
|
|
1284
|
-
function extractTag(htmlx, tag
|
|
1284
|
+
function extractTag(htmlx, tag) {
|
|
1285
1285
|
const exp = new RegExp(`(<!--[^]*?-->)|(<${tag}([\\S\\s]*?)>)([\\S\\s]*?)<\\/${tag}>`, 'g');
|
|
1286
1286
|
const matches = [];
|
|
1287
1287
|
let match = null;
|
|
@@ -1292,2090 +1292,111 @@ function extractTag(htmlx, tag, useNewTransformation) {
|
|
|
1292
1292
|
}
|
|
1293
1293
|
let content = match[4];
|
|
1294
1294
|
if (!content) {
|
|
1295
|
-
|
|
1296
|
-
|
|
1297
|
-
content = '';
|
|
1298
|
-
}
|
|
1299
|
-
else {
|
|
1300
|
-
// Self-closing/empty tags don't need replacement
|
|
1301
|
-
continue;
|
|
1302
|
-
}
|
|
1295
|
+
// Keep tag and transform it like a regular element
|
|
1296
|
+
content = '';
|
|
1303
1297
|
}
|
|
1304
1298
|
const start = match.index + match[2].length;
|
|
1305
1299
|
const end = start + content.length;
|
|
1306
1300
|
const containerStart = match.index;
|
|
1307
1301
|
const containerEnd = match.index + match[0].length;
|
|
1308
1302
|
matches.push({
|
|
1309
|
-
start: containerStart,
|
|
1310
|
-
end: containerEnd,
|
|
1311
|
-
name: tag,
|
|
1312
|
-
type: tag === 'style' ? 'Style' : 'Script',
|
|
1313
|
-
attributes: parseAttributes(match[3], containerStart + `<${tag}`.length),
|
|
1314
|
-
content: {
|
|
1315
|
-
type: 'Text',
|
|
1316
|
-
start,
|
|
1317
|
-
end,
|
|
1318
|
-
value: content,
|
|
1319
|
-
raw: content
|
|
1320
|
-
}
|
|
1321
|
-
});
|
|
1322
|
-
}
|
|
1323
|
-
return matches;
|
|
1324
|
-
}
|
|
1325
|
-
function findVerbatimElements(htmlx, useNewTransformation) {
|
|
1326
|
-
return [
|
|
1327
|
-
...extractTag(htmlx, 'script', useNewTransformation),
|
|
1328
|
-
...extractTag(htmlx, 'style', useNewTransformation)
|
|
1329
|
-
];
|
|
1330
|
-
}
|
|
1331
|
-
function blankVerbatimContent(htmlx, verbatimElements) {
|
|
1332
|
-
let output = htmlx;
|
|
1333
|
-
for (const node of verbatimElements) {
|
|
1334
|
-
const content = node.content;
|
|
1335
|
-
if (content) {
|
|
1336
|
-
output =
|
|
1337
|
-
output.substring(0, content.start) +
|
|
1338
|
-
output
|
|
1339
|
-
.substring(content.start, content.end)
|
|
1340
|
-
// blank out the content
|
|
1341
|
-
.replace(/[^\n]/g, ' ')
|
|
1342
|
-
// excess blank space can make the svelte parser very slow (sec->min). break it up with comments (works in style/script)
|
|
1343
|
-
.replace(/[^\n][^\n][^\n][^\n]\n/g, '/**/\n') +
|
|
1344
|
-
output.substring(content.end);
|
|
1345
|
-
}
|
|
1346
|
-
}
|
|
1347
|
-
return output;
|
|
1348
|
-
}
|
|
1349
|
-
function parseHtmlx(htmlx, options) {
|
|
1350
|
-
//Svelte tries to parse style and script tags which doesn't play well with typescript, so we blank them out.
|
|
1351
|
-
//HTMLx spec says they should just be retained after processing as is, so this is fine
|
|
1352
|
-
const verbatimElements = findVerbatimElements(htmlx, options === null || options === void 0 ? void 0 : options.useNewTransformation);
|
|
1353
|
-
const deconstructed = blankVerbatimContent(htmlx, verbatimElements);
|
|
1354
|
-
//extract the html content parsed as htmlx this excludes our script and style tags
|
|
1355
|
-
const parsingCode = (options === null || options === void 0 ? void 0 : options.emitOnTemplateError)
|
|
1356
|
-
? blankPossiblyErrorOperatorOrPropertyAccess(deconstructed)
|
|
1357
|
-
: deconstructed;
|
|
1358
|
-
const htmlxAst = compiler.parse(parsingCode).html;
|
|
1359
|
-
//restore our script and style tags as nodes to maintain validity with HTMLx
|
|
1360
|
-
for (const s of verbatimElements) {
|
|
1361
|
-
htmlxAst.children.push(s);
|
|
1362
|
-
htmlxAst.start = Math.min(htmlxAst.start, s.start);
|
|
1363
|
-
htmlxAst.end = Math.max(htmlxAst.end, s.end);
|
|
1364
|
-
}
|
|
1365
|
-
return { htmlxAst, tags: verbatimElements };
|
|
1366
|
-
}
|
|
1367
|
-
const possibleOperatorOrPropertyAccess = new Set([
|
|
1368
|
-
'.',
|
|
1369
|
-
'?',
|
|
1370
|
-
'*',
|
|
1371
|
-
'~',
|
|
1372
|
-
'=',
|
|
1373
|
-
'<',
|
|
1374
|
-
'!',
|
|
1375
|
-
'&',
|
|
1376
|
-
'^',
|
|
1377
|
-
'|',
|
|
1378
|
-
',',
|
|
1379
|
-
'+',
|
|
1380
|
-
'-'
|
|
1381
|
-
]);
|
|
1382
|
-
function blankPossiblyErrorOperatorOrPropertyAccess(htmlx) {
|
|
1383
|
-
let index = htmlx.indexOf('}');
|
|
1384
|
-
let lastIndex = 0;
|
|
1385
|
-
const { length } = htmlx;
|
|
1386
|
-
while (index < length && index >= 0) {
|
|
1387
|
-
let backwardIndex = index - 1;
|
|
1388
|
-
while (backwardIndex > lastIndex) {
|
|
1389
|
-
const char = htmlx.charAt(backwardIndex);
|
|
1390
|
-
if (possibleOperatorOrPropertyAccess.has(char)) {
|
|
1391
|
-
const isPlusOrMinus = char === '+' || char === '-';
|
|
1392
|
-
const isIncrementOrDecrement = isPlusOrMinus && htmlx.charAt(backwardIndex - 1) === char;
|
|
1393
|
-
if (isIncrementOrDecrement) {
|
|
1394
|
-
backwardIndex -= 2;
|
|
1395
|
-
continue;
|
|
1396
|
-
}
|
|
1397
|
-
htmlx =
|
|
1398
|
-
htmlx.substring(0, backwardIndex) + ' ' + htmlx.substring(backwardIndex + 1);
|
|
1399
|
-
}
|
|
1400
|
-
else if (!/\s/.test(char)) {
|
|
1401
|
-
break;
|
|
1402
|
-
}
|
|
1403
|
-
backwardIndex--;
|
|
1404
|
-
}
|
|
1405
|
-
lastIndex = index;
|
|
1406
|
-
index = htmlx.indexOf('}', index + 1);
|
|
1407
|
-
}
|
|
1408
|
-
return htmlx;
|
|
1409
|
-
}
|
|
1410
|
-
|
|
1411
|
-
function isMember$1(parent, prop) {
|
|
1412
|
-
return parent.type == 'MemberExpression' && prop == 'property';
|
|
1413
|
-
}
|
|
1414
|
-
function isObjectKey(parent, prop) {
|
|
1415
|
-
return parent.type == 'Property' && prop == 'key';
|
|
1416
|
-
}
|
|
1417
|
-
function isObjectValue(parent, prop) {
|
|
1418
|
-
return parent.type == 'Property' && prop == 'value';
|
|
1419
|
-
}
|
|
1420
|
-
function isObjectValueShortHand(property) {
|
|
1421
|
-
const { value, key } = property;
|
|
1422
|
-
return value && isIdentifier(value) && key.start === value.start && key.end == value.end;
|
|
1423
|
-
}
|
|
1424
|
-
function attributeValueIsString(attr) {
|
|
1425
|
-
var _a;
|
|
1426
|
-
return attr.value.length !== 1 || ((_a = attr.value[0]) === null || _a === void 0 ? void 0 : _a.type) === 'Text';
|
|
1427
|
-
}
|
|
1428
|
-
function isDestructuringPatterns(node) {
|
|
1429
|
-
return node.type === 'ArrayPattern' || node.type === 'ObjectPattern';
|
|
1430
|
-
}
|
|
1431
|
-
function isIdentifier(node) {
|
|
1432
|
-
return node.type === 'Identifier';
|
|
1433
|
-
}
|
|
1434
|
-
function getSlotName(child) {
|
|
1435
|
-
var _a, _b;
|
|
1436
|
-
const slot = (_a = child.attributes) === null || _a === void 0 ? void 0 : _a.find((a) => a.name == 'slot');
|
|
1437
|
-
return (_b = slot === null || slot === void 0 ? void 0 : slot.value) === null || _b === void 0 ? void 0 : _b[0].raw;
|
|
1438
|
-
}
|
|
1439
|
-
|
|
1440
|
-
// @ts-check
|
|
1441
|
-
/** @typedef { import('estree').BaseNode} BaseNode */
|
|
1442
|
-
|
|
1443
|
-
/** @typedef {{
|
|
1444
|
-
skip: () => void;
|
|
1445
|
-
remove: () => void;
|
|
1446
|
-
replace: (node: BaseNode) => void;
|
|
1447
|
-
}} WalkerContext */
|
|
1448
|
-
|
|
1449
|
-
class WalkerBase {
|
|
1450
|
-
constructor() {
|
|
1451
|
-
/** @type {boolean} */
|
|
1452
|
-
this.should_skip = false;
|
|
1453
|
-
|
|
1454
|
-
/** @type {boolean} */
|
|
1455
|
-
this.should_remove = false;
|
|
1456
|
-
|
|
1457
|
-
/** @type {BaseNode | null} */
|
|
1458
|
-
this.replacement = null;
|
|
1459
|
-
|
|
1460
|
-
/** @type {WalkerContext} */
|
|
1461
|
-
this.context = {
|
|
1462
|
-
skip: () => (this.should_skip = true),
|
|
1463
|
-
remove: () => (this.should_remove = true),
|
|
1464
|
-
replace: (node) => (this.replacement = node)
|
|
1465
|
-
};
|
|
1466
|
-
}
|
|
1467
|
-
|
|
1468
|
-
/**
|
|
1469
|
-
*
|
|
1470
|
-
* @param {any} parent
|
|
1471
|
-
* @param {string} prop
|
|
1472
|
-
* @param {number} index
|
|
1473
|
-
* @param {BaseNode} node
|
|
1474
|
-
*/
|
|
1475
|
-
replace(parent, prop, index, node) {
|
|
1476
|
-
if (parent) {
|
|
1477
|
-
if (index !== null) {
|
|
1478
|
-
parent[prop][index] = node;
|
|
1479
|
-
} else {
|
|
1480
|
-
parent[prop] = node;
|
|
1481
|
-
}
|
|
1482
|
-
}
|
|
1483
|
-
}
|
|
1484
|
-
|
|
1485
|
-
/**
|
|
1486
|
-
*
|
|
1487
|
-
* @param {any} parent
|
|
1488
|
-
* @param {string} prop
|
|
1489
|
-
* @param {number} index
|
|
1490
|
-
*/
|
|
1491
|
-
remove(parent, prop, index) {
|
|
1492
|
-
if (parent) {
|
|
1493
|
-
if (index !== null) {
|
|
1494
|
-
parent[prop].splice(index, 1);
|
|
1495
|
-
} else {
|
|
1496
|
-
delete parent[prop];
|
|
1497
|
-
}
|
|
1498
|
-
}
|
|
1499
|
-
}
|
|
1500
|
-
}
|
|
1501
|
-
|
|
1502
|
-
// @ts-check
|
|
1503
|
-
|
|
1504
|
-
/** @typedef { import('estree').BaseNode} BaseNode */
|
|
1505
|
-
/** @typedef { import('./walker.js').WalkerContext} WalkerContext */
|
|
1506
|
-
|
|
1507
|
-
/** @typedef {(
|
|
1508
|
-
* this: WalkerContext,
|
|
1509
|
-
* node: BaseNode,
|
|
1510
|
-
* parent: BaseNode,
|
|
1511
|
-
* key: string,
|
|
1512
|
-
* index: number
|
|
1513
|
-
* ) => void} SyncHandler */
|
|
1514
|
-
|
|
1515
|
-
class SyncWalker extends WalkerBase {
|
|
1516
|
-
/**
|
|
1517
|
-
*
|
|
1518
|
-
* @param {SyncHandler} enter
|
|
1519
|
-
* @param {SyncHandler} leave
|
|
1520
|
-
*/
|
|
1521
|
-
constructor(enter, leave) {
|
|
1522
|
-
super();
|
|
1523
|
-
|
|
1524
|
-
/** @type {SyncHandler} */
|
|
1525
|
-
this.enter = enter;
|
|
1526
|
-
|
|
1527
|
-
/** @type {SyncHandler} */
|
|
1528
|
-
this.leave = leave;
|
|
1529
|
-
}
|
|
1530
|
-
|
|
1531
|
-
/**
|
|
1532
|
-
*
|
|
1533
|
-
* @param {BaseNode} node
|
|
1534
|
-
* @param {BaseNode} parent
|
|
1535
|
-
* @param {string} [prop]
|
|
1536
|
-
* @param {number} [index]
|
|
1537
|
-
* @returns {BaseNode}
|
|
1538
|
-
*/
|
|
1539
|
-
visit(node, parent, prop, index) {
|
|
1540
|
-
if (node) {
|
|
1541
|
-
if (this.enter) {
|
|
1542
|
-
const _should_skip = this.should_skip;
|
|
1543
|
-
const _should_remove = this.should_remove;
|
|
1544
|
-
const _replacement = this.replacement;
|
|
1545
|
-
this.should_skip = false;
|
|
1546
|
-
this.should_remove = false;
|
|
1547
|
-
this.replacement = null;
|
|
1548
|
-
|
|
1549
|
-
this.enter.call(this.context, node, parent, prop, index);
|
|
1550
|
-
|
|
1551
|
-
if (this.replacement) {
|
|
1552
|
-
node = this.replacement;
|
|
1553
|
-
this.replace(parent, prop, index, node);
|
|
1554
|
-
}
|
|
1555
|
-
|
|
1556
|
-
if (this.should_remove) {
|
|
1557
|
-
this.remove(parent, prop, index);
|
|
1558
|
-
}
|
|
1559
|
-
|
|
1560
|
-
const skipped = this.should_skip;
|
|
1561
|
-
const removed = this.should_remove;
|
|
1562
|
-
|
|
1563
|
-
this.should_skip = _should_skip;
|
|
1564
|
-
this.should_remove = _should_remove;
|
|
1565
|
-
this.replacement = _replacement;
|
|
1566
|
-
|
|
1567
|
-
if (skipped) return node;
|
|
1568
|
-
if (removed) return null;
|
|
1569
|
-
}
|
|
1570
|
-
|
|
1571
|
-
for (const key in node) {
|
|
1572
|
-
const value = node[key];
|
|
1573
|
-
|
|
1574
|
-
if (typeof value !== "object") {
|
|
1575
|
-
continue;
|
|
1576
|
-
} else if (Array.isArray(value)) {
|
|
1577
|
-
for (let i = 0; i < value.length; i += 1) {
|
|
1578
|
-
if (value[i] !== null && typeof value[i].type === 'string') {
|
|
1579
|
-
if (!this.visit(value[i], node, key, i)) {
|
|
1580
|
-
// removed
|
|
1581
|
-
i--;
|
|
1582
|
-
}
|
|
1583
|
-
}
|
|
1584
|
-
}
|
|
1585
|
-
} else if (value !== null && typeof value.type === "string") {
|
|
1586
|
-
this.visit(value, node, key, null);
|
|
1587
|
-
}
|
|
1588
|
-
}
|
|
1589
|
-
|
|
1590
|
-
if (this.leave) {
|
|
1591
|
-
const _replacement = this.replacement;
|
|
1592
|
-
const _should_remove = this.should_remove;
|
|
1593
|
-
this.replacement = null;
|
|
1594
|
-
this.should_remove = false;
|
|
1595
|
-
|
|
1596
|
-
this.leave.call(this.context, node, parent, prop, index);
|
|
1597
|
-
|
|
1598
|
-
if (this.replacement) {
|
|
1599
|
-
node = this.replacement;
|
|
1600
|
-
this.replace(parent, prop, index, node);
|
|
1601
|
-
}
|
|
1602
|
-
|
|
1603
|
-
if (this.should_remove) {
|
|
1604
|
-
this.remove(parent, prop, index);
|
|
1605
|
-
}
|
|
1606
|
-
|
|
1607
|
-
const removed = this.should_remove;
|
|
1608
|
-
|
|
1609
|
-
this.replacement = _replacement;
|
|
1610
|
-
this.should_remove = _should_remove;
|
|
1611
|
-
|
|
1612
|
-
if (removed) return null;
|
|
1613
|
-
}
|
|
1614
|
-
}
|
|
1615
|
-
|
|
1616
|
-
return node;
|
|
1617
|
-
}
|
|
1618
|
-
}
|
|
1619
|
-
|
|
1620
|
-
// @ts-check
|
|
1621
|
-
|
|
1622
|
-
/** @typedef { import('estree').BaseNode} BaseNode */
|
|
1623
|
-
/** @typedef { import('./sync.js').SyncHandler} SyncHandler */
|
|
1624
|
-
/** @typedef { import('./async.js').AsyncHandler} AsyncHandler */
|
|
1625
|
-
|
|
1626
|
-
/**
|
|
1627
|
-
*
|
|
1628
|
-
* @param {BaseNode} ast
|
|
1629
|
-
* @param {{
|
|
1630
|
-
* enter?: SyncHandler
|
|
1631
|
-
* leave?: SyncHandler
|
|
1632
|
-
* }} walker
|
|
1633
|
-
* @returns {BaseNode}
|
|
1634
|
-
*/
|
|
1635
|
-
function walk(ast, { enter, leave }) {
|
|
1636
|
-
const instance = new SyncWalker(enter, leave);
|
|
1637
|
-
return instance.visit(ast, null);
|
|
1638
|
-
}
|
|
1639
|
-
|
|
1640
|
-
const IGNORE_START_COMMENT = '/*Ωignore_startΩ*/';
|
|
1641
|
-
const IGNORE_END_COMMENT = '/*Ωignore_endΩ*/';
|
|
1642
|
-
/**
|
|
1643
|
-
* Surrounds given string with a start/end comment which marks it
|
|
1644
|
-
* to be ignored by tooling.
|
|
1645
|
-
*/
|
|
1646
|
-
function surroundWithIgnoreComments(str) {
|
|
1647
|
-
return IGNORE_START_COMMENT + str + IGNORE_END_COMMENT;
|
|
1648
|
-
}
|
|
1649
|
-
|
|
1650
|
-
/**
|
|
1651
|
-
* Get the constructor type of a component node
|
|
1652
|
-
* @param node The component node to infer the this type from
|
|
1653
|
-
* @param thisValue If node is svelte:component, you may pass the value
|
|
1654
|
-
* of this={..} to use that instead of the more general componentType
|
|
1655
|
-
*/
|
|
1656
|
-
function getTypeForComponent(node) {
|
|
1657
|
-
if (node.name === 'svelte:component' || node.name === 'svelte:self') {
|
|
1658
|
-
return '__sveltets_1_componentType()';
|
|
1659
|
-
}
|
|
1660
|
-
else {
|
|
1661
|
-
return node.name;
|
|
1662
|
-
}
|
|
1663
|
-
}
|
|
1664
|
-
/**
|
|
1665
|
-
* Get the instance type of a node from its constructor.
|
|
1666
|
-
*/
|
|
1667
|
-
function getInstanceTypeSimple(node, str) {
|
|
1668
|
-
const instanceOf = (str) => `__sveltets_2_instanceOf(${str})`;
|
|
1669
|
-
switch (node.type) {
|
|
1670
|
-
case 'InlineComponent':
|
|
1671
|
-
if (node.name === 'svelte:component' && node.expression) {
|
|
1672
|
-
const thisVal = str.original.substring(node.expression.start, node.expression.end);
|
|
1673
|
-
return `new (${thisVal})({target: __sveltets_2_any(''), props: __sveltets_2_any('')})`;
|
|
1674
|
-
}
|
|
1675
|
-
else if (node.name === 'svelte:component' || node.name === 'svelte:self') {
|
|
1676
|
-
return instanceOf('__sveltets_1_componentType()');
|
|
1677
|
-
}
|
|
1678
|
-
else {
|
|
1679
|
-
return `new ${node.name}({target: __sveltets_2_any(''), props: __sveltets_2_any('')})`;
|
|
1680
|
-
}
|
|
1681
|
-
case 'Element':
|
|
1682
|
-
return instanceOf(`__sveltets_1_ctorOf(__sveltets_1_mapElementTag('${node.name}'))`);
|
|
1683
|
-
case 'Body':
|
|
1684
|
-
return instanceOf('HTMLBodyElement');
|
|
1685
|
-
case 'Slot': // Web Components only
|
|
1686
|
-
return instanceOf('HTMLSlotElement');
|
|
1687
|
-
}
|
|
1688
|
-
}
|
|
1689
|
-
/**
|
|
1690
|
-
* Get the instance type of a node from its constructor.
|
|
1691
|
-
* If it's a component, pass in the exact props. This ensures that
|
|
1692
|
-
* the component instance has the right type in case of generic prop types.
|
|
1693
|
-
*/
|
|
1694
|
-
function getInstanceType(node, originalStr, replacedPropValues = []) {
|
|
1695
|
-
if (node.name === 'svelte:component' || node.name === 'svelte:self') {
|
|
1696
|
-
return '__sveltets_2_instanceOf(__sveltets_1_componentType())';
|
|
1697
|
-
}
|
|
1698
|
-
const propsStr = getNameValuePairsFromAttributes(node, originalStr)
|
|
1699
|
-
.map(({ name, value }) => {
|
|
1700
|
-
var _a;
|
|
1701
|
-
const replacedPropValue = (_a = replacedPropValues.find(({ name: propName }) => propName === name)) === null || _a === void 0 ? void 0 : _a.replacement;
|
|
1702
|
-
return `'${name}':${replacedPropValue || value}`;
|
|
1703
|
-
})
|
|
1704
|
-
.join(', ');
|
|
1705
|
-
return surroundWithIgnoreComments(`new ${node.name}({target: __sveltets_2_any(''), props: {${propsStr}}})`);
|
|
1706
|
-
}
|
|
1707
|
-
/**
|
|
1708
|
-
* Return a string which makes it possible for TypeScript to infer the instance type of the given component.
|
|
1709
|
-
* In the case of another component, this is done by creating a `new Comp({.. props: {..}})` code string.
|
|
1710
|
-
* Alongside with the result a list of shadowed props is returned. A shadowed prop is a prop
|
|
1711
|
-
* whose value is either too complex to analyse or contains an identifier which has the same name
|
|
1712
|
-
* as a `let:X` expression on the component. In that case, the returned string only contains a reference
|
|
1713
|
-
* to a constant which is `replacedPropsPrefix + propName`, so the calling code needs to make sure
|
|
1714
|
-
* to create such a `const`.
|
|
1715
|
-
*/
|
|
1716
|
-
function getInstanceTypeForDefaultSlot(node, originalStr, replacedPropsPrefix) {
|
|
1717
|
-
if (node.name === 'svelte:component' || node.name === 'svelte:self') {
|
|
1718
|
-
return {
|
|
1719
|
-
str: '__sveltets_2_instanceOf(__sveltets_1_componentType())',
|
|
1720
|
-
shadowedProps: []
|
|
1721
|
-
};
|
|
1722
|
-
}
|
|
1723
|
-
const lets = new Set((node.attributes || []).filter((attr) => attr.type === 'Let').map((attr) => attr.name));
|
|
1724
|
-
const shadowedProps = [];
|
|
1725
|
-
// Go through attribute values and mark those for reassignment to a const that
|
|
1726
|
-
// either definitely shadow a let: or where it cannot be determined because the value is too complex.
|
|
1727
|
-
const propsStr = getNameValuePairsFromAttributes(node, originalStr)
|
|
1728
|
-
.map(({ name, value, identifier, complexExpression }) => {
|
|
1729
|
-
if (complexExpression || lets.has(identifier)) {
|
|
1730
|
-
const replacement = replacedPropsPrefix + sanitizePropName$1(name);
|
|
1731
|
-
shadowedProps.push({ name, value, replacement });
|
|
1732
|
-
return `'${name}':${replacement}`;
|
|
1733
|
-
}
|
|
1734
|
-
else {
|
|
1735
|
-
return `'${name}':${value}`;
|
|
1736
|
-
}
|
|
1737
|
-
})
|
|
1738
|
-
.join(', ');
|
|
1739
|
-
const str = surroundWithIgnoreComments(`new ${node.name}({target: __sveltets_2_any(''), props: {${propsStr}}})`);
|
|
1740
|
-
return { str, shadowedProps };
|
|
1741
|
-
}
|
|
1742
|
-
function getNameValuePairsFromAttributes(node, originalStr) {
|
|
1743
|
-
return (node.attributes || [])
|
|
1744
|
-
.filter((attr) => attr.type === 'Attribute' && !attr.name.startsWith('--'))
|
|
1745
|
-
.map((attr) => {
|
|
1746
|
-
const name = attr.name;
|
|
1747
|
-
if (attr.value === true) {
|
|
1748
|
-
return { name, value: 'true' };
|
|
1749
|
-
}
|
|
1750
|
-
if (attr.value.length === 1) {
|
|
1751
|
-
const val = attr.value[0];
|
|
1752
|
-
if (val.type === 'AttributeShorthand') {
|
|
1753
|
-
return { name, value: name, identifier: name };
|
|
1754
|
-
}
|
|
1755
|
-
if (val.type === 'Text') {
|
|
1756
|
-
const quote = ['"', "'"].includes(originalStr[val.start - 1])
|
|
1757
|
-
? originalStr[val.start - 1]
|
|
1758
|
-
: "'";
|
|
1759
|
-
return { name, value: `${quote}${val.data || val.raw}${quote}` };
|
|
1760
|
-
}
|
|
1761
|
-
if (val.type === 'MustacheTag') {
|
|
1762
|
-
const valueStr = originalStr.substring(val.start + 1, val.end - 1);
|
|
1763
|
-
if (val.expression.type === 'Identifier') {
|
|
1764
|
-
return { name, value: valueStr, identifier: valueStr };
|
|
1765
|
-
}
|
|
1766
|
-
if (val.expression.type === 'Literal') {
|
|
1767
|
-
const value = typeof val.expression.value === 'string'
|
|
1768
|
-
? val.expression.raw
|
|
1769
|
-
: val.expression.value;
|
|
1770
|
-
return { name, value };
|
|
1771
|
-
}
|
|
1772
|
-
return { name, value: valueStr, complexExpression: true };
|
|
1773
|
-
}
|
|
1774
|
-
}
|
|
1775
|
-
if (!attr.value.length) {
|
|
1776
|
-
return { name, value: '""' };
|
|
1777
|
-
}
|
|
1778
|
-
const value = attr.value
|
|
1779
|
-
.map((val) => val.type === 'Text'
|
|
1780
|
-
? val.raw
|
|
1781
|
-
: val.type === 'MustacheTag'
|
|
1782
|
-
? '$' + originalStr.substring(val.start, val.end)
|
|
1783
|
-
: '')
|
|
1784
|
-
.join('');
|
|
1785
|
-
return { name, value: `\`${value}\`` };
|
|
1786
|
-
});
|
|
1787
|
-
}
|
|
1788
|
-
function sanitizePropName$1(name) {
|
|
1789
|
-
return name
|
|
1790
|
-
.split('')
|
|
1791
|
-
.map((char) => (/[0-9A-Za-z$_]/.test(char) ? char : '_'))
|
|
1792
|
-
.join('');
|
|
1793
|
-
}
|
|
1794
|
-
function beforeStart(start) {
|
|
1795
|
-
return start - 1;
|
|
1796
|
-
}
|
|
1797
|
-
function isShortHandAttribute(attr) {
|
|
1798
|
-
return attr.expression.end === attr.end;
|
|
1799
|
-
}
|
|
1800
|
-
function isQuote(str) {
|
|
1801
|
-
return str === '"' || str === "'";
|
|
1802
|
-
}
|
|
1803
|
-
function getIdentifiersInIfExpression(expression) {
|
|
1804
|
-
const offset = expression.start;
|
|
1805
|
-
const identifiers = new Map();
|
|
1806
|
-
walk(expression, {
|
|
1807
|
-
enter: (node, parent) => {
|
|
1808
|
-
switch (node.type) {
|
|
1809
|
-
case 'Identifier':
|
|
1810
|
-
// parent.property === node => node is "prop" in "obj.prop"
|
|
1811
|
-
// parent.callee === node => node is "fun" in "fun(..)"
|
|
1812
|
-
if ((parent === null || parent === void 0 ? void 0 : parent.property) !== node && (parent === null || parent === void 0 ? void 0 : parent.callee) !== node) {
|
|
1813
|
-
add(node);
|
|
1814
|
-
}
|
|
1815
|
-
break;
|
|
1816
|
-
}
|
|
1817
|
-
}
|
|
1818
|
-
});
|
|
1819
|
-
function add(node) {
|
|
1820
|
-
let entry = identifiers.get(node.name);
|
|
1821
|
-
if (!entry) {
|
|
1822
|
-
entry = [];
|
|
1823
|
-
}
|
|
1824
|
-
entry.push({ start: node.start - offset, end: node.end - offset });
|
|
1825
|
-
identifiers.set(node.name, entry);
|
|
1826
|
-
}
|
|
1827
|
-
return identifiers;
|
|
1828
|
-
}
|
|
1829
|
-
function usesLet(node) {
|
|
1830
|
-
var _a;
|
|
1831
|
-
return (_a = node.attributes) === null || _a === void 0 ? void 0 : _a.some((attr) => attr.type === 'Let');
|
|
1832
|
-
}
|
|
1833
|
-
function buildTemplateString(attr, str, htmlx, leadingOverride, trailingOverride, overrideStart) {
|
|
1834
|
-
overrideStart = overrideStart !== null && overrideStart !== void 0 ? overrideStart : htmlx.lastIndexOf('=', attr.value[0].start);
|
|
1835
|
-
str.overwrite(overrideStart, attr.value[0].start, leadingOverride);
|
|
1836
|
-
for (const n of attr.value) {
|
|
1837
|
-
if (n.type == 'MustacheTag') {
|
|
1838
|
-
str.appendRight(n.start, '$');
|
|
1839
|
-
}
|
|
1840
|
-
}
|
|
1841
|
-
if (isQuote(htmlx[attr.end - 1])) {
|
|
1842
|
-
str.overwrite(attr.end - 1, attr.end, trailingOverride);
|
|
1843
|
-
}
|
|
1844
|
-
else {
|
|
1845
|
-
str.appendLeft(attr.end, trailingOverride);
|
|
1846
|
-
}
|
|
1847
|
-
}
|
|
1848
|
-
/**
|
|
1849
|
-
* Check if there's a member access trailing behind given expression and if yes,
|
|
1850
|
-
* bump the position to include it.
|
|
1851
|
-
* Usually it's there because of the preprocessing we do before we let Svelte parse the template.
|
|
1852
|
-
*/
|
|
1853
|
-
function withTrailingPropertyAccess$1(originalText, position) {
|
|
1854
|
-
let index = position;
|
|
1855
|
-
while (index < originalText.length) {
|
|
1856
|
-
const char = originalText[index];
|
|
1857
|
-
if (!char.trim()) {
|
|
1858
|
-
index++;
|
|
1859
|
-
continue;
|
|
1860
|
-
}
|
|
1861
|
-
if (char === '.') {
|
|
1862
|
-
return index + 1;
|
|
1863
|
-
}
|
|
1864
|
-
if (char === '?' && originalText[index + 1] === '.') {
|
|
1865
|
-
return index + 2;
|
|
1866
|
-
}
|
|
1867
|
-
break;
|
|
1868
|
-
}
|
|
1869
|
-
return position;
|
|
1870
|
-
}
|
|
1871
|
-
|
|
1872
|
-
/**
|
|
1873
|
-
* use:xxx={params} ---> {...__sveltets_1_ensureAction(xxx(__sveltets_1_mapElementTag('ParentNodeName'),(params)))}
|
|
1874
|
-
*/
|
|
1875
|
-
function handleActionDirective$1(htmlx, str, attr, parent) {
|
|
1876
|
-
str.overwrite(attr.start, attr.start + 'use:'.length, '{...__sveltets_1_ensureAction(');
|
|
1877
|
-
const name = parent.name === 'svelte:body' ? 'body' : parent.name;
|
|
1878
|
-
if (!attr.expression) {
|
|
1879
|
-
str.appendLeft(attr.end, `(__sveltets_1_mapElementTag('${name}')))}`);
|
|
1880
|
-
return;
|
|
1881
|
-
}
|
|
1882
|
-
str.overwrite(attr.start + `use:${attr.name}`.length, attr.expression.start, `(__sveltets_1_mapElementTag('${name}'),(`);
|
|
1883
|
-
str.appendLeft(withTrailingPropertyAccess$1(str.original, attr.expression.end), ')))');
|
|
1884
|
-
const lastChar = htmlx[attr.end - 1];
|
|
1885
|
-
if (isQuote(lastChar)) {
|
|
1886
|
-
str.remove(attr.end - 1, attr.end);
|
|
1887
|
-
}
|
|
1888
|
-
}
|
|
1889
|
-
|
|
1890
|
-
/**
|
|
1891
|
-
* animate:xxx(yyy) ---> {...__sveltets_1_ensureAnimation(xxx(__sveltets_1_mapElementTag('..'),__sveltets_1_AnimationMove,(yyy)))}
|
|
1892
|
-
*/
|
|
1893
|
-
function handleAnimateDirective$1(htmlx, str, attr, parent) {
|
|
1894
|
-
str.overwrite(attr.start, htmlx.indexOf(':', attr.start) + 1, '{...__sveltets_1_ensureAnimation(');
|
|
1895
|
-
const nodeType = `__sveltets_1_mapElementTag('${parent.name}')`;
|
|
1896
|
-
if (!attr.expression) {
|
|
1897
|
-
str.appendLeft(attr.end, `(${nodeType},__sveltets_1_AnimationMove,{}))}`);
|
|
1898
|
-
return;
|
|
1899
|
-
}
|
|
1900
|
-
str.overwrite(htmlx.indexOf(':', attr.start) + 1 + `${attr.name}`.length, attr.expression.start, `(${nodeType},__sveltets_1_AnimationMove,(`);
|
|
1901
|
-
str.appendLeft(withTrailingPropertyAccess$1(str.original, attr.expression.end), ')))');
|
|
1902
|
-
if (isQuote(htmlx[attr.end - 1])) {
|
|
1903
|
-
str.remove(attr.end - 1, attr.end);
|
|
1904
|
-
}
|
|
1905
|
-
}
|
|
1906
|
-
|
|
1907
|
-
var svgAttributes$1 = 'accent-height accumulate additive alignment-baseline allowReorder alphabetic amplitude arabic-form ascent attributeName attributeType autoReverse azimuth baseFrequency baseline-shift baseProfile bbox begin bias by calcMode cap-height class clip clipPathUnits clip-path clip-rule color color-interpolation color-interpolation-filters color-profile color-rendering contentScriptType contentStyleType cursor cx cy d decelerate descent diffuseConstant direction display divisor dominant-baseline dur dx dy edgeMode elevation enable-background end exponent externalResourcesRequired fill fill-opacity fill-rule filter filterRes filterUnits flood-color flood-opacity font-family font-size font-size-adjust font-stretch font-style font-variant font-weight format from fr fx fy g1 g2 glyph-name glyph-orientation-horizontal glyph-orientation-vertical glyphRef gradientTransform gradientUnits hanging height href horiz-adv-x horiz-origin-x id ideographic image-rendering in in2 intercept k k1 k2 k3 k4 kernelMatrix kernelUnitLength kerning keyPoints keySplines keyTimes lang lengthAdjust letter-spacing lighting-color limitingConeAngle local marker-end marker-mid marker-start markerHeight markerUnits markerWidth mask maskContentUnits maskUnits mathematical max media method min mode name numOctaves offset onabort onactivate onbegin onclick onend onerror onfocusin onfocusout onload onmousedown onmousemove onmouseout onmouseover onmouseup onrepeat onresize onscroll onunload opacity operator order orient orientation origin overflow overline-position overline-thickness panose-1 paint-order pathLength patternContentUnits patternTransform patternUnits pointer-events points pointsAtX pointsAtY pointsAtZ preserveAlpha preserveAspectRatio primitiveUnits r radius refX refY rendering-intent repeatCount repeatDur requiredExtensions requiredFeatures restart result rotate rx ry scale seed shape-rendering slope spacing specularConstant specularExponent speed spreadMethod startOffset stdDeviation stemh stemv stitchTiles stop-color stop-opacity strikethrough-position strikethrough-thickness string stroke stroke-dasharray stroke-dashoffset stroke-linecap stroke-linejoin stroke-miterlimit stroke-opacity stroke-width style surfaceScale systemLanguage tabindex tableValues target targetX targetY text-anchor text-decoration text-rendering textLength to transform type u1 u2 underline-position underline-thickness unicode unicode-bidi unicode-range units-per-em v-alphabetic v-hanging v-ideographic v-mathematical values version vert-adv-y vert-origin-x vert-origin-y viewBox viewTarget visibility width widths word-spacing writing-mode x x-height x1 x2 xChannelSelector xlink:actuate xlink:arcrole xlink:href xlink:role xlink:show xlink:title xlink:type xml:base xml:lang xml:space y y1 y2 yChannelSelector z zoomAndPan'.split(' ');
|
|
1908
|
-
|
|
1909
|
-
/**
|
|
1910
|
-
* List taken from `svelte-jsx.d.ts` by searching for all attributes of type number
|
|
1911
|
-
*/
|
|
1912
|
-
const numberOnlyAttributes$1 = new Set([
|
|
1913
|
-
'cols',
|
|
1914
|
-
'colspan',
|
|
1915
|
-
'currenttime',
|
|
1916
|
-
'defaultplaybackrate',
|
|
1917
|
-
'high',
|
|
1918
|
-
'low',
|
|
1919
|
-
'marginheight',
|
|
1920
|
-
'marginwidth',
|
|
1921
|
-
'minlength',
|
|
1922
|
-
'maxlength',
|
|
1923
|
-
'optimum',
|
|
1924
|
-
'rows',
|
|
1925
|
-
'rowspan',
|
|
1926
|
-
'size',
|
|
1927
|
-
'span',
|
|
1928
|
-
'start',
|
|
1929
|
-
'tabindex',
|
|
1930
|
-
'results',
|
|
1931
|
-
'volume'
|
|
1932
|
-
]);
|
|
1933
|
-
/**
|
|
1934
|
-
* Handle various kinds of attributes and make them conform to JSX.
|
|
1935
|
-
* - {x} ---> x={x}
|
|
1936
|
-
* - x="{..}" ---> x={..}
|
|
1937
|
-
* - lowercase DOM attributes
|
|
1938
|
-
* - multi-value handling
|
|
1939
|
-
*/
|
|
1940
|
-
function handleAttribute$1(htmlx, str, attr, parent, preserveCase) {
|
|
1941
|
-
var _a, _b, _c;
|
|
1942
|
-
const shouldApplySlotCheck = parent.type === 'Slot' && attr.name !== 'name';
|
|
1943
|
-
const slotName = shouldApplySlotCheck
|
|
1944
|
-
? ((_c = (_b = (_a = parent.attributes) === null || _a === void 0 ? void 0 : _a.find((a) => a.name === 'name')) === null || _b === void 0 ? void 0 : _b.value[0]) === null || _c === void 0 ? void 0 : _c.data) || 'default'
|
|
1945
|
-
: undefined;
|
|
1946
|
-
const ensureSlotStr = `__sveltets_ensureSlot("${slotName}","${attr.name}",`;
|
|
1947
|
-
let transformedFromDirectiveOrNamespace = false;
|
|
1948
|
-
const transformAttributeCase = (name) => {
|
|
1949
|
-
if (!preserveCase && !svgAttributes$1.find((x) => x == name)) {
|
|
1950
|
-
return name.toLowerCase();
|
|
1951
|
-
}
|
|
1952
|
-
else {
|
|
1953
|
-
return name;
|
|
1954
|
-
}
|
|
1955
|
-
};
|
|
1956
|
-
//if we are on an "element" we are case insensitive, lowercase to match our JSX
|
|
1957
|
-
if (parent.type == 'Element') {
|
|
1958
|
-
const sapperLinkActions = ['sapper:prefetch', 'sapper:noscroll'];
|
|
1959
|
-
const sveltekitLinkActions = [
|
|
1960
|
-
'data-sveltekit-preload-code',
|
|
1961
|
-
'data-sveltekit-preload-data',
|
|
1962
|
-
'data-sveltekit-noscroll',
|
|
1963
|
-
'data-sveltekit-reload'
|
|
1964
|
-
];
|
|
1965
|
-
// skip Attribute shorthand, that is handled below
|
|
1966
|
-
if ((attr.value !== true &&
|
|
1967
|
-
!(attr.value.length &&
|
|
1968
|
-
attr.value.length == 1 &&
|
|
1969
|
-
attr.value[0].type == 'AttributeShorthand')) ||
|
|
1970
|
-
sapperLinkActions.includes(attr.name) ||
|
|
1971
|
-
sveltekitLinkActions.includes(attr.name)) {
|
|
1972
|
-
let name = transformAttributeCase(attr.name);
|
|
1973
|
-
//strip ":" from out attribute name and uppercase the next letter to convert to jsx attribute
|
|
1974
|
-
const colonIndex = name.indexOf(':');
|
|
1975
|
-
if (colonIndex >= 0) {
|
|
1976
|
-
const parts = name.split(':');
|
|
1977
|
-
name = parts[0] + parts[1][0].toUpperCase() + parts[1].substring(1);
|
|
1978
|
-
}
|
|
1979
|
-
str.overwrite(attr.start, attr.start + attr.name.length, name);
|
|
1980
|
-
transformedFromDirectiveOrNamespace = true;
|
|
1981
|
-
}
|
|
1982
|
-
}
|
|
1983
|
-
// Custom CSS property
|
|
1984
|
-
if (parent.type === 'InlineComponent' && attr.name.startsWith('--') && attr.value !== true) {
|
|
1985
|
-
str.prependRight(attr.start, '{...__sveltets_1_cssProp({"');
|
|
1986
|
-
buildTemplateString(attr, str, htmlx, '": `', '`})}');
|
|
1987
|
-
return;
|
|
1988
|
-
}
|
|
1989
|
-
//we are a bare attribute
|
|
1990
|
-
if (attr.value === true) {
|
|
1991
|
-
if (parent.type === 'Element' &&
|
|
1992
|
-
!transformedFromDirectiveOrNamespace &&
|
|
1993
|
-
parent.name !== '!DOCTYPE') {
|
|
1994
|
-
str.overwrite(attr.start, attr.end, transformAttributeCase(attr.name));
|
|
1995
|
-
}
|
|
1996
|
-
return;
|
|
1997
|
-
}
|
|
1998
|
-
if (attr.value.length == 0) {
|
|
1999
|
-
return; //wut?
|
|
2000
|
-
}
|
|
2001
|
-
//handle single value
|
|
2002
|
-
if (attr.value.length == 1) {
|
|
2003
|
-
const attrVal = attr.value[0];
|
|
2004
|
-
if (attr.name == 'slot') {
|
|
2005
|
-
str.remove(attr.start, attr.end);
|
|
2006
|
-
return;
|
|
2007
|
-
}
|
|
2008
|
-
if (attrVal.type == 'AttributeShorthand') {
|
|
2009
|
-
let attrName = attrVal.expression.name;
|
|
2010
|
-
if (parent.type == 'Element') {
|
|
2011
|
-
attrName = transformAttributeCase(attrName);
|
|
2012
|
-
}
|
|
2013
|
-
str.appendRight(attr.start, `${attrName}=`);
|
|
2014
|
-
if (shouldApplySlotCheck) {
|
|
2015
|
-
str.prependRight(attr.start + 1, ensureSlotStr);
|
|
2016
|
-
str.prependLeft(attr.end - 1, ')');
|
|
2017
|
-
}
|
|
2018
|
-
return;
|
|
2019
|
-
}
|
|
2020
|
-
const equals = htmlx.lastIndexOf('=', attrVal.start);
|
|
2021
|
-
const sanitizedName = sanitizeLeadingChars(attr.name);
|
|
2022
|
-
if (sanitizedName !== attr.name) {
|
|
2023
|
-
str.overwrite(attr.start, equals, sanitizedName);
|
|
2024
|
-
}
|
|
2025
|
-
if (attrVal.type == 'Text') {
|
|
2026
|
-
const endsWithQuote = htmlx.lastIndexOf('"', attrVal.end) === attrVal.end - 1 ||
|
|
2027
|
-
htmlx.lastIndexOf("'", attrVal.end) === attrVal.end - 1;
|
|
2028
|
-
const needsQuotes = attrVal.end == attr.end && !endsWithQuote;
|
|
2029
|
-
const hasBrackets = htmlx.lastIndexOf('}', attrVal.end) === attrVal.end - 1 ||
|
|
2030
|
-
htmlx.lastIndexOf('}"', attrVal.end) === attrVal.end - 1 ||
|
|
2031
|
-
htmlx.lastIndexOf("}'", attrVal.end) === attrVal.end - 1;
|
|
2032
|
-
const needsNumberConversion = !hasBrackets &&
|
|
2033
|
-
parent.type === 'Element' &&
|
|
2034
|
-
numberOnlyAttributes$1.has(attr.name.toLowerCase()) &&
|
|
2035
|
-
!isNaN(attrVal.data);
|
|
2036
|
-
if (needsNumberConversion) {
|
|
2037
|
-
const begin = '{' + (shouldApplySlotCheck ? ensureSlotStr : '');
|
|
2038
|
-
const end = shouldApplySlotCheck ? ')}' : '}';
|
|
2039
|
-
if (needsQuotes) {
|
|
2040
|
-
str.prependRight(equals + 1, begin);
|
|
2041
|
-
str.appendLeft(attr.end, end);
|
|
2042
|
-
}
|
|
2043
|
-
else {
|
|
2044
|
-
str.overwrite(equals + 1, equals + 2, begin);
|
|
2045
|
-
str.overwrite(attr.end - 1, attr.end, end);
|
|
2046
|
-
}
|
|
2047
|
-
}
|
|
2048
|
-
else if (needsQuotes) {
|
|
2049
|
-
const begin = shouldApplySlotCheck ? `{${ensureSlotStr}"` : '"';
|
|
2050
|
-
const end = shouldApplySlotCheck ? '")}' : '"';
|
|
2051
|
-
str.prependRight(equals + 1, begin);
|
|
2052
|
-
str.appendLeft(attr.end, end);
|
|
2053
|
-
}
|
|
2054
|
-
else if (shouldApplySlotCheck) {
|
|
2055
|
-
str.prependRight(equals + 1, `{${ensureSlotStr}`);
|
|
2056
|
-
str.appendLeft(attr.end, ')}');
|
|
2057
|
-
}
|
|
2058
|
-
return;
|
|
2059
|
-
}
|
|
2060
|
-
if (attrVal.type == 'MustacheTag') {
|
|
2061
|
-
const isInQuotes = attrVal.end != attr.end;
|
|
2062
|
-
//if the end doesn't line up, we are wrapped in quotes
|
|
2063
|
-
if (isInQuotes) {
|
|
2064
|
-
str.remove(attrVal.start - 1, attrVal.start);
|
|
2065
|
-
str.remove(attr.end - 1, attr.end);
|
|
2066
|
-
}
|
|
2067
|
-
if (shouldApplySlotCheck) {
|
|
2068
|
-
str.prependRight(attrVal.start + 1, ensureSlotStr);
|
|
2069
|
-
str.appendLeft(attr.end - (isInQuotes ? 2 : 1), ')');
|
|
2070
|
-
}
|
|
2071
|
-
return;
|
|
2072
|
-
}
|
|
2073
|
-
return;
|
|
2074
|
-
}
|
|
2075
|
-
// We have multiple attribute values, so we build a template string out of them.
|
|
2076
|
-
buildTemplateString(attr, str, htmlx, shouldApplySlotCheck ? `={${ensureSlotStr}\`` : '={`', shouldApplySlotCheck ? '`)}' : '`}');
|
|
2077
|
-
}
|
|
2078
|
-
function sanitizeLeadingChars(attrName) {
|
|
2079
|
-
let sanitizedName = '';
|
|
2080
|
-
for (let i = 0; i < attrName.length; i++) {
|
|
2081
|
-
if (/[A-Za-z$_]/.test(attrName[i])) {
|
|
2082
|
-
sanitizedName += attrName.substr(i);
|
|
2083
|
-
return sanitizedName;
|
|
2084
|
-
}
|
|
2085
|
-
else {
|
|
2086
|
-
sanitizedName += '_';
|
|
2087
|
-
}
|
|
2088
|
-
}
|
|
2089
|
-
return sanitizedName;
|
|
2090
|
-
}
|
|
2091
|
-
|
|
2092
|
-
function extractConstTags(children) {
|
|
2093
|
-
const tags = [];
|
|
2094
|
-
for (const child of children) {
|
|
2095
|
-
if (child.type === 'ConstTag') {
|
|
2096
|
-
const constTag = child;
|
|
2097
|
-
tags.push((insertionPoint, str) => {
|
|
2098
|
-
str.appendRight(constTag.expression.left.start, 'const ');
|
|
2099
|
-
const expressionEnd = withTrailingPropertyAccess$1(str.original, constTag.expression.right.end);
|
|
2100
|
-
str.move(constTag.expression.left.start, expressionEnd, insertionPoint);
|
|
2101
|
-
str.appendLeft(expressionEnd, ';');
|
|
2102
|
-
str.overwrite(constTag.start + 1, constTag.expression.left.start - 1, '', {
|
|
2103
|
-
contentOnly: true
|
|
2104
|
-
});
|
|
2105
|
-
});
|
|
2106
|
-
}
|
|
2107
|
-
}
|
|
2108
|
-
return tags;
|
|
2109
|
-
}
|
|
2110
|
-
|
|
2111
|
-
/**
|
|
2112
|
-
* Transform {#await ...} into something JSX understands
|
|
2113
|
-
*/
|
|
2114
|
-
function handleAwait$1(htmlx, str, awaitBlock, ifScope, templateScopeManager) {
|
|
2115
|
-
// {#await somePromise then value} ->
|
|
2116
|
-
// {() => {let _$$p = (somePromise);
|
|
2117
|
-
let ifCondition = ifScope.getFullCondition();
|
|
2118
|
-
ifCondition = ifCondition ? surroundWithIgnoreComments(`if(${ifCondition}) {`) : '';
|
|
2119
|
-
templateScopeManager.awaitEnter(awaitBlock);
|
|
2120
|
-
const constRedeclares = ifScope.getConstDeclaration();
|
|
2121
|
-
str.overwrite(awaitBlock.start, awaitBlock.expression.start, `{() => {${constRedeclares}${ifCondition}let _$$p = (`);
|
|
2122
|
-
// {/await} ->
|
|
2123
|
-
// <>})}
|
|
2124
|
-
const awaitEndStart = htmlx.lastIndexOf('{', awaitBlock.end - 1);
|
|
2125
|
-
str.overwrite(awaitEndStart, awaitBlock.end, '</>})}}' + (ifCondition ? '}' : ''));
|
|
2126
|
-
}
|
|
2127
|
-
function handleAwaitPending(awaitBlock, htmlx, str, ifScope) {
|
|
2128
|
-
if (awaitBlock.pending.skip) {
|
|
2129
|
-
return;
|
|
2130
|
-
}
|
|
2131
|
-
// {await aPromise} ... -> aPromise); (possibleIfCondition &&)<> ... </>
|
|
2132
|
-
const pendingStart = htmlx.indexOf('}', awaitBlock.expression.end);
|
|
2133
|
-
const pendingEnd = !awaitBlock.then.skip
|
|
2134
|
-
? awaitBlock.then.start
|
|
2135
|
-
: !awaitBlock.catch.skip
|
|
2136
|
-
? awaitBlock.catch.start
|
|
2137
|
-
: htmlx.lastIndexOf('{', awaitBlock.end);
|
|
2138
|
-
str.overwrite(withTrailingPropertyAccess$1(str.original, awaitBlock.expression.end), pendingStart + 1, ');');
|
|
2139
|
-
str.appendRight(pendingStart + 1, ` ${ifScope.addPossibleIfCondition()}<>`);
|
|
2140
|
-
str.appendLeft(pendingEnd, '</>; ');
|
|
2141
|
-
if (!awaitBlock.then.skip) {
|
|
2142
|
-
return;
|
|
2143
|
-
}
|
|
2144
|
-
// no need to prepend ifcondition here as we know the then block is empty
|
|
2145
|
-
str.appendLeft(pendingEnd, '__sveltets_1_awaitThen(_$$p, () => {<>');
|
|
2146
|
-
}
|
|
2147
|
-
function handleAwaitThen(awaitBlock, htmlx, str, ifScope) {
|
|
2148
|
-
if (awaitBlock.then.skip) {
|
|
2149
|
-
return;
|
|
2150
|
-
}
|
|
2151
|
-
// then value } | then} | {:then value} | {await ..} .. {/await} ->
|
|
2152
|
-
// __sveltets_1_awaitThen(_$$p, (value) => {(possibleIfCondition && )<>
|
|
2153
|
-
let thenStart;
|
|
2154
|
-
let thenEnd;
|
|
2155
|
-
// then value } | {:then value}
|
|
2156
|
-
if (!awaitBlock.pending.skip) {
|
|
2157
|
-
// {await ...} ... {:then ...}
|
|
2158
|
-
// thenBlock includes the {:then}
|
|
2159
|
-
thenStart = awaitBlock.then.start;
|
|
2160
|
-
if (awaitBlock.value) {
|
|
2161
|
-
thenEnd = htmlx.indexOf('}', awaitBlock.value.end) + 1;
|
|
2162
|
-
}
|
|
2163
|
-
else {
|
|
2164
|
-
thenEnd = htmlx.indexOf('}', awaitBlock.then.start) + 1;
|
|
2165
|
-
}
|
|
2166
|
-
}
|
|
2167
|
-
else {
|
|
2168
|
-
// {await ... then ...}
|
|
2169
|
-
thenStart = htmlx.indexOf('then', awaitBlock.expression.end);
|
|
2170
|
-
thenEnd = htmlx.lastIndexOf('}', awaitBlock.then.start) + 1;
|
|
2171
|
-
// somePromise then -> somePromise); then
|
|
2172
|
-
str.overwrite(awaitBlock.expression.end, thenStart, '); ');
|
|
2173
|
-
}
|
|
2174
|
-
if (awaitBlock.value) {
|
|
2175
|
-
str.overwrite(thenStart, awaitBlock.value.start, '__sveltets_1_awaitThen(_$$p, (');
|
|
2176
|
-
str.overwrite(awaitBlock.value.end, thenEnd, ') => {');
|
|
2177
|
-
extractConstTags(awaitBlock.then.children).forEach((insertion) => {
|
|
2178
|
-
insertion(thenEnd, str);
|
|
2179
|
-
});
|
|
2180
|
-
str.appendRight(thenEnd, `${ifScope.addPossibleIfCondition()}<>`);
|
|
2181
|
-
}
|
|
2182
|
-
else {
|
|
2183
|
-
const awaitThenFn = '__sveltets_1_awaitThen(_$$p, () => {';
|
|
2184
|
-
if (thenStart === thenEnd) {
|
|
2185
|
-
str.appendLeft(thenStart, awaitThenFn);
|
|
2186
|
-
}
|
|
2187
|
-
else {
|
|
2188
|
-
str.overwrite(thenStart, thenEnd, awaitThenFn);
|
|
2189
|
-
}
|
|
2190
|
-
extractConstTags(awaitBlock.then.children).forEach((insertion) => {
|
|
2191
|
-
insertion(thenEnd, str);
|
|
2192
|
-
});
|
|
2193
|
-
str.appendRight(thenEnd, `${ifScope.addPossibleIfCondition()}<>`);
|
|
2194
|
-
}
|
|
2195
|
-
}
|
|
2196
|
-
function handleAwaitCatch(awaitBlock, htmlx, str, ifScope) {
|
|
2197
|
-
if (awaitBlock.catch.skip) {
|
|
2198
|
-
return;
|
|
2199
|
-
}
|
|
2200
|
-
if (awaitBlock.pending.skip && awaitBlock.then.skip) {
|
|
2201
|
-
if (awaitBlock.error) {
|
|
2202
|
-
// {#await ... catch ...}
|
|
2203
|
-
const catchBegin = htmlx.indexOf('}', awaitBlock.error.end) + 1;
|
|
2204
|
-
str.overwrite(awaitBlock.expression.end, awaitBlock.error.start, '); __sveltets_1_awaitThen(_$$p, () => {}, (');
|
|
2205
|
-
str.overwrite(awaitBlock.error.end, catchBegin, ') => {');
|
|
2206
|
-
extractConstTags(awaitBlock.catch.children).forEach((insertion) => {
|
|
2207
|
-
insertion(catchBegin, str);
|
|
2208
|
-
});
|
|
2209
|
-
str.appendRight(catchBegin, '<>');
|
|
2210
|
-
}
|
|
2211
|
-
else {
|
|
2212
|
-
// {#await ... catch}
|
|
2213
|
-
const catchBegin = htmlx.indexOf('}', awaitBlock.expression.end) + 1;
|
|
2214
|
-
str.overwrite(awaitBlock.expression.end, catchBegin, '); __sveltets_1_awaitThen(_$$p, () => {}, () => {');
|
|
2215
|
-
extractConstTags(awaitBlock.catch.children).forEach((insertion) => {
|
|
2216
|
-
insertion(catchBegin, str);
|
|
2217
|
-
});
|
|
2218
|
-
str.appendRight(catchBegin, '<>');
|
|
2219
|
-
}
|
|
2220
|
-
}
|
|
2221
|
-
else {
|
|
2222
|
-
//{:catch error} ->
|
|
2223
|
-
//</>}, (error) => {<>
|
|
2224
|
-
//catch block includes the {:catch}
|
|
2225
|
-
const catchStart = awaitBlock.catch.start;
|
|
2226
|
-
const catchSymbolEnd = htmlx.indexOf(':catch', catchStart) + ':catch'.length;
|
|
2227
|
-
const errorStart = awaitBlock.error ? awaitBlock.error.start : catchSymbolEnd;
|
|
2228
|
-
const errorEnd = awaitBlock.error ? awaitBlock.error.end : errorStart;
|
|
2229
|
-
const catchEnd = htmlx.indexOf('}', errorEnd) + 1;
|
|
2230
|
-
str.overwrite(catchStart, errorStart, '</>}, (');
|
|
2231
|
-
str.overwrite(errorEnd, catchEnd, ') => {');
|
|
2232
|
-
extractConstTags(awaitBlock.catch.children).forEach((insertion) => {
|
|
2233
|
-
insertion(catchEnd, str);
|
|
2234
|
-
});
|
|
2235
|
-
str.appendRight(catchEnd, `${ifScope.addPossibleIfCondition()}<>`);
|
|
2236
|
-
}
|
|
2237
|
-
}
|
|
2238
|
-
|
|
2239
|
-
const oneWayBindingAttributes$1 = new Map(['clientWidth', 'clientHeight', 'offsetWidth', 'offsetHeight']
|
|
2240
|
-
.map((e) => [e, 'HTMLDivElement'])
|
|
2241
|
-
.concat(['duration', 'buffered', 'seekable', 'seeking', 'played', 'ended'].map((e) => [
|
|
2242
|
-
e,
|
|
2243
|
-
'HTMLMediaElement'
|
|
2244
|
-
])));
|
|
2245
|
-
/**
|
|
2246
|
-
* List of all binding names that are transformed to sth like `binding = variable`.
|
|
2247
|
-
* This applies to readonly bindings and the this binding.
|
|
2248
|
-
*/
|
|
2249
|
-
new Set([...oneWayBindingAttributes$1.keys(), 'this']);
|
|
2250
|
-
/**
|
|
2251
|
-
* Transform bind:xxx into something that conforms to JSX
|
|
2252
|
-
*/
|
|
2253
|
-
function handleBinding$1(htmlx, str, attr, el) {
|
|
2254
|
-
//bind group on input
|
|
2255
|
-
if (attr.name == 'group' && el.name == 'input') {
|
|
2256
|
-
str.remove(attr.start, attr.expression.start);
|
|
2257
|
-
str.appendLeft(attr.expression.start, '{...__sveltets_1_empty(');
|
|
2258
|
-
const endBrackets = ')}';
|
|
2259
|
-
if (isShortHandAttribute(attr)) {
|
|
2260
|
-
str.prependRight(attr.end, endBrackets);
|
|
2261
|
-
}
|
|
2262
|
-
else {
|
|
2263
|
-
str.overwrite(withTrailingPropertyAccess$1(str.original, attr.expression.end), attr.end, endBrackets);
|
|
2264
|
-
}
|
|
2265
|
-
return;
|
|
2266
|
-
}
|
|
2267
|
-
const supportsBindThis = [
|
|
2268
|
-
'InlineComponent',
|
|
2269
|
-
'Element',
|
|
2270
|
-
'Body',
|
|
2271
|
-
'Slot' // only valid for Web Components compile target
|
|
2272
|
-
];
|
|
2273
|
-
//bind this
|
|
2274
|
-
if (attr.name === 'this' && supportsBindThis.includes(el.type)) {
|
|
2275
|
-
// bind:this is effectively only works bottom up - the variable is updated by the element, not
|
|
2276
|
-
// the other way round. So we check if the instance is assignable to the variable.
|
|
2277
|
-
// Some notes:
|
|
2278
|
-
// - If the component unmounts (it's inside an if block, or svelte:component this={null},
|
|
2279
|
-
// the value becomes null, but we don't add it to the clause because it would introduce
|
|
2280
|
-
// worse DX for the 99% use case, and because null !== undefined which others might use to type the declaration.
|
|
2281
|
-
// - This doesn't do a 100% correct job of infering the instance type in case someone used generics for input props.
|
|
2282
|
-
// For now it errs on the side of "no false positives" at the cost of maybe some missed type bugs
|
|
2283
|
-
const thisType = getInstanceTypeSimple(el, str);
|
|
2284
|
-
if (thisType) {
|
|
2285
|
-
str.overwrite(attr.start, attr.expression.start, '{...__sveltets_1_empty(');
|
|
2286
|
-
const instanceOfThisAssignment = ' = ' + surroundWithIgnoreComments(thisType) + ')}';
|
|
2287
|
-
str.overwrite(attr.expression.end, attr.end, instanceOfThisAssignment);
|
|
2288
|
-
return;
|
|
2289
|
-
}
|
|
2290
|
-
}
|
|
2291
|
-
//one way binding
|
|
2292
|
-
if (oneWayBindingAttributes$1.has(attr.name) && el.type === 'Element') {
|
|
2293
|
-
str.remove(attr.start, attr.expression.start);
|
|
2294
|
-
str.appendLeft(attr.expression.start, '{...__sveltets_1_empty(');
|
|
2295
|
-
if (isShortHandAttribute(attr)) {
|
|
2296
|
-
str.appendLeft(attr.end, `=__sveltets_2_instanceOf(${oneWayBindingAttributes$1.get(attr.name)}).${attr.name})}`);
|
|
2297
|
-
}
|
|
2298
|
-
else {
|
|
2299
|
-
str.overwrite(attr.expression.end, attr.end, `=__sveltets_2_instanceOf(${oneWayBindingAttributes$1.get(attr.name)}).${attr.name})}`);
|
|
2300
|
-
}
|
|
2301
|
-
return;
|
|
2302
|
-
}
|
|
2303
|
-
str.remove(attr.start, attr.start + 'bind:'.length);
|
|
2304
|
-
if (attr.expression.start === attr.start + 'bind:'.length) {
|
|
2305
|
-
str.prependLeft(attr.expression.start, `${attr.name}={`);
|
|
2306
|
-
str.appendLeft(attr.end, '}');
|
|
2307
|
-
return;
|
|
2308
|
-
}
|
|
2309
|
-
//remove possible quotes
|
|
2310
|
-
const lastChar = htmlx[attr.end - 1];
|
|
2311
|
-
if (isQuote(lastChar)) {
|
|
2312
|
-
const firstQuote = htmlx.indexOf(lastChar, attr.start);
|
|
2313
|
-
str.remove(firstQuote, firstQuote + 1);
|
|
2314
|
-
str.remove(attr.end - 1, attr.end);
|
|
2315
|
-
}
|
|
2316
|
-
}
|
|
2317
|
-
|
|
2318
|
-
/**
|
|
2319
|
-
* class:xx={yyy} ---> {...__sveltets_1_ensureType(Boolean, !!(yyy))}
|
|
2320
|
-
*/
|
|
2321
|
-
function handleClassDirective$1(str, attr) {
|
|
2322
|
-
str.overwrite(attr.start, attr.expression.start, '{...__sveltets_1_ensureType(Boolean, !!(');
|
|
2323
|
-
const endBrackets = '))}';
|
|
2324
|
-
if (attr.end !== attr.expression.end) {
|
|
2325
|
-
str.overwrite(withTrailingPropertyAccess$1(str.original, attr.expression.end), attr.end, endBrackets);
|
|
2326
|
-
}
|
|
2327
|
-
else {
|
|
2328
|
-
str.appendLeft(attr.end, endBrackets);
|
|
2329
|
-
}
|
|
2330
|
-
}
|
|
2331
|
-
|
|
2332
|
-
/**
|
|
2333
|
-
* Removes comment
|
|
2334
|
-
*/
|
|
2335
|
-
function handleComment$1(str, node) {
|
|
2336
|
-
str.overwrite(node.start, node.end, '', { contentOnly: true });
|
|
2337
|
-
}
|
|
2338
|
-
|
|
2339
|
-
const shadowedPropsSymbol = Symbol('shadowedProps');
|
|
2340
|
-
/**
|
|
2341
|
-
* Transforms the usage of a slot (slot="xxx")
|
|
2342
|
-
* - transforms let:xx, {@const xx}
|
|
2343
|
-
*/
|
|
2344
|
-
function handleSlot(htmlx, str, slotEl, component, slotName, ifScope, templateScope) {
|
|
2345
|
-
var _a;
|
|
2346
|
-
//collect "let" definitions
|
|
2347
|
-
const slotElIsComponent = slotEl === component;
|
|
2348
|
-
let hasMovedLet = false;
|
|
2349
|
-
let slotDefInsertionPoint;
|
|
2350
|
-
// lazily calculate insertion point only when needed
|
|
2351
|
-
const calculateSlotDefInsertionPoint = () => {
|
|
2352
|
-
slotDefInsertionPoint =
|
|
2353
|
-
slotDefInsertionPoint ||
|
|
2354
|
-
(slotElIsComponent
|
|
2355
|
-
? htmlx.lastIndexOf('>', slotEl.children[0].start) + 1
|
|
2356
|
-
: slotEl.start);
|
|
2357
|
-
};
|
|
2358
|
-
for (const attr of slotEl.attributes) {
|
|
2359
|
-
if (attr.type != 'Let') {
|
|
2360
|
-
continue;
|
|
2361
|
-
}
|
|
2362
|
-
if (slotElIsComponent && slotEl.children.length == 0) {
|
|
2363
|
-
//no children anyway, just wipe out the attribute
|
|
2364
|
-
str.remove(attr.start, attr.end);
|
|
2365
|
-
continue;
|
|
2366
|
-
}
|
|
2367
|
-
calculateSlotDefInsertionPoint();
|
|
2368
|
-
str.move(attr.start, attr.end, slotDefInsertionPoint);
|
|
2369
|
-
//remove let:
|
|
2370
|
-
str.remove(attr.start, attr.start + 'let:'.length);
|
|
2371
|
-
if (hasMovedLet) {
|
|
2372
|
-
str.appendRight(attr.start + 'let:'.length, ', ');
|
|
2373
|
-
}
|
|
2374
|
-
templateScope.inits.add(((_a = attr.expression) === null || _a === void 0 ? void 0 : _a.name) || attr.name);
|
|
2375
|
-
hasMovedLet = true;
|
|
2376
|
-
if (attr.expression) {
|
|
2377
|
-
//overwrite the = as a :
|
|
2378
|
-
const equalSign = htmlx.lastIndexOf('=', attr.expression.start);
|
|
2379
|
-
const curly = htmlx.lastIndexOf('{', beforeStart(attr.expression.start));
|
|
2380
|
-
str.overwrite(equalSign, curly + 1, ':');
|
|
2381
|
-
str.remove(attr.expression.end, attr.end);
|
|
2382
|
-
}
|
|
2383
|
-
}
|
|
2384
|
-
const hasConstTag = slotEl.children.some((child) => child.type === 'ConstTag');
|
|
2385
|
-
if (!hasMovedLet && !hasConstTag) {
|
|
2386
|
-
return;
|
|
2387
|
-
}
|
|
2388
|
-
calculateSlotDefInsertionPoint();
|
|
2389
|
-
const { singleSlotDef, constRedeclares } = getSingleSlotDefAndConstsRedeclaration(component, slotName, str.original, ifScope, slotElIsComponent);
|
|
2390
|
-
const prefix = constRedeclares ? `() => {${constRedeclares}` : '';
|
|
2391
|
-
str.appendLeft(slotDefInsertionPoint, `{${prefix}() => { `);
|
|
2392
|
-
if (hasMovedLet) {
|
|
2393
|
-
str.appendLeft(slotDefInsertionPoint, 'let {');
|
|
2394
|
-
str.appendRight(slotDefInsertionPoint, `} = ${singleSlotDef};`);
|
|
2395
|
-
}
|
|
2396
|
-
if (hasConstTag) {
|
|
2397
|
-
// unable to move multiple codes to the same place while insert code in between
|
|
2398
|
-
// NOTE: cheat by move to `slotDefInsertionPoint + 1` position
|
|
2399
|
-
// then copy the character in str[slotDefInsertionPoint...slotDefInsertionPoint + 1] to the back
|
|
2400
|
-
// and comment out the original str[slotDefInsertionPoint...slotDefInsertionPoint + 1]
|
|
2401
|
-
str.appendRight(slotDefInsertionPoint, '/*');
|
|
2402
|
-
extractConstTags(slotEl.children).forEach((insertion) => {
|
|
2403
|
-
insertion(slotDefInsertionPoint + 1, str);
|
|
2404
|
-
});
|
|
2405
|
-
str.appendRight(slotDefInsertionPoint + 1, `${ifScope.addPossibleIfCondition()}<>`);
|
|
2406
|
-
str.appendRight(slotDefInsertionPoint + 1, str.original.slice(slotDefInsertionPoint, slotDefInsertionPoint + 1));
|
|
2407
|
-
str.appendLeft(slotDefInsertionPoint + 1, '*/');
|
|
2408
|
-
}
|
|
2409
|
-
else {
|
|
2410
|
-
str.appendRight(slotDefInsertionPoint, `${ifScope.addPossibleIfCondition()}<>`);
|
|
2411
|
-
}
|
|
2412
|
-
const closeSlotDefInsertionPoint = slotElIsComponent
|
|
2413
|
-
? htmlx.lastIndexOf('<', slotEl.end - 1)
|
|
2414
|
-
: slotEl.end;
|
|
2415
|
-
str.appendLeft(closeSlotDefInsertionPoint, `</>}}${constRedeclares ? '}' : ''}`);
|
|
2416
|
-
}
|
|
2417
|
-
function getSingleSlotDefAndConstsRedeclaration(componentNode, slotName, originalStr, ifScope, findAndRedeclareShadowedProps) {
|
|
2418
|
-
if (findAndRedeclareShadowedProps) {
|
|
2419
|
-
const replacement = 'Ψ';
|
|
2420
|
-
const { str, shadowedProps } = getInstanceTypeForDefaultSlot(componentNode, originalStr, replacement);
|
|
2421
|
-
componentNode[shadowedPropsSymbol] = shadowedProps;
|
|
2422
|
-
return {
|
|
2423
|
-
singleSlotDef: `${str}.$$slot_def['${slotName}']`,
|
|
2424
|
-
constRedeclares: getConstsToRedeclare(ifScope, shadowedProps)
|
|
2425
|
-
};
|
|
2426
|
-
}
|
|
2427
|
-
else {
|
|
2428
|
-
const str = getInstanceType(componentNode, originalStr, componentNode[shadowedPropsSymbol] || []);
|
|
2429
|
-
return {
|
|
2430
|
-
singleSlotDef: `${str}.$$slot_def['${slotName}']`,
|
|
2431
|
-
constRedeclares: ifScope.getConstDeclaration()
|
|
2432
|
-
};
|
|
2433
|
-
}
|
|
2434
|
-
}
|
|
2435
|
-
function getConstsToRedeclare(ifScope, shadowedProps) {
|
|
2436
|
-
const ifScopeRedeclarations = ifScope.getConstsToRedeclare();
|
|
2437
|
-
const letRedeclarations = shadowedProps.map(({ value, replacement }) => `${replacement}=${value}`);
|
|
2438
|
-
const replacements = [...ifScopeRedeclarations, ...letRedeclarations].join(',');
|
|
2439
|
-
return replacements ? surroundWithIgnoreComments(`const ${replacements};`) : '';
|
|
2440
|
-
}
|
|
2441
|
-
|
|
2442
|
-
/**
|
|
2443
|
-
* Handle `<svelte:self>` and slot-specific transformations.
|
|
2444
|
-
*/
|
|
2445
|
-
function handleComponent(htmlx, str, el, parent, ifScope, templateScope) {
|
|
2446
|
-
//we need to remove : if it is a svelte component
|
|
2447
|
-
if (el.name.startsWith('svelte:')) {
|
|
2448
|
-
const colon = htmlx.indexOf(':', el.start);
|
|
2449
|
-
str.remove(colon, colon + 1);
|
|
2450
|
-
const closeTag = htmlx.lastIndexOf('/' + el.name, el.end);
|
|
2451
|
-
if (closeTag > el.start) {
|
|
2452
|
-
const colon = htmlx.indexOf(':', closeTag);
|
|
2453
|
-
str.remove(colon, colon + 1);
|
|
2454
|
-
}
|
|
2455
|
-
}
|
|
2456
|
-
// Handle possible slot
|
|
2457
|
-
const slotName = getSlotName(el) || 'default';
|
|
2458
|
-
handleSlot(htmlx, str, el, slotName === 'default' ? el : parent, slotName, ifScope, templateScope);
|
|
2459
|
-
}
|
|
2460
|
-
|
|
2461
|
-
/**
|
|
2462
|
-
* {@debug a} ---> {a}
|
|
2463
|
-
* {@debug a, b} ---> {a}{b}
|
|
2464
|
-
* tsx won't accept commas, must split
|
|
2465
|
-
*/
|
|
2466
|
-
function handleDebug$1(_htmlx, str, debugBlock) {
|
|
2467
|
-
let cursor = debugBlock.start;
|
|
2468
|
-
for (const identifier of debugBlock.identifiers) {
|
|
2469
|
-
str.remove(cursor, identifier.start);
|
|
2470
|
-
str.prependLeft(identifier.start, '{');
|
|
2471
|
-
str.prependLeft(identifier.end, '}');
|
|
2472
|
-
cursor = identifier.end;
|
|
2473
|
-
}
|
|
2474
|
-
str.remove(cursor, debugBlock.end);
|
|
2475
|
-
}
|
|
2476
|
-
|
|
2477
|
-
/**
|
|
2478
|
-
* Transform each block into something JSX can understand.
|
|
2479
|
-
*/
|
|
2480
|
-
function handleEach$1(htmlx, str, eachBlock, ifScope) {
|
|
2481
|
-
// {#each items as item,i (key)} ->
|
|
2482
|
-
// {__sveltets_1_each(items, (item,i) => (key) && (possible if expression &&) <>
|
|
2483
|
-
const constRedeclares = ifScope.getConstDeclaration();
|
|
2484
|
-
const prefix = constRedeclares ? `{() => {${constRedeclares}() => ` : '';
|
|
2485
|
-
str.overwrite(eachBlock.start, eachBlock.expression.start, `${prefix}{__sveltets_1_each(`);
|
|
2486
|
-
str.overwrite(eachBlock.expression.end, eachBlock.context.start, ', (');
|
|
2487
|
-
// {#each true, items as item}
|
|
2488
|
-
if (eachBlock.expression.type === 'SequenceExpression') {
|
|
2489
|
-
str.appendRight(eachBlock.expression.start, '(');
|
|
2490
|
-
str.appendLeft(eachBlock.expression.end, ')');
|
|
2491
|
-
}
|
|
2492
|
-
let contextEnd = eachBlock.context.end;
|
|
2493
|
-
if (eachBlock.index) {
|
|
2494
|
-
const idxLoc = htmlx.indexOf(eachBlock.index, contextEnd);
|
|
2495
|
-
contextEnd = idxLoc + eachBlock.index.length;
|
|
2496
|
-
}
|
|
2497
|
-
const constTags = extractConstTags(eachBlock.children);
|
|
2498
|
-
str.prependLeft(contextEnd, ') =>' + (constTags.length ? ' {' : ''));
|
|
2499
|
-
constTags.forEach((insertion) => {
|
|
2500
|
-
insertion(contextEnd, str);
|
|
2501
|
-
});
|
|
2502
|
-
if (eachBlock.key) {
|
|
2503
|
-
const endEachStart = htmlx.indexOf('}', eachBlock.key.end);
|
|
2504
|
-
str.overwrite(endEachStart, endEachStart + 1, ` && ${ifScope.addPossibleIfCondition()}<>`);
|
|
2505
|
-
}
|
|
2506
|
-
else {
|
|
2507
|
-
const endEachStart = htmlx.indexOf('}', contextEnd);
|
|
2508
|
-
str.overwrite(endEachStart, endEachStart + 1, ` ${ifScope.addPossibleIfCondition()}<>`);
|
|
2509
|
-
}
|
|
2510
|
-
const endEach = htmlx.lastIndexOf('{', eachBlock.end - 1);
|
|
2511
|
-
const suffix = '</>' + (constTags.length ? '}' : '') + (constRedeclares ? ')}}}' : ')}');
|
|
2512
|
-
// {/each} -> </>})} or {:else} -> </>})}
|
|
2513
|
-
if (eachBlock.else) {
|
|
2514
|
-
const elseEnd = htmlx.lastIndexOf('}', eachBlock.else.start);
|
|
2515
|
-
const elseStart = htmlx.lastIndexOf('{', elseEnd);
|
|
2516
|
-
str.overwrite(elseStart, elseEnd + 1, suffix);
|
|
2517
|
-
str.remove(endEach, eachBlock.end);
|
|
2518
|
-
}
|
|
2519
|
-
else {
|
|
2520
|
-
str.overwrite(endEach, eachBlock.end, suffix);
|
|
2521
|
-
}
|
|
2522
|
-
}
|
|
2523
|
-
|
|
2524
|
-
/**
|
|
2525
|
-
* Special treatment for self-closing / void tags to make them conform to JSX.
|
|
2526
|
-
*/
|
|
2527
|
-
function handleElement(htmlx, str, node, parent, ifScope, templateScope) {
|
|
2528
|
-
const slotName = getSlotName(node);
|
|
2529
|
-
if (slotName) {
|
|
2530
|
-
handleSlot(htmlx, str, node, parent, slotName, ifScope, templateScope);
|
|
2531
|
-
}
|
|
2532
|
-
//we just have to self close void tags since jsx always wants the />
|
|
2533
|
-
const voidTags = 'area,base,br,col,embed,hr,img,input,link,meta,param,source,track,wbr'.split(',');
|
|
2534
|
-
if (voidTags.find((x) => x == node.name)) {
|
|
2535
|
-
if (htmlx[node.end - 2] != '/') {
|
|
2536
|
-
str.appendRight(node.end - 1, '/');
|
|
2537
|
-
}
|
|
2538
|
-
}
|
|
2539
|
-
//some tags auto close when they encounter certain elements, jsx doesn't support this
|
|
2540
|
-
if (htmlx[node.end - 1] != '>') {
|
|
2541
|
-
str.appendRight(node.end, `</${node.name}>`);
|
|
2542
|
-
}
|
|
2543
|
-
}
|
|
2544
|
-
|
|
2545
|
-
/**
|
|
2546
|
-
* Transform on:xxx={yyy}
|
|
2547
|
-
* - For DOM elements: ---> onxxx={yyy}
|
|
2548
|
-
* - For Svelte components/special elements: ---> {__sveltets_2_instanceOf(..ComponentType..).$on("xxx", yyy)}
|
|
2549
|
-
*/
|
|
2550
|
-
function handleEventHandler$1(htmlx, str, attr, parent) {
|
|
2551
|
-
const jsxEventName = attr.name;
|
|
2552
|
-
if (['Element', 'Window', 'Body'].includes(parent.type) /*&& KnownEvents.indexOf('on'+jsxEventName) >= 0*/) {
|
|
2553
|
-
if (attr.expression) {
|
|
2554
|
-
const endAttr = htmlx.indexOf('=', attr.start);
|
|
2555
|
-
str.overwrite(attr.start + 'on:'.length - 1, endAttr, jsxEventName);
|
|
2556
|
-
const lastChar = htmlx[attr.end - 1];
|
|
2557
|
-
if (isQuote(lastChar)) {
|
|
2558
|
-
const firstQuote = htmlx.indexOf(lastChar, endAttr);
|
|
2559
|
-
str.remove(firstQuote, firstQuote + 1);
|
|
2560
|
-
str.remove(attr.end - 1, attr.end);
|
|
2561
|
-
}
|
|
2562
|
-
}
|
|
2563
|
-
else {
|
|
2564
|
-
str.overwrite(attr.start + 'on:'.length - 1, attr.end, `${jsxEventName}={undefined}`);
|
|
2565
|
-
}
|
|
2566
|
-
}
|
|
2567
|
-
else {
|
|
2568
|
-
if (attr.expression) {
|
|
2569
|
-
const on = 'on';
|
|
2570
|
-
//for handler assignment, we change it to call to our __sveltets_1_ensureFunction
|
|
2571
|
-
str.appendRight(attr.start, `{${getInstanceType(parent, str.original)}.$`);
|
|
2572
|
-
const eventNameIndex = htmlx.indexOf(':', attr.start) + 1;
|
|
2573
|
-
str.overwrite(htmlx.indexOf(on, attr.start) + on.length, eventNameIndex, "('");
|
|
2574
|
-
const eventEnd = htmlx.lastIndexOf('=', attr.expression.start);
|
|
2575
|
-
str.overwrite(eventEnd, attr.expression.start, "', ");
|
|
2576
|
-
str.overwrite(withTrailingPropertyAccess$1(str.original, attr.expression.end), attr.end, ')}');
|
|
2577
|
-
str.move(attr.start, attr.end, parent.end);
|
|
2578
|
-
}
|
|
2579
|
-
else {
|
|
2580
|
-
//for passthrough handlers, we just remove
|
|
2581
|
-
str.remove(attr.start, attr.end);
|
|
2582
|
-
}
|
|
2583
|
-
}
|
|
2584
|
-
}
|
|
2585
|
-
|
|
2586
|
-
/**
|
|
2587
|
-
* {# if ...}...{/if} ---> {() => {if(...){<>...</>}}}
|
|
2588
|
-
*/
|
|
2589
|
-
function handleIf$1(htmlx, str, ifBlock, ifScope) {
|
|
2590
|
-
const endIf = htmlx.lastIndexOf('{', ifBlock.end - 1);
|
|
2591
|
-
const constTags = extractConstTags(ifBlock.children);
|
|
2592
|
-
const ifConditionEnd = htmlx.indexOf('}', ifBlock.expression.end) + 1;
|
|
2593
|
-
const hasConstTags = !!constTags.length;
|
|
2594
|
-
const endIIFE = createEndIIFE(hasConstTags);
|
|
2595
|
-
const startIIFE = createStartIIFE(hasConstTags);
|
|
2596
|
-
if (hasConstTags) {
|
|
2597
|
-
// {@const hi = exp} <div>{hi}> -> {(() => { const hi = exp; return <> <div>{hi}<div></> })}
|
|
2598
|
-
constTags.forEach((constTag) => {
|
|
2599
|
-
constTag(ifConditionEnd, str);
|
|
2600
|
-
});
|
|
2601
|
-
str.appendRight(ifConditionEnd, 'return <>');
|
|
2602
|
-
if (ifBlock.else) {
|
|
2603
|
-
// {:else} -> </>})()}</> : <>
|
|
2604
|
-
const elseWord = htmlx.lastIndexOf(':else', ifBlock.else.start);
|
|
2605
|
-
const elseStart = htmlx.lastIndexOf('{', elseWord);
|
|
2606
|
-
str.appendLeft(elseStart, endIIFE);
|
|
2607
|
-
}
|
|
2608
|
-
}
|
|
2609
|
-
if (ifBlock.elseif) {
|
|
2610
|
-
// {:else if expr} -> : (expr) ? <>
|
|
2611
|
-
// {:else if expr}{@const ...} -> : (expr) ? <>{(() => {const ...; return <>
|
|
2612
|
-
const elseIfStart = htmlx.lastIndexOf('{', ifBlock.expression.start);
|
|
2613
|
-
str.overwrite(elseIfStart, ifBlock.expression.start, '</> : (', {
|
|
2614
|
-
contentOnly: true
|
|
2615
|
-
});
|
|
2616
|
-
str.overwrite(withTrailingPropertyAccess$1(str.original, ifBlock.expression.end), ifConditionEnd, ') ? <>' + startIIFE);
|
|
2617
|
-
ifScope.addElseIf(ifBlock.expression, str);
|
|
2618
|
-
if (!ifBlock.else) {
|
|
2619
|
-
str.appendLeft(endIf, endIIFE + '</> : <>');
|
|
2620
|
-
}
|
|
2621
|
-
return;
|
|
2622
|
-
}
|
|
2623
|
-
// {#if expr} -> {(expr) ? <>
|
|
2624
|
-
// {#if expr}{@const ...} -> {(expr) ? <>{(() => {const ...; return <>
|
|
2625
|
-
str.overwrite(ifBlock.start, ifBlock.expression.start, '{(', { contentOnly: true });
|
|
2626
|
-
str.overwrite(withTrailingPropertyAccess$1(str.original, ifBlock.expression.end), ifConditionEnd, ') ? <>' + startIIFE, { contentOnly: true });
|
|
2627
|
-
ifScope.addNestedIf(ifBlock.expression, str);
|
|
2628
|
-
if (ifBlock.else) {
|
|
2629
|
-
// {/if} -> </> }
|
|
2630
|
-
str.overwrite(endIf, ifBlock.end, '</> }', { contentOnly: true });
|
|
2631
|
-
}
|
|
2632
|
-
else {
|
|
2633
|
-
// {/if} -> </> : <></>}
|
|
2634
|
-
// {@const ...} -> </>})()}</> : <></>}
|
|
2635
|
-
str.overwrite(endIf, ifBlock.end, endIIFE + '</> : <></>}', {
|
|
2636
|
-
contentOnly: true
|
|
2637
|
-
});
|
|
2638
|
-
}
|
|
2639
|
-
}
|
|
2640
|
-
function createStartIIFE(hasConstTags) {
|
|
2641
|
-
return hasConstTags ? '{(() => {' : '';
|
|
2642
|
-
}
|
|
2643
|
-
function createEndIIFE(hasConstTags) {
|
|
2644
|
-
return hasConstTags ? '</>})()}' : '';
|
|
2645
|
-
}
|
|
2646
|
-
/**
|
|
2647
|
-
* {:else} ---> </> : <>
|
|
2648
|
-
* {:else} {@const ...} -> </> : <>{(() => { const ...; return<>
|
|
2649
|
-
*/
|
|
2650
|
-
function handleElse$1(htmlx, str, elseBlock, parent, ifScope) {
|
|
2651
|
-
var _a, _b;
|
|
2652
|
-
if (parent.type !== 'IfBlock' ||
|
|
2653
|
-
(((_a = elseBlock.children[0]) === null || _a === void 0 ? void 0 : _a.type) === 'IfBlock' && ((_b = elseBlock.children[0]) === null || _b === void 0 ? void 0 : _b.elseif))) {
|
|
2654
|
-
return;
|
|
2655
|
-
}
|
|
2656
|
-
const elseEnd = htmlx.lastIndexOf('}', elseBlock.start);
|
|
2657
|
-
const elseword = htmlx.lastIndexOf(':else', elseEnd);
|
|
2658
|
-
const elseStart = htmlx.lastIndexOf('{', elseword);
|
|
2659
|
-
const constTags = extractConstTags(elseBlock.children);
|
|
2660
|
-
const hasConstTags = !!constTags.length;
|
|
2661
|
-
str.overwrite(elseStart, elseEnd + 1, '</> : <>' + createStartIIFE(hasConstTags));
|
|
2662
|
-
ifScope.addElse();
|
|
2663
|
-
if (!hasConstTags) {
|
|
2664
|
-
return;
|
|
2665
|
-
}
|
|
2666
|
-
constTags.forEach((constTag) => {
|
|
2667
|
-
constTag(elseEnd + 1, str);
|
|
2668
|
-
});
|
|
2669
|
-
str.appendRight(elseEnd + 1, 'return <>');
|
|
2670
|
-
str.appendLeft(elseBlock.end, createEndIIFE(true));
|
|
2671
|
-
}
|
|
2672
|
-
|
|
2673
|
-
var IfType;
|
|
2674
|
-
(function (IfType) {
|
|
2675
|
-
IfType[IfType["If"] = 0] = "If";
|
|
2676
|
-
IfType[IfType["ElseIf"] = 1] = "ElseIf";
|
|
2677
|
-
IfType[IfType["Else"] = 2] = "Else";
|
|
2678
|
-
})(IfType || (IfType = {}));
|
|
2679
|
-
/**
|
|
2680
|
-
* Creates a new condition whos parent is the current condition
|
|
2681
|
-
* and the leaf is the passed in condition info.
|
|
2682
|
-
* See `Condition` for an explanation of the structure.
|
|
2683
|
-
*/
|
|
2684
|
-
function addElseIfCondition(existingCondition, newCondition) {
|
|
2685
|
-
return {
|
|
2686
|
-
parent: existingCondition,
|
|
2687
|
-
condition: newCondition,
|
|
2688
|
-
type: IfType.ElseIf
|
|
2689
|
-
};
|
|
2690
|
-
}
|
|
2691
|
-
/**
|
|
2692
|
-
* Creates a new condition whos parent is the current condition
|
|
2693
|
-
* and the leaf is the else condition, where children can follow.
|
|
2694
|
-
* See `Condition` for an explanation of the structure.
|
|
2695
|
-
*/
|
|
2696
|
-
function addElseCondition(existingCondition) {
|
|
2697
|
-
return {
|
|
2698
|
-
parent: existingCondition,
|
|
2699
|
-
type: IfType.Else
|
|
2700
|
-
};
|
|
2701
|
-
}
|
|
2702
|
-
const REPLACEMENT_PREFIX = '\u03A9';
|
|
2703
|
-
/**
|
|
2704
|
-
* Returns the full currently known condition. Identifiers in the condition
|
|
2705
|
-
* get replaced if they were redeclared.
|
|
2706
|
-
*/
|
|
2707
|
-
function getFullCondition(condition, replacedNames, replacementPrefix) {
|
|
2708
|
-
switch (condition.type) {
|
|
2709
|
-
case IfType.If:
|
|
2710
|
-
return _getFullCondition(condition, false, replacedNames, replacementPrefix);
|
|
2711
|
-
case IfType.ElseIf:
|
|
2712
|
-
return _getFullCondition(condition, false, replacedNames, replacementPrefix);
|
|
2713
|
-
case IfType.Else:
|
|
2714
|
-
return _getFullCondition(condition, false, replacedNames, replacementPrefix);
|
|
2715
|
-
}
|
|
2716
|
-
}
|
|
2717
|
-
function _getFullCondition(condition, negate, replacedNames, replacementPrefix) {
|
|
2718
|
-
switch (condition.type) {
|
|
2719
|
-
case IfType.If:
|
|
2720
|
-
return negate
|
|
2721
|
-
? `!(${getConditionString(condition.condition, replacedNames, replacementPrefix)})`
|
|
2722
|
-
: `(${getConditionString(condition.condition, replacedNames, replacementPrefix)})`;
|
|
2723
|
-
case IfType.ElseIf:
|
|
2724
|
-
return `${_getFullCondition(condition.parent, true, replacedNames, replacementPrefix)} && ${negate ? '!' : ''}(${getConditionString(condition.condition, replacedNames, replacementPrefix)})`;
|
|
2725
|
-
case IfType.Else:
|
|
2726
|
-
return `${_getFullCondition(condition.parent, true, replacedNames, replacementPrefix)}`;
|
|
2727
|
-
}
|
|
2728
|
-
}
|
|
2729
|
-
/**
|
|
2730
|
-
* Alter a condition text such that identifiers which needs replacement
|
|
2731
|
-
* are replaced accordingly.
|
|
2732
|
-
*/
|
|
2733
|
-
function getConditionString(condition, replacedNames, replacementPrefix) {
|
|
2734
|
-
const replacements = [];
|
|
2735
|
-
for (const name of replacedNames) {
|
|
2736
|
-
const occurences = condition.identifiers.get(name);
|
|
2737
|
-
if (occurences) {
|
|
2738
|
-
for (const occurence of occurences) {
|
|
2739
|
-
replacements.push({ ...occurence, name });
|
|
2740
|
-
}
|
|
2741
|
-
}
|
|
2742
|
-
}
|
|
2743
|
-
if (!replacements.length) {
|
|
2744
|
-
return condition.text;
|
|
2745
|
-
}
|
|
2746
|
-
replacements.sort((r1, r2) => r1.start - r2.start);
|
|
2747
|
-
return (condition.text.substring(0, replacements[0].start) +
|
|
2748
|
-
replacements
|
|
2749
|
-
.map((replacement, idx) => {
|
|
2750
|
-
var _a;
|
|
2751
|
-
return replacementPrefix +
|
|
2752
|
-
replacement.name +
|
|
2753
|
-
condition.text.substring(replacement.end, (_a = replacements[idx + 1]) === null || _a === void 0 ? void 0 : _a.start);
|
|
2754
|
-
})
|
|
2755
|
-
.join(''));
|
|
2756
|
-
}
|
|
2757
|
-
/**
|
|
2758
|
-
* Returns a set of all identifiers that were used in this condition
|
|
2759
|
-
*/
|
|
2760
|
-
function collectReferencedIdentifiers(condition) {
|
|
2761
|
-
const identifiers = new Set();
|
|
2762
|
-
let current = condition;
|
|
2763
|
-
while (current) {
|
|
2764
|
-
if (current.type === IfType.ElseIf || current.type === IfType.If) {
|
|
2765
|
-
for (const identifier of current.condition.identifiers.keys()) {
|
|
2766
|
-
identifiers.add(identifier);
|
|
2767
|
-
}
|
|
2768
|
-
}
|
|
2769
|
-
current =
|
|
2770
|
-
current.type === IfType.ElseIf || current.type === IfType.Else
|
|
2771
|
-
? current.parent
|
|
2772
|
-
: undefined;
|
|
2773
|
-
}
|
|
2774
|
-
return identifiers;
|
|
2775
|
-
}
|
|
2776
|
-
/**
|
|
2777
|
-
* A scope contains a if-condition including else(if) branches.
|
|
2778
|
-
* The branches are added over time and the whole known condition is updated accordingly.
|
|
2779
|
-
*
|
|
2780
|
-
* This class is then mainly used to reprint if-conditions. This is necessary when
|
|
2781
|
-
* a lambda-function is declared within the jsx-template because that function loses
|
|
2782
|
-
* the control flow information. The reprint should be prepended to the jsx-content
|
|
2783
|
-
* of the lambda function.
|
|
2784
|
-
*
|
|
2785
|
-
* Example:
|
|
2786
|
-
* `{check ? {() => {<p>hi</p>}} : ''}`
|
|
2787
|
-
* becomes
|
|
2788
|
-
* `{check ? {() => {check && <p>hi</p>}} : ''}`
|
|
2789
|
-
*
|
|
2790
|
-
* Most of the logic in here deals with the possibility of shadowed variables.
|
|
2791
|
-
* Example:
|
|
2792
|
-
* `{check ? {(check) => {<p>{check}</p>}} : ''}`
|
|
2793
|
-
* becomes
|
|
2794
|
-
* `{check ? {const Ωcheck = check;(check) => {Ωcheck && <p>{check}</p>}} : ''}`
|
|
2795
|
-
*
|
|
2796
|
-
*/
|
|
2797
|
-
class IfScope {
|
|
2798
|
-
constructor(scope, current, parent) {
|
|
2799
|
-
this.scope = scope;
|
|
2800
|
-
this.current = current;
|
|
2801
|
-
this.parent = parent;
|
|
2802
|
-
this.ownScope = this.scope.value;
|
|
2803
|
-
this.replacementPrefix = REPLACEMENT_PREFIX.repeat(this.computeDepth());
|
|
2804
|
-
}
|
|
2805
|
-
/**
|
|
2806
|
-
* Returns the full currently known condition, prepended with the conditions
|
|
2807
|
-
* of its parents. Identifiers in the condition get replaced if they were redeclared.
|
|
2808
|
-
*/
|
|
2809
|
-
getFullCondition() {
|
|
2810
|
-
var _a;
|
|
2811
|
-
if (!this.current) {
|
|
2812
|
-
return '';
|
|
2813
|
-
}
|
|
2814
|
-
const parentCondition = (_a = this.parent) === null || _a === void 0 ? void 0 : _a.getFullCondition();
|
|
2815
|
-
const condition = `(${getFullCondition(this.current, this.getNamesThatNeedReplacement(), this.replacementPrefix)})`;
|
|
2816
|
-
return parentCondition ? `(${parentCondition}) && ${condition}` : condition;
|
|
2817
|
-
}
|
|
2818
|
-
/**
|
|
2819
|
-
* Convenience method which invokes `getFullCondition` and adds a `&&` at the end
|
|
2820
|
-
* for easy chaining.
|
|
2821
|
-
*/
|
|
2822
|
-
addPossibleIfCondition() {
|
|
2823
|
-
const condition = this.getFullCondition();
|
|
2824
|
-
return condition ? surroundWithIgnoreComments(`${condition} && `) : '';
|
|
2825
|
-
}
|
|
2826
|
-
/**
|
|
2827
|
-
* Adds a new child IfScope.
|
|
2828
|
-
*/
|
|
2829
|
-
addNestedIf(expression, str) {
|
|
2830
|
-
const condition = this.getConditionInfo(str, expression);
|
|
2831
|
-
const ifScope = new IfScope(this.scope, { condition, type: IfType.If }, this);
|
|
2832
|
-
this.child = ifScope;
|
|
2833
|
-
}
|
|
2834
|
-
/**
|
|
2835
|
-
* Adds a `else if` branch to the scope and enhances the condition accordingly.
|
|
2836
|
-
*/
|
|
2837
|
-
addElseIf(expression, str) {
|
|
2838
|
-
const condition = this.getConditionInfo(str, expression);
|
|
2839
|
-
this.current = addElseIfCondition(this.current, condition);
|
|
2840
|
-
}
|
|
2841
|
-
/**
|
|
2842
|
-
* Adds a `else` branch to the scope and enhances the condition accordingly.
|
|
2843
|
-
*/
|
|
2844
|
-
addElse() {
|
|
2845
|
-
this.current = addElseCondition(this.current);
|
|
2846
|
-
}
|
|
2847
|
-
getChild() {
|
|
2848
|
-
return this.child || this;
|
|
2849
|
-
}
|
|
2850
|
-
getParent() {
|
|
2851
|
-
return this.parent || this;
|
|
2852
|
-
}
|
|
2853
|
-
/**
|
|
2854
|
-
* Returns a set of all identifiers that were used in this IfScope and its parent scopes.
|
|
2855
|
-
*/
|
|
2856
|
-
collectReferencedIdentifiers() {
|
|
2857
|
-
var _a;
|
|
2858
|
-
const current = collectReferencedIdentifiers(this.current);
|
|
2859
|
-
const parent = (_a = this.parent) === null || _a === void 0 ? void 0 : _a.collectReferencedIdentifiers();
|
|
2860
|
-
if (parent) {
|
|
2861
|
-
for (const identifier of parent) {
|
|
2862
|
-
current.add(identifier);
|
|
2863
|
-
}
|
|
2864
|
-
}
|
|
2865
|
-
return current;
|
|
2866
|
-
}
|
|
2867
|
-
/**
|
|
2868
|
-
* Should be invoked when a new template scope which resets control flow (await, each, slot) is created.
|
|
2869
|
-
* The returned string contains a list of `const` declarations which redeclares the identifiers
|
|
2870
|
-
* in the conditions which would be overwritten by the scope
|
|
2871
|
-
* (because they declare a variable with the same name, therefore shadowing the outer variable).
|
|
2872
|
-
*/
|
|
2873
|
-
getConstDeclaration() {
|
|
2874
|
-
const replacements = this.getConstsToRedeclare().join(',');
|
|
2875
|
-
return replacements ? surroundWithIgnoreComments(`const ${replacements};`) : '';
|
|
2876
|
-
}
|
|
2877
|
-
/**
|
|
2878
|
-
* Like `getConstsRedaclarationString`, but only returns a list of redaclaration-string without
|
|
2879
|
-
* merging the result with `const` and a ignore comments surround.
|
|
2880
|
-
*/
|
|
2881
|
-
getConstsToRedeclare() {
|
|
2882
|
-
return this.getNamesToRedeclare().map((identifier) => `${this.replacementPrefix + identifier}=${identifier}`);
|
|
2883
|
-
}
|
|
2884
|
-
/**
|
|
2885
|
-
* Returns true if given identifier is referenced in this IfScope or a parent scope.
|
|
2886
|
-
*/
|
|
2887
|
-
referencesIdentifier(name) {
|
|
2888
|
-
const current = collectReferencedIdentifiers(this.current);
|
|
2889
|
-
if (current.has(name)) {
|
|
2890
|
-
return true;
|
|
2891
|
-
}
|
|
2892
|
-
if (!this.parent || this.ownScope.inits.has(name)) {
|
|
2893
|
-
return false;
|
|
2894
|
-
}
|
|
2895
|
-
return this.parent.referencesIdentifier(name);
|
|
2896
|
-
}
|
|
2897
|
-
getConditionInfo(str, expression) {
|
|
2898
|
-
const identifiers = getIdentifiersInIfExpression(expression);
|
|
2899
|
-
const text = str.original.substring(expression.start, expression.end);
|
|
2900
|
-
return { identifiers, text };
|
|
2901
|
-
}
|
|
2902
|
-
/**
|
|
2903
|
-
* Contains a list of identifiers which would be overwritten by the child template scope.
|
|
2904
|
-
*/
|
|
2905
|
-
getNamesToRedeclare() {
|
|
2906
|
-
return [...this.scope.value.inits.keys()].filter((init) => {
|
|
2907
|
-
let parent = this.scope.value.parent;
|
|
2908
|
-
while (parent && parent !== this.ownScope) {
|
|
2909
|
-
if (parent.inits.has(init)) {
|
|
2910
|
-
return false;
|
|
2911
|
-
}
|
|
2912
|
-
parent = parent.parent;
|
|
2913
|
-
}
|
|
2914
|
-
return this.referencesIdentifier(init);
|
|
2915
|
-
});
|
|
2916
|
-
}
|
|
2917
|
-
/**
|
|
2918
|
-
* Return all identifiers that were redeclared and therefore need replacement.
|
|
2919
|
-
*/
|
|
2920
|
-
getNamesThatNeedReplacement() {
|
|
2921
|
-
const referencedIdentifiers = this.collectReferencedIdentifiers();
|
|
2922
|
-
return [...referencedIdentifiers].filter((identifier) => this.someChildScopeHasRedeclaredVariable(identifier));
|
|
2923
|
-
}
|
|
2924
|
-
/**
|
|
2925
|
-
* Returns true if given identifier name is redeclared in a child template scope
|
|
2926
|
-
* and is therefore shadowed within that scope.
|
|
2927
|
-
*/
|
|
2928
|
-
someChildScopeHasRedeclaredVariable(name) {
|
|
2929
|
-
let scope = this.scope.value;
|
|
2930
|
-
while (scope && scope !== this.ownScope) {
|
|
2931
|
-
if (scope.inits.has(name)) {
|
|
2932
|
-
return true;
|
|
2933
|
-
}
|
|
2934
|
-
scope = scope.parent;
|
|
2935
|
-
}
|
|
2936
|
-
return false;
|
|
2937
|
-
}
|
|
2938
|
-
computeDepth() {
|
|
2939
|
-
let idx = 1;
|
|
2940
|
-
let parent = this.ownScope.parent;
|
|
2941
|
-
while (parent) {
|
|
2942
|
-
idx++;
|
|
2943
|
-
parent = parent.parent;
|
|
2944
|
-
}
|
|
2945
|
-
return idx;
|
|
2946
|
-
}
|
|
2947
|
-
}
|
|
2948
|
-
|
|
2949
|
-
/**
|
|
2950
|
-
* {#key expr}content{/key} ---> {expr} content
|
|
2951
|
-
*/
|
|
2952
|
-
function handleKey$1(htmlx, str, keyBlock) {
|
|
2953
|
-
// {#key expr} -> {expr}
|
|
2954
|
-
str.overwrite(keyBlock.start, keyBlock.expression.start, '{');
|
|
2955
|
-
const end = htmlx.indexOf('}', keyBlock.expression.end);
|
|
2956
|
-
str.overwrite(withTrailingPropertyAccess$1(str.original, keyBlock.expression.end), end + 1, '} ');
|
|
2957
|
-
// {/key} ->
|
|
2958
|
-
const endKey = htmlx.lastIndexOf('{', keyBlock.end - 1);
|
|
2959
|
-
str.remove(endKey, keyBlock.end);
|
|
2960
|
-
}
|
|
2961
|
-
|
|
2962
|
-
/**
|
|
2963
|
-
* {@html ...} ---> {...}
|
|
2964
|
-
*/
|
|
2965
|
-
function handleRawHtml$1(htmlx, str, rawBlock) {
|
|
2966
|
-
const tokenStart = htmlx.indexOf('@html', rawBlock.start);
|
|
2967
|
-
str.remove(tokenStart, tokenStart + '@html'.length);
|
|
2968
|
-
}
|
|
2969
|
-
|
|
2970
|
-
/**
|
|
2971
|
-
* style:xx ---> __sveltets_1_ensureType(String, Number, xx);
|
|
2972
|
-
* style:xx={yy} ---> __sveltets_1_ensureType(String, Number, yy);
|
|
2973
|
-
* style:xx="yy" ---> __sveltets_1_ensureType(String, Number, "yy");
|
|
2974
|
-
* style:xx="a{b}" ---> __sveltets_1_ensureType(String, Number, `a${b}`);
|
|
2975
|
-
*/
|
|
2976
|
-
function handleStyleDirective$1(str, style) {
|
|
2977
|
-
const htmlx = str.original;
|
|
2978
|
-
if (style.value === true || style.value.length === 0) {
|
|
2979
|
-
str.overwrite(style.start, htmlx.indexOf(':', style.start) + 1, '{...__sveltets_1_ensureType(String, Number, ');
|
|
2980
|
-
str.appendLeft(style.end, ')}');
|
|
2981
|
-
return;
|
|
2982
|
-
}
|
|
2983
|
-
if (style.value.length > 1) {
|
|
2984
|
-
buildTemplateString(style, str, htmlx, '{...__sveltets_1_ensureType(String, Number, `', '`)}', style.start);
|
|
2985
|
-
return;
|
|
2986
|
-
}
|
|
2987
|
-
const styleVal = style.value[0];
|
|
2988
|
-
if (styleVal.type === 'Text') {
|
|
2989
|
-
str.overwrite(style.start, styleVal.start, '{...__sveltets_1_ensureType(String, Number, "');
|
|
2990
|
-
if (styleVal.end === style.end) {
|
|
2991
|
-
str.appendLeft(style.end, '")}');
|
|
2992
|
-
}
|
|
2993
|
-
else {
|
|
2994
|
-
str.overwrite(styleVal.end, style.end, '")}');
|
|
2995
|
-
}
|
|
2996
|
-
}
|
|
2997
|
-
else {
|
|
2998
|
-
// MustacheTag
|
|
2999
|
-
str.overwrite(style.start, styleVal.start + 1, '{...__sveltets_1_ensureType(String, Number, ');
|
|
3000
|
-
str.overwrite(styleVal.end - 1, style.end, ')}');
|
|
3001
|
-
}
|
|
3002
|
-
}
|
|
3003
|
-
|
|
3004
|
-
/**
|
|
3005
|
-
* `<svelte:window>...</svelte:window>` ----> `<sveltewindow>...</sveltewindow>`
|
|
3006
|
-
* (same for :head, :body, :options, :fragment, :element)
|
|
3007
|
-
*/
|
|
3008
|
-
function handleSvelteTag(htmlx, str, node) {
|
|
3009
|
-
const colon = htmlx.indexOf(':', node.start);
|
|
3010
|
-
str.remove(colon, colon + 1);
|
|
3011
|
-
const closeTag = htmlx.lastIndexOf('/' + node.name, node.end);
|
|
3012
|
-
if (closeTag > node.start) {
|
|
3013
|
-
const colon = htmlx.indexOf(':', closeTag);
|
|
3014
|
-
str.remove(colon, colon + 1);
|
|
3015
|
-
}
|
|
3016
|
-
}
|
|
3017
|
-
|
|
3018
|
-
/**
|
|
3019
|
-
*
|
|
3020
|
-
* @param {Node} param
|
|
3021
|
-
* @param {Identifier[]} nodes
|
|
3022
|
-
* @returns {Identifier[]}
|
|
3023
|
-
*/
|
|
3024
|
-
function extract_identifiers(param, nodes = []) {
|
|
3025
|
-
switch (param.type) {
|
|
3026
|
-
case 'Identifier':
|
|
3027
|
-
nodes.push(param);
|
|
3028
|
-
break;
|
|
3029
|
-
|
|
3030
|
-
case 'MemberExpression':
|
|
3031
|
-
let object = param;
|
|
3032
|
-
while (object.type === 'MemberExpression') {
|
|
3033
|
-
object = /** @type {any} */ (object.object);
|
|
3034
|
-
}
|
|
3035
|
-
nodes.push(/** @type {any} */ (object));
|
|
3036
|
-
break;
|
|
3037
|
-
|
|
3038
|
-
case 'ObjectPattern':
|
|
3039
|
-
/**
|
|
3040
|
-
*
|
|
3041
|
-
* @param {Property | RestElement} prop
|
|
3042
|
-
*/
|
|
3043
|
-
const handle_prop = (prop) => {
|
|
3044
|
-
if (prop.type === 'RestElement') {
|
|
3045
|
-
extract_identifiers(prop.argument, nodes);
|
|
3046
|
-
} else {
|
|
3047
|
-
extract_identifiers(prop.value, nodes);
|
|
3048
|
-
}
|
|
3049
|
-
};
|
|
3050
|
-
|
|
3051
|
-
param.properties.forEach(handle_prop);
|
|
3052
|
-
break;
|
|
3053
|
-
|
|
3054
|
-
case 'ArrayPattern':
|
|
3055
|
-
/**
|
|
3056
|
-
*
|
|
3057
|
-
* @param {Node} element
|
|
3058
|
-
*/
|
|
3059
|
-
const handle_element = (element) => {
|
|
3060
|
-
if (element) extract_identifiers(element, nodes);
|
|
3061
|
-
};
|
|
3062
|
-
|
|
3063
|
-
param.elements.forEach(handle_element);
|
|
3064
|
-
break;
|
|
3065
|
-
|
|
3066
|
-
case 'RestElement':
|
|
3067
|
-
extract_identifiers(param.argument, nodes);
|
|
3068
|
-
break;
|
|
3069
|
-
|
|
3070
|
-
case 'AssignmentPattern':
|
|
3071
|
-
extract_identifiers(param.left, nodes);
|
|
3072
|
-
break;
|
|
3073
|
-
}
|
|
3074
|
-
|
|
3075
|
-
return nodes;
|
|
3076
|
-
}
|
|
3077
|
-
|
|
3078
|
-
let TemplateScope$1 = class TemplateScope {
|
|
3079
|
-
constructor(parent) {
|
|
3080
|
-
this.inits = new Set();
|
|
3081
|
-
this.parent = parent;
|
|
3082
|
-
}
|
|
3083
|
-
child() {
|
|
3084
|
-
const child = new TemplateScope$1(this);
|
|
3085
|
-
return child;
|
|
3086
|
-
}
|
|
3087
|
-
};
|
|
3088
|
-
class TemplateScopeManager {
|
|
3089
|
-
constructor() {
|
|
3090
|
-
this.value = new TemplateScope$1();
|
|
3091
|
-
}
|
|
3092
|
-
eachEnter(node) {
|
|
3093
|
-
this.value = this.value.child();
|
|
3094
|
-
if (node.context) {
|
|
3095
|
-
this.handleScope(node.context, node.children);
|
|
3096
|
-
}
|
|
3097
|
-
if (node.index) {
|
|
3098
|
-
this.value.inits.add(node.index);
|
|
3099
|
-
}
|
|
3100
|
-
}
|
|
3101
|
-
eachLeave(node) {
|
|
3102
|
-
if (!node.else) {
|
|
3103
|
-
this.value = this.value.parent;
|
|
3104
|
-
}
|
|
3105
|
-
}
|
|
3106
|
-
awaitEnter(node) {
|
|
3107
|
-
var _a;
|
|
3108
|
-
this.value = this.value.child();
|
|
3109
|
-
if (node.value) {
|
|
3110
|
-
this.handleScope(node.value, (_a = node.then) === null || _a === void 0 ? void 0 : _a.children);
|
|
3111
|
-
}
|
|
3112
|
-
if (node.error) {
|
|
3113
|
-
this.handleScope(node.error, []);
|
|
3114
|
-
}
|
|
3115
|
-
}
|
|
3116
|
-
awaitPendingEnter(node, parent) {
|
|
3117
|
-
if (node.skip || parent.type !== 'AwaitBlock') {
|
|
3118
|
-
return;
|
|
3119
|
-
}
|
|
3120
|
-
// Reset inits, as pending can have no inits
|
|
3121
|
-
this.value.inits.clear();
|
|
3122
|
-
}
|
|
3123
|
-
awaitThenEnter(node, parent) {
|
|
3124
|
-
if (node.skip || parent.type !== 'AwaitBlock') {
|
|
3125
|
-
return;
|
|
3126
|
-
}
|
|
3127
|
-
// Reset inits, this time only taking the then
|
|
3128
|
-
// scope into account.
|
|
3129
|
-
this.value.inits.clear();
|
|
3130
|
-
if (parent.value) {
|
|
3131
|
-
this.handleScope(parent.value, node.children);
|
|
3132
|
-
}
|
|
3133
|
-
}
|
|
3134
|
-
awaitCatchEnter(node, parent) {
|
|
3135
|
-
if (node.skip || parent.type !== 'AwaitBlock') {
|
|
3136
|
-
return;
|
|
3137
|
-
}
|
|
3138
|
-
// Reset inits, this time only taking the error
|
|
3139
|
-
// scope into account.
|
|
3140
|
-
this.value.inits.clear();
|
|
3141
|
-
if (parent.error) {
|
|
3142
|
-
this.handleScope(parent.error, node.children);
|
|
3143
|
-
}
|
|
3144
|
-
}
|
|
3145
|
-
awaitLeave() {
|
|
3146
|
-
this.value = this.value.parent;
|
|
3147
|
-
}
|
|
3148
|
-
elseEnter(parent) {
|
|
3149
|
-
if (parent.type === 'EachBlock') {
|
|
3150
|
-
this.value = this.value.parent;
|
|
3151
|
-
}
|
|
3152
|
-
}
|
|
3153
|
-
componentOrSlotTemplateOrElementEnter(node) {
|
|
3154
|
-
var _a;
|
|
3155
|
-
const hasConstTags = (_a = node.children) === null || _a === void 0 ? void 0 : _a.some((child) => child.type === 'ConstTag');
|
|
3156
|
-
if (usesLet(node) || hasConstTags) {
|
|
3157
|
-
this.value = this.value.child();
|
|
3158
|
-
this.handleScope({}, node.children);
|
|
3159
|
-
}
|
|
3160
|
-
}
|
|
3161
|
-
componentOrSlotTemplateOrElementLeave(node) {
|
|
3162
|
-
if (usesLet(node)) {
|
|
3163
|
-
this.value = this.value.parent;
|
|
3164
|
-
}
|
|
3165
|
-
}
|
|
3166
|
-
handleScope(identifierDef, children) {
|
|
3167
|
-
if (isIdentifier(identifierDef)) {
|
|
3168
|
-
this.value.inits.add(identifierDef.name);
|
|
3169
|
-
}
|
|
3170
|
-
if (isDestructuringPatterns(identifierDef)) {
|
|
3171
|
-
// the node object is returned as-it with no mutation
|
|
3172
|
-
const identifiers = extract_identifiers(identifierDef);
|
|
3173
|
-
identifiers.forEach((id) => this.value.inits.add(id.name));
|
|
3174
|
-
}
|
|
3175
|
-
if (children === null || children === void 0 ? void 0 : children.length) {
|
|
3176
|
-
children.forEach((child) => {
|
|
3177
|
-
if (child.type === 'ConstTag') {
|
|
3178
|
-
const identifiers = extract_identifiers(child.expression.left);
|
|
3179
|
-
identifiers.forEach((id) => this.value.inits.add(id.name));
|
|
3180
|
-
}
|
|
3181
|
-
});
|
|
3182
|
-
}
|
|
1303
|
+
start: containerStart,
|
|
1304
|
+
end: containerEnd,
|
|
1305
|
+
name: tag,
|
|
1306
|
+
type: tag === 'style' ? 'Style' : 'Script',
|
|
1307
|
+
attributes: parseAttributes(match[3], containerStart + `<${tag}`.length),
|
|
1308
|
+
content: {
|
|
1309
|
+
type: 'Text',
|
|
1310
|
+
start,
|
|
1311
|
+
end,
|
|
1312
|
+
value: content,
|
|
1313
|
+
raw: content
|
|
1314
|
+
}
|
|
1315
|
+
});
|
|
3183
1316
|
}
|
|
1317
|
+
return matches;
|
|
3184
1318
|
}
|
|
3185
|
-
|
|
3186
|
-
|
|
3187
|
-
if (!node.data) {
|
|
3188
|
-
return;
|
|
3189
|
-
}
|
|
3190
|
-
const needsRemoves = ['}', '>'];
|
|
3191
|
-
for (const token of needsRemoves) {
|
|
3192
|
-
let index = node.data.indexOf(token);
|
|
3193
|
-
while (index >= 0) {
|
|
3194
|
-
str.remove(index + node.start, index + node.start + 1);
|
|
3195
|
-
index = node.data.indexOf(token, index + 1);
|
|
3196
|
-
}
|
|
3197
|
-
}
|
|
1319
|
+
function findVerbatimElements(htmlx) {
|
|
1320
|
+
return [...extractTag(htmlx, 'script'), ...extractTag(htmlx, 'style')];
|
|
3198
1321
|
}
|
|
3199
|
-
|
|
3200
|
-
|
|
3201
|
-
|
|
3202
|
-
|
|
3203
|
-
|
|
3204
|
-
|
|
3205
|
-
|
|
3206
|
-
|
|
3207
|
-
|
|
3208
|
-
|
|
3209
|
-
|
|
3210
|
-
|
|
3211
|
-
|
|
3212
|
-
|
|
3213
|
-
|
|
3214
|
-
str.overwrite(htmlx.indexOf(':', attr.start) + 1 + `${attr.name}`.length, attr.expression.start, `(${nodeType},(`);
|
|
3215
|
-
str.appendLeft(withTrailingPropertyAccess$1(str.original, attr.expression.end), ')))');
|
|
3216
|
-
if (isQuote(htmlx[attr.end - 1])) {
|
|
3217
|
-
str.remove(attr.end - 1, attr.end);
|
|
1322
|
+
function blankVerbatimContent(htmlx, verbatimElements) {
|
|
1323
|
+
let output = htmlx;
|
|
1324
|
+
for (const node of verbatimElements) {
|
|
1325
|
+
const content = node.content;
|
|
1326
|
+
if (content) {
|
|
1327
|
+
output =
|
|
1328
|
+
output.substring(0, content.start) +
|
|
1329
|
+
output
|
|
1330
|
+
.substring(content.start, content.end)
|
|
1331
|
+
// blank out the content
|
|
1332
|
+
.replace(/[^\n]/g, ' ')
|
|
1333
|
+
// excess blank space can make the svelte parser very slow (sec->min). break it up with comments (works in style/script)
|
|
1334
|
+
.replace(/[^\n][^\n][^\n][^\n]\n/g, '/**/\n') +
|
|
1335
|
+
output.substring(content.end);
|
|
1336
|
+
}
|
|
3218
1337
|
}
|
|
1338
|
+
return output;
|
|
3219
1339
|
}
|
|
3220
|
-
|
|
3221
|
-
|
|
3222
|
-
|
|
3223
|
-
const
|
|
3224
|
-
|
|
3225
|
-
|
|
1340
|
+
function parseHtmlx(htmlx, options) {
|
|
1341
|
+
//Svelte tries to parse style and script tags which doesn't play well with typescript, so we blank them out.
|
|
1342
|
+
//HTMLx spec says they should just be retained after processing as is, so this is fine
|
|
1343
|
+
const verbatimElements = findVerbatimElements(htmlx);
|
|
1344
|
+
const deconstructed = blankVerbatimContent(htmlx, verbatimElements);
|
|
1345
|
+
//extract the html content parsed as htmlx this excludes our script and style tags
|
|
1346
|
+
const parsingCode = (options === null || options === void 0 ? void 0 : options.emitOnTemplateError)
|
|
1347
|
+
? blankPossiblyErrorOperatorOrPropertyAccess(deconstructed)
|
|
1348
|
+
: deconstructed;
|
|
1349
|
+
const htmlxAst = compiler.parse(parsingCode).html;
|
|
1350
|
+
//restore our script and style tags as nodes to maintain validity with HTMLx
|
|
1351
|
+
for (const s of verbatimElements) {
|
|
1352
|
+
htmlxAst.children.push(s);
|
|
1353
|
+
htmlxAst.start = Math.min(htmlxAst.start, s.start);
|
|
1354
|
+
htmlxAst.end = Math.max(htmlxAst.end, s.end);
|
|
3226
1355
|
}
|
|
1356
|
+
return { htmlxAst, tags: verbatimElements };
|
|
3227
1357
|
}
|
|
3228
|
-
|
|
3229
|
-
|
|
3230
|
-
|
|
3231
|
-
|
|
3232
|
-
|
|
3233
|
-
|
|
3234
|
-
|
|
3235
|
-
|
|
3236
|
-
|
|
3237
|
-
|
|
3238
|
-
|
|
3239
|
-
|
|
3240
|
-
|
|
3241
|
-
|
|
3242
|
-
|
|
3243
|
-
|
|
3244
|
-
|
|
3245
|
-
|
|
3246
|
-
|
|
3247
|
-
|
|
3248
|
-
|
|
3249
|
-
|
|
3250
|
-
|
|
3251
|
-
|
|
3252
|
-
|
|
3253
|
-
|
|
3254
|
-
|
|
3255
|
-
|
|
3256
|
-
|
|
3257
|
-
case 'AwaitBlock':
|
|
3258
|
-
handleAwait$1(htmlx, str, node, ifScope, templateScopeManager);
|
|
3259
|
-
break;
|
|
3260
|
-
case 'PendingBlock':
|
|
3261
|
-
templateScopeManager.awaitPendingEnter(node, parent);
|
|
3262
|
-
handleAwaitPending(parent, htmlx, str, ifScope);
|
|
3263
|
-
break;
|
|
3264
|
-
case 'ThenBlock':
|
|
3265
|
-
templateScopeManager.awaitThenEnter(node, parent);
|
|
3266
|
-
handleAwaitThen(parent, htmlx, str, ifScope);
|
|
3267
|
-
break;
|
|
3268
|
-
case 'CatchBlock':
|
|
3269
|
-
templateScopeManager.awaitCatchEnter(node, parent);
|
|
3270
|
-
handleAwaitCatch(parent, htmlx, str, ifScope);
|
|
3271
|
-
break;
|
|
3272
|
-
case 'KeyBlock':
|
|
3273
|
-
handleKey$1(htmlx, str, node);
|
|
3274
|
-
break;
|
|
3275
|
-
case 'RawMustacheTag':
|
|
3276
|
-
handleRawHtml$1(htmlx, str, node);
|
|
3277
|
-
break;
|
|
3278
|
-
case 'DebugTag':
|
|
3279
|
-
handleDebug$1(htmlx, str, node);
|
|
3280
|
-
break;
|
|
3281
|
-
case 'InlineComponent':
|
|
3282
|
-
templateScopeManager.componentOrSlotTemplateOrElementEnter(node);
|
|
3283
|
-
handleComponent(htmlx, str, node, parent, ifScope, templateScopeManager.value);
|
|
3284
|
-
break;
|
|
3285
|
-
case 'Element':
|
|
3286
|
-
if (node.name === 'svelte:element') {
|
|
3287
|
-
handleSvelteTag(htmlx, str, node);
|
|
3288
|
-
}
|
|
3289
|
-
templateScopeManager.componentOrSlotTemplateOrElementEnter(node);
|
|
3290
|
-
handleElement(htmlx, str, node, parent, ifScope, templateScopeManager.value);
|
|
3291
|
-
break;
|
|
3292
|
-
case 'Comment':
|
|
3293
|
-
handleComment$1(str, node);
|
|
3294
|
-
break;
|
|
3295
|
-
case 'Binding':
|
|
3296
|
-
handleBinding$1(htmlx, str, node, parent);
|
|
3297
|
-
break;
|
|
3298
|
-
case 'Class':
|
|
3299
|
-
handleClassDirective$1(str, node);
|
|
3300
|
-
break;
|
|
3301
|
-
case 'StyleDirective':
|
|
3302
|
-
handleStyleDirective$1(str, node);
|
|
3303
|
-
break;
|
|
3304
|
-
case 'Action':
|
|
3305
|
-
handleActionDirective$1(htmlx, str, node, parent);
|
|
3306
|
-
break;
|
|
3307
|
-
case 'Transition':
|
|
3308
|
-
handleTransitionDirective$1(htmlx, str, node, parent);
|
|
3309
|
-
break;
|
|
3310
|
-
case 'Animation':
|
|
3311
|
-
handleAnimateDirective$1(htmlx, str, node, parent);
|
|
3312
|
-
break;
|
|
3313
|
-
case 'Attribute':
|
|
3314
|
-
handleAttribute$1(htmlx, str, node, parent, options.preserveAttributeCase);
|
|
3315
|
-
break;
|
|
3316
|
-
case 'EventHandler':
|
|
3317
|
-
handleEventHandler$1(htmlx, str, node, parent);
|
|
3318
|
-
break;
|
|
3319
|
-
case 'Options':
|
|
3320
|
-
handleSvelteTag(htmlx, str, node);
|
|
3321
|
-
break;
|
|
3322
|
-
case 'Window':
|
|
3323
|
-
handleSvelteTag(htmlx, str, node);
|
|
3324
|
-
break;
|
|
3325
|
-
case 'Head':
|
|
3326
|
-
handleSvelteTag(htmlx, str, node);
|
|
3327
|
-
break;
|
|
3328
|
-
case 'Body':
|
|
3329
|
-
handleSvelteTag(htmlx, str, node);
|
|
3330
|
-
break;
|
|
3331
|
-
case 'SlotTemplate':
|
|
3332
|
-
handleSvelteTag(htmlx, str, node);
|
|
3333
|
-
templateScopeManager.componentOrSlotTemplateOrElementEnter(node);
|
|
3334
|
-
handleSlot(htmlx, str, node, parent, getSlotName(node) || 'default', ifScope, templateScopeManager.value);
|
|
3335
|
-
break;
|
|
3336
|
-
case 'Text':
|
|
3337
|
-
handleText$1(str, node);
|
|
3338
|
-
break;
|
|
3339
|
-
}
|
|
3340
|
-
if (onWalk) {
|
|
3341
|
-
onWalk(node, parent, prop, index);
|
|
3342
|
-
}
|
|
3343
|
-
}
|
|
3344
|
-
catch (e) {
|
|
3345
|
-
console.error('Error walking node ', node, e);
|
|
3346
|
-
throw e;
|
|
3347
|
-
}
|
|
3348
|
-
},
|
|
3349
|
-
leave: (node, parent, prop, index) => {
|
|
3350
|
-
try {
|
|
3351
|
-
switch (node.type) {
|
|
3352
|
-
case 'IfBlock':
|
|
3353
|
-
if (!node.elseif) {
|
|
3354
|
-
ifScope = ifScope.getParent();
|
|
3355
|
-
}
|
|
3356
|
-
break;
|
|
3357
|
-
case 'EachBlock':
|
|
3358
|
-
templateScopeManager.eachLeave(node);
|
|
3359
|
-
break;
|
|
3360
|
-
case 'AwaitBlock':
|
|
3361
|
-
templateScopeManager.awaitLeave();
|
|
3362
|
-
break;
|
|
3363
|
-
case 'InlineComponent':
|
|
3364
|
-
case 'Element':
|
|
3365
|
-
case 'SlotTemplate':
|
|
3366
|
-
templateScopeManager.componentOrSlotTemplateOrElementLeave(node);
|
|
3367
|
-
break;
|
|
3368
|
-
}
|
|
3369
|
-
if (onLeave) {
|
|
3370
|
-
onLeave(node, parent, prop, index);
|
|
1358
|
+
const possibleOperatorOrPropertyAccess = new Set([
|
|
1359
|
+
'.',
|
|
1360
|
+
'?',
|
|
1361
|
+
'*',
|
|
1362
|
+
'~',
|
|
1363
|
+
'=',
|
|
1364
|
+
'<',
|
|
1365
|
+
'!',
|
|
1366
|
+
'&',
|
|
1367
|
+
'^',
|
|
1368
|
+
'|',
|
|
1369
|
+
',',
|
|
1370
|
+
'+',
|
|
1371
|
+
'-'
|
|
1372
|
+
]);
|
|
1373
|
+
function blankPossiblyErrorOperatorOrPropertyAccess(htmlx) {
|
|
1374
|
+
let index = htmlx.indexOf('}');
|
|
1375
|
+
let lastIndex = 0;
|
|
1376
|
+
const { length } = htmlx;
|
|
1377
|
+
while (index < length && index >= 0) {
|
|
1378
|
+
let backwardIndex = index - 1;
|
|
1379
|
+
while (backwardIndex > lastIndex) {
|
|
1380
|
+
const char = htmlx.charAt(backwardIndex);
|
|
1381
|
+
if (possibleOperatorOrPropertyAccess.has(char)) {
|
|
1382
|
+
const isPlusOrMinus = char === '+' || char === '-';
|
|
1383
|
+
const isIncrementOrDecrement = isPlusOrMinus && htmlx.charAt(backwardIndex - 1) === char;
|
|
1384
|
+
if (isIncrementOrDecrement) {
|
|
1385
|
+
backwardIndex -= 2;
|
|
1386
|
+
continue;
|
|
3371
1387
|
}
|
|
1388
|
+
htmlx =
|
|
1389
|
+
htmlx.substring(0, backwardIndex) + ' ' + htmlx.substring(backwardIndex + 1);
|
|
3372
1390
|
}
|
|
3373
|
-
|
|
3374
|
-
|
|
3375
|
-
throw e;
|
|
1391
|
+
else if (!/\s/.test(char)) {
|
|
1392
|
+
break;
|
|
3376
1393
|
}
|
|
1394
|
+
backwardIndex--;
|
|
3377
1395
|
}
|
|
3378
|
-
|
|
1396
|
+
lastIndex = index;
|
|
1397
|
+
index = htmlx.indexOf('}', index + 1);
|
|
1398
|
+
}
|
|
1399
|
+
return htmlx;
|
|
3379
1400
|
}
|
|
3380
1401
|
|
|
3381
1402
|
/**
|
|
@@ -3567,6 +1588,16 @@ function handleAnimateDirective(str, attr, element) {
|
|
|
3567
1588
|
|
|
3568
1589
|
var svgAttributes = 'accent-height accumulate additive alignment-baseline allowReorder alphabetic amplitude arabic-form ascent attributeName attributeType autoReverse azimuth baseFrequency baseline-shift baseProfile bbox begin bias by calcMode cap-height class clip clipPathUnits clip-path clip-rule color color-interpolation color-interpolation-filters color-profile color-rendering contentScriptType contentStyleType cursor cx cy d decelerate descent diffuseConstant direction display divisor dominant-baseline dur dx dy edgeMode elevation enable-background end exponent externalResourcesRequired fill fill-opacity fill-rule filter filterRes filterUnits flood-color flood-opacity font-family font-size font-size-adjust font-stretch font-style font-variant font-weight format from fr fx fy g1 g2 glyph-name glyph-orientation-horizontal glyph-orientation-vertical glyphRef gradientTransform gradientUnits hanging height href horiz-adv-x horiz-origin-x id ideographic image-rendering in in2 intercept k k1 k2 k3 k4 kernelMatrix kernelUnitLength kerning keyPoints keySplines keyTimes lang lengthAdjust letter-spacing lighting-color limitingConeAngle local marker-end marker-mid marker-start markerHeight markerUnits markerWidth mask maskContentUnits maskUnits mathematical max media method min mode name numOctaves offset onabort onactivate onbegin onclick onend onerror onfocusin onfocusout onload onmousedown onmousemove onmouseout onmouseover onmouseup onrepeat onresize onscroll onunload opacity operator order orient orientation origin overflow overline-position overline-thickness panose-1 paint-order pathLength patternContentUnits patternTransform patternUnits pointer-events points pointsAtX pointsAtY pointsAtZ preserveAlpha preserveAspectRatio primitiveUnits r radius refX refY rendering-intent repeatCount repeatDur requiredExtensions requiredFeatures restart result rotate rx ry scale seed shape-rendering slope spacing specularConstant specularExponent speed spreadMethod startOffset stdDeviation stemh stemv stitchTiles stop-color stop-opacity strikethrough-position strikethrough-thickness string stroke stroke-dasharray stroke-dashoffset stroke-linecap stroke-linejoin stroke-miterlimit stroke-opacity stroke-width style surfaceScale systemLanguage tabindex tableValues target targetX targetY text-anchor text-decoration text-rendering textLength to transform type u1 u2 underline-position underline-thickness unicode unicode-bidi unicode-range units-per-em v-alphabetic v-hanging v-ideographic v-mathematical values version vert-adv-y vert-origin-x vert-origin-y viewBox viewTarget visibility width widths word-spacing writing-mode x x-height x1 x2 xChannelSelector xlink:actuate xlink:arcrole xlink:href xlink:role xlink:show xlink:title xlink:type xml:base xml:lang xml:space y y1 y2 yChannelSelector z zoomAndPan'.split(' ');
|
|
3569
1590
|
|
|
1591
|
+
const IGNORE_START_COMMENT = '/*Ωignore_startΩ*/';
|
|
1592
|
+
const IGNORE_END_COMMENT = '/*Ωignore_endΩ*/';
|
|
1593
|
+
/**
|
|
1594
|
+
* Surrounds given string with a start/end comment which marks it
|
|
1595
|
+
* to be ignored by tooling.
|
|
1596
|
+
*/
|
|
1597
|
+
function surroundWithIgnoreComments(str) {
|
|
1598
|
+
return IGNORE_START_COMMENT + str + IGNORE_END_COMMENT;
|
|
1599
|
+
}
|
|
1600
|
+
|
|
3570
1601
|
const voidTags = 'area,base,br,col,embed,hr,img,input,link,meta,param,source,track,wbr'.split(',');
|
|
3571
1602
|
/**
|
|
3572
1603
|
* Handles HTML elements as well as svelte:options, svelte:head, svelte:window, svelte:body, svelte:element
|
|
@@ -4976,9 +3007,9 @@ function extractIdentifiers(node, identifiers = []) {
|
|
|
4976
3007
|
else if (ts.isBindingElement(node)) {
|
|
4977
3008
|
extractIdentifiers(node.name, identifiers);
|
|
4978
3009
|
}
|
|
4979
|
-
else if (isMember(node)) {
|
|
3010
|
+
else if (isMember$1(node)) {
|
|
4980
3011
|
let object = node;
|
|
4981
|
-
while (isMember(object)) {
|
|
3012
|
+
while (isMember$1(object)) {
|
|
4982
3013
|
object = object.expression;
|
|
4983
3014
|
}
|
|
4984
3015
|
if (ts.isIdentifier(object)) {
|
|
@@ -5020,7 +3051,7 @@ function extractIdentifiers(node, identifiers = []) {
|
|
|
5020
3051
|
}
|
|
5021
3052
|
return identifiers;
|
|
5022
3053
|
}
|
|
5023
|
-
function isMember(node) {
|
|
3054
|
+
function isMember$1(node) {
|
|
5024
3055
|
return ts.isElementAccessExpression(node) || ts.isPropertyAccessExpression(node);
|
|
5025
3056
|
}
|
|
5026
3057
|
/**
|
|
@@ -5778,9 +3809,9 @@ class ExportedNames {
|
|
|
5778
3809
|
* Creates a string from the collected props
|
|
5779
3810
|
*
|
|
5780
3811
|
* @param isTsFile Whether this is a TypeScript file or not.
|
|
5781
|
-
* @param uses$$
|
|
3812
|
+
* @param uses$$propsOr$$restProps whether the file references the $$props or $$restProps variable
|
|
5782
3813
|
*/
|
|
5783
|
-
createPropsStr(isTsFile, uses$$
|
|
3814
|
+
createPropsStr(isTsFile, uses$$propsOr$$restProps) {
|
|
5784
3815
|
const names = Array.from(this.exports.entries());
|
|
5785
3816
|
if (this.uses$$Props) {
|
|
5786
3817
|
const lets = names.filter(([, { isLet }]) => isLet);
|
|
@@ -5795,7 +3826,7 @@ class ExportedNames {
|
|
|
5795
3826
|
this.createReturnElementsType(lets).join(',') +
|
|
5796
3827
|
'}>(__sveltets_2_any("") as $$Props), ' +
|
|
5797
3828
|
'...__sveltets_2_ensureRightProps<' +
|
|
5798
|
-
(uses$$
|
|
3829
|
+
(uses$$propsOr$$restProps ? 'Partial<$$Props>' : '$$Props') +
|
|
5799
3830
|
'>({' +
|
|
5800
3831
|
this.createReturnElements(lets, false).join(',') +
|
|
5801
3832
|
'}), ...{} as unknown as $$Props, ...{' +
|
|
@@ -5807,7 +3838,7 @@ class ExportedNames {
|
|
|
5807
3838
|
this.createReturnElementsType(others).join(',') +
|
|
5808
3839
|
'}}');
|
|
5809
3840
|
}
|
|
5810
|
-
if (names.length === 0 && !uses$$
|
|
3841
|
+
if (names.length === 0 && !uses$$propsOr$$restProps) {
|
|
5811
3842
|
// Necessary, because {} roughly equals to any
|
|
5812
3843
|
return isTsFile
|
|
5813
3844
|
? '{} as Record<string, never>'
|
|
@@ -5848,6 +3879,295 @@ class ExportedNames {
|
|
|
5848
3879
|
}
|
|
5849
3880
|
}
|
|
5850
3881
|
|
|
3882
|
+
function isMember(parent, prop) {
|
|
3883
|
+
return parent.type == 'MemberExpression' && prop == 'property';
|
|
3884
|
+
}
|
|
3885
|
+
function isObjectKey(parent, prop) {
|
|
3886
|
+
return parent.type == 'Property' && prop == 'key';
|
|
3887
|
+
}
|
|
3888
|
+
function isObjectValue(parent, prop) {
|
|
3889
|
+
return parent.type == 'Property' && prop == 'value';
|
|
3890
|
+
}
|
|
3891
|
+
function isObjectValueShortHand(property) {
|
|
3892
|
+
const { value, key } = property;
|
|
3893
|
+
return value && isIdentifier(value) && key.start === value.start && key.end == value.end;
|
|
3894
|
+
}
|
|
3895
|
+
function attributeValueIsString(attr) {
|
|
3896
|
+
var _a;
|
|
3897
|
+
return attr.value.length !== 1 || ((_a = attr.value[0]) === null || _a === void 0 ? void 0 : _a.type) === 'Text';
|
|
3898
|
+
}
|
|
3899
|
+
function isDestructuringPatterns(node) {
|
|
3900
|
+
return node.type === 'ArrayPattern' || node.type === 'ObjectPattern';
|
|
3901
|
+
}
|
|
3902
|
+
function isIdentifier(node) {
|
|
3903
|
+
return node.type === 'Identifier';
|
|
3904
|
+
}
|
|
3905
|
+
function getSlotName(child) {
|
|
3906
|
+
var _a, _b;
|
|
3907
|
+
const slot = (_a = child.attributes) === null || _a === void 0 ? void 0 : _a.find((a) => a.name == 'slot');
|
|
3908
|
+
return (_b = slot === null || slot === void 0 ? void 0 : slot.value) === null || _b === void 0 ? void 0 : _b[0].raw;
|
|
3909
|
+
}
|
|
3910
|
+
|
|
3911
|
+
// @ts-check
|
|
3912
|
+
/** @typedef { import('estree').BaseNode} BaseNode */
|
|
3913
|
+
|
|
3914
|
+
/** @typedef {{
|
|
3915
|
+
skip: () => void;
|
|
3916
|
+
remove: () => void;
|
|
3917
|
+
replace: (node: BaseNode) => void;
|
|
3918
|
+
}} WalkerContext */
|
|
3919
|
+
|
|
3920
|
+
class WalkerBase {
|
|
3921
|
+
constructor() {
|
|
3922
|
+
/** @type {boolean} */
|
|
3923
|
+
this.should_skip = false;
|
|
3924
|
+
|
|
3925
|
+
/** @type {boolean} */
|
|
3926
|
+
this.should_remove = false;
|
|
3927
|
+
|
|
3928
|
+
/** @type {BaseNode | null} */
|
|
3929
|
+
this.replacement = null;
|
|
3930
|
+
|
|
3931
|
+
/** @type {WalkerContext} */
|
|
3932
|
+
this.context = {
|
|
3933
|
+
skip: () => (this.should_skip = true),
|
|
3934
|
+
remove: () => (this.should_remove = true),
|
|
3935
|
+
replace: (node) => (this.replacement = node)
|
|
3936
|
+
};
|
|
3937
|
+
}
|
|
3938
|
+
|
|
3939
|
+
/**
|
|
3940
|
+
*
|
|
3941
|
+
* @param {any} parent
|
|
3942
|
+
* @param {string} prop
|
|
3943
|
+
* @param {number} index
|
|
3944
|
+
* @param {BaseNode} node
|
|
3945
|
+
*/
|
|
3946
|
+
replace(parent, prop, index, node) {
|
|
3947
|
+
if (parent) {
|
|
3948
|
+
if (index !== null) {
|
|
3949
|
+
parent[prop][index] = node;
|
|
3950
|
+
} else {
|
|
3951
|
+
parent[prop] = node;
|
|
3952
|
+
}
|
|
3953
|
+
}
|
|
3954
|
+
}
|
|
3955
|
+
|
|
3956
|
+
/**
|
|
3957
|
+
*
|
|
3958
|
+
* @param {any} parent
|
|
3959
|
+
* @param {string} prop
|
|
3960
|
+
* @param {number} index
|
|
3961
|
+
*/
|
|
3962
|
+
remove(parent, prop, index) {
|
|
3963
|
+
if (parent) {
|
|
3964
|
+
if (index !== null) {
|
|
3965
|
+
parent[prop].splice(index, 1);
|
|
3966
|
+
} else {
|
|
3967
|
+
delete parent[prop];
|
|
3968
|
+
}
|
|
3969
|
+
}
|
|
3970
|
+
}
|
|
3971
|
+
}
|
|
3972
|
+
|
|
3973
|
+
// @ts-check
|
|
3974
|
+
|
|
3975
|
+
/** @typedef { import('estree').BaseNode} BaseNode */
|
|
3976
|
+
/** @typedef { import('./walker.js').WalkerContext} WalkerContext */
|
|
3977
|
+
|
|
3978
|
+
/** @typedef {(
|
|
3979
|
+
* this: WalkerContext,
|
|
3980
|
+
* node: BaseNode,
|
|
3981
|
+
* parent: BaseNode,
|
|
3982
|
+
* key: string,
|
|
3983
|
+
* index: number
|
|
3984
|
+
* ) => void} SyncHandler */
|
|
3985
|
+
|
|
3986
|
+
class SyncWalker extends WalkerBase {
|
|
3987
|
+
/**
|
|
3988
|
+
*
|
|
3989
|
+
* @param {SyncHandler} enter
|
|
3990
|
+
* @param {SyncHandler} leave
|
|
3991
|
+
*/
|
|
3992
|
+
constructor(enter, leave) {
|
|
3993
|
+
super();
|
|
3994
|
+
|
|
3995
|
+
/** @type {SyncHandler} */
|
|
3996
|
+
this.enter = enter;
|
|
3997
|
+
|
|
3998
|
+
/** @type {SyncHandler} */
|
|
3999
|
+
this.leave = leave;
|
|
4000
|
+
}
|
|
4001
|
+
|
|
4002
|
+
/**
|
|
4003
|
+
*
|
|
4004
|
+
* @param {BaseNode} node
|
|
4005
|
+
* @param {BaseNode} parent
|
|
4006
|
+
* @param {string} [prop]
|
|
4007
|
+
* @param {number} [index]
|
|
4008
|
+
* @returns {BaseNode}
|
|
4009
|
+
*/
|
|
4010
|
+
visit(node, parent, prop, index) {
|
|
4011
|
+
if (node) {
|
|
4012
|
+
if (this.enter) {
|
|
4013
|
+
const _should_skip = this.should_skip;
|
|
4014
|
+
const _should_remove = this.should_remove;
|
|
4015
|
+
const _replacement = this.replacement;
|
|
4016
|
+
this.should_skip = false;
|
|
4017
|
+
this.should_remove = false;
|
|
4018
|
+
this.replacement = null;
|
|
4019
|
+
|
|
4020
|
+
this.enter.call(this.context, node, parent, prop, index);
|
|
4021
|
+
|
|
4022
|
+
if (this.replacement) {
|
|
4023
|
+
node = this.replacement;
|
|
4024
|
+
this.replace(parent, prop, index, node);
|
|
4025
|
+
}
|
|
4026
|
+
|
|
4027
|
+
if (this.should_remove) {
|
|
4028
|
+
this.remove(parent, prop, index);
|
|
4029
|
+
}
|
|
4030
|
+
|
|
4031
|
+
const skipped = this.should_skip;
|
|
4032
|
+
const removed = this.should_remove;
|
|
4033
|
+
|
|
4034
|
+
this.should_skip = _should_skip;
|
|
4035
|
+
this.should_remove = _should_remove;
|
|
4036
|
+
this.replacement = _replacement;
|
|
4037
|
+
|
|
4038
|
+
if (skipped) return node;
|
|
4039
|
+
if (removed) return null;
|
|
4040
|
+
}
|
|
4041
|
+
|
|
4042
|
+
for (const key in node) {
|
|
4043
|
+
const value = node[key];
|
|
4044
|
+
|
|
4045
|
+
if (typeof value !== "object") {
|
|
4046
|
+
continue;
|
|
4047
|
+
} else if (Array.isArray(value)) {
|
|
4048
|
+
for (let i = 0; i < value.length; i += 1) {
|
|
4049
|
+
if (value[i] !== null && typeof value[i].type === 'string') {
|
|
4050
|
+
if (!this.visit(value[i], node, key, i)) {
|
|
4051
|
+
// removed
|
|
4052
|
+
i--;
|
|
4053
|
+
}
|
|
4054
|
+
}
|
|
4055
|
+
}
|
|
4056
|
+
} else if (value !== null && typeof value.type === "string") {
|
|
4057
|
+
this.visit(value, node, key, null);
|
|
4058
|
+
}
|
|
4059
|
+
}
|
|
4060
|
+
|
|
4061
|
+
if (this.leave) {
|
|
4062
|
+
const _replacement = this.replacement;
|
|
4063
|
+
const _should_remove = this.should_remove;
|
|
4064
|
+
this.replacement = null;
|
|
4065
|
+
this.should_remove = false;
|
|
4066
|
+
|
|
4067
|
+
this.leave.call(this.context, node, parent, prop, index);
|
|
4068
|
+
|
|
4069
|
+
if (this.replacement) {
|
|
4070
|
+
node = this.replacement;
|
|
4071
|
+
this.replace(parent, prop, index, node);
|
|
4072
|
+
}
|
|
4073
|
+
|
|
4074
|
+
if (this.should_remove) {
|
|
4075
|
+
this.remove(parent, prop, index);
|
|
4076
|
+
}
|
|
4077
|
+
|
|
4078
|
+
const removed = this.should_remove;
|
|
4079
|
+
|
|
4080
|
+
this.replacement = _replacement;
|
|
4081
|
+
this.should_remove = _should_remove;
|
|
4082
|
+
|
|
4083
|
+
if (removed) return null;
|
|
4084
|
+
}
|
|
4085
|
+
}
|
|
4086
|
+
|
|
4087
|
+
return node;
|
|
4088
|
+
}
|
|
4089
|
+
}
|
|
4090
|
+
|
|
4091
|
+
// @ts-check
|
|
4092
|
+
|
|
4093
|
+
/** @typedef { import('estree').BaseNode} BaseNode */
|
|
4094
|
+
/** @typedef { import('./sync.js').SyncHandler} SyncHandler */
|
|
4095
|
+
/** @typedef { import('./async.js').AsyncHandler} AsyncHandler */
|
|
4096
|
+
|
|
4097
|
+
/**
|
|
4098
|
+
*
|
|
4099
|
+
* @param {BaseNode} ast
|
|
4100
|
+
* @param {{
|
|
4101
|
+
* enter?: SyncHandler
|
|
4102
|
+
* leave?: SyncHandler
|
|
4103
|
+
* }} walker
|
|
4104
|
+
* @returns {BaseNode}
|
|
4105
|
+
*/
|
|
4106
|
+
function walk(ast, { enter, leave }) {
|
|
4107
|
+
const instance = new SyncWalker(enter, leave);
|
|
4108
|
+
return instance.visit(ast, null);
|
|
4109
|
+
}
|
|
4110
|
+
|
|
4111
|
+
/**
|
|
4112
|
+
*
|
|
4113
|
+
* @param {Node} param
|
|
4114
|
+
* @param {Identifier[]} nodes
|
|
4115
|
+
* @returns {Identifier[]}
|
|
4116
|
+
*/
|
|
4117
|
+
function extract_identifiers(param, nodes = []) {
|
|
4118
|
+
switch (param.type) {
|
|
4119
|
+
case 'Identifier':
|
|
4120
|
+
nodes.push(param);
|
|
4121
|
+
break;
|
|
4122
|
+
|
|
4123
|
+
case 'MemberExpression':
|
|
4124
|
+
let object = param;
|
|
4125
|
+
while (object.type === 'MemberExpression') {
|
|
4126
|
+
object = /** @type {any} */ (object.object);
|
|
4127
|
+
}
|
|
4128
|
+
nodes.push(/** @type {any} */ (object));
|
|
4129
|
+
break;
|
|
4130
|
+
|
|
4131
|
+
case 'ObjectPattern':
|
|
4132
|
+
/**
|
|
4133
|
+
*
|
|
4134
|
+
* @param {Property | RestElement} prop
|
|
4135
|
+
*/
|
|
4136
|
+
const handle_prop = (prop) => {
|
|
4137
|
+
if (prop.type === 'RestElement') {
|
|
4138
|
+
extract_identifiers(prop.argument, nodes);
|
|
4139
|
+
} else {
|
|
4140
|
+
extract_identifiers(prop.value, nodes);
|
|
4141
|
+
}
|
|
4142
|
+
};
|
|
4143
|
+
|
|
4144
|
+
param.properties.forEach(handle_prop);
|
|
4145
|
+
break;
|
|
4146
|
+
|
|
4147
|
+
case 'ArrayPattern':
|
|
4148
|
+
/**
|
|
4149
|
+
*
|
|
4150
|
+
* @param {Node} element
|
|
4151
|
+
*/
|
|
4152
|
+
const handle_element = (element) => {
|
|
4153
|
+
if (element) extract_identifiers(element, nodes);
|
|
4154
|
+
};
|
|
4155
|
+
|
|
4156
|
+
param.elements.forEach(handle_element);
|
|
4157
|
+
break;
|
|
4158
|
+
|
|
4159
|
+
case 'RestElement':
|
|
4160
|
+
extract_identifiers(param.argument, nodes);
|
|
4161
|
+
break;
|
|
4162
|
+
|
|
4163
|
+
case 'AssignmentPattern':
|
|
4164
|
+
extract_identifiers(param.left, nodes);
|
|
4165
|
+
break;
|
|
4166
|
+
}
|
|
4167
|
+
|
|
4168
|
+
return nodes;
|
|
4169
|
+
}
|
|
4170
|
+
|
|
5851
4171
|
function handleScopeAndResolveForSlot({ identifierDef, initExpression, owner, slotHandler, templateScope }) {
|
|
5852
4172
|
if (isIdentifier(identifierDef)) {
|
|
5853
4173
|
templateScope.add(identifierDef, owner);
|
|
@@ -6014,6 +4334,20 @@ class Scripts {
|
|
|
6014
4334
|
}
|
|
6015
4335
|
}
|
|
6016
4336
|
|
|
4337
|
+
/**
|
|
4338
|
+
* Get the constructor type of a component node
|
|
4339
|
+
* @param node The component node to infer the this type from
|
|
4340
|
+
* @param thisValue If node is svelte:component, you may pass the value
|
|
4341
|
+
* of this={..} to use that instead of the more general componentType
|
|
4342
|
+
*/
|
|
4343
|
+
function getTypeForComponent(node) {
|
|
4344
|
+
if (node.name === 'svelte:component' || node.name === 'svelte:self') {
|
|
4345
|
+
return '__sveltets_1_componentType()';
|
|
4346
|
+
}
|
|
4347
|
+
else {
|
|
4348
|
+
return node.name;
|
|
4349
|
+
}
|
|
4350
|
+
}
|
|
6017
4351
|
function attributeStrValueAsJsExpression(attr) {
|
|
6018
4352
|
if (attr.value.length == 0) {
|
|
6019
4353
|
return "''"; //wut?
|
|
@@ -6140,7 +4474,7 @@ class SlotHandler {
|
|
|
6140
4474
|
enter(node, parent, prop) {
|
|
6141
4475
|
if (node.type === 'Identifier') {
|
|
6142
4476
|
if (parent) {
|
|
6143
|
-
if (isMember
|
|
4477
|
+
if (isMember(parent, prop)) {
|
|
6144
4478
|
return;
|
|
6145
4479
|
}
|
|
6146
4480
|
if (isObjectKey(parent, prop)) {
|
|
@@ -6267,7 +4601,7 @@ class Stores {
|
|
|
6267
4601
|
this.scope.current.declared.add(node.name);
|
|
6268
4602
|
}
|
|
6269
4603
|
else {
|
|
6270
|
-
if (isMember
|
|
4604
|
+
if (isMember(parent, prop) && !parent.computed) {
|
|
6271
4605
|
return;
|
|
6272
4606
|
}
|
|
6273
4607
|
if (isObjectKey(parent, prop)) {
|
|
@@ -6882,7 +5216,7 @@ function transformInterfacesToTypes(tsAst, str, astOffset, movedNodes) {
|
|
|
6882
5216
|
});
|
|
6883
5217
|
}
|
|
6884
5218
|
|
|
6885
|
-
function processModuleScriptTag(str, script, implicitStoreValues
|
|
5219
|
+
function processModuleScriptTag(str, script, implicitStoreValues) {
|
|
6886
5220
|
const htmlx = str.original;
|
|
6887
5221
|
const scriptContent = htmlx.substring(script.content.start, script.content.end);
|
|
6888
5222
|
const tsAst = ts.createSourceFile('component.module.ts.svelte', scriptContent, ts.ScriptTarget.Latest, true, ts.ScriptKind.TS);
|
|
@@ -6902,10 +5236,10 @@ function processModuleScriptTag(str, script, implicitStoreValues, useNewTransfor
|
|
|
6902
5236
|
implicitStoreValues.modifyCode(astOffset, str);
|
|
6903
5237
|
const scriptStartTagEnd = htmlx.indexOf('>', script.start) + 1;
|
|
6904
5238
|
const scriptEndTagStart = htmlx.lastIndexOf('<', script.end - 1);
|
|
6905
|
-
str.overwrite(script.start, scriptStartTagEnd,
|
|
5239
|
+
str.overwrite(script.start, scriptStartTagEnd, ';', {
|
|
6906
5240
|
contentOnly: true
|
|
6907
5241
|
});
|
|
6908
|
-
str.overwrite(scriptEndTagStart, script.end,
|
|
5242
|
+
str.overwrite(scriptEndTagStart, script.end, ';', {
|
|
6909
5243
|
contentOnly: true
|
|
6910
5244
|
});
|
|
6911
5245
|
}
|
|
@@ -7079,7 +5413,6 @@ function classNameFromFilename(filename, appendSuffix) {
|
|
|
7079
5413
|
}
|
|
7080
5414
|
|
|
7081
5415
|
function createRenderFunction({ str, scriptTag, scriptDestination, slots, events, exportedNames, isTsFile, uses$$props, uses$$restProps, uses$$slots, uses$$SlotsInterface, generics, mode }) {
|
|
7082
|
-
const useNewTransformation = mode === 'ts';
|
|
7083
5416
|
const htmlx = str.original;
|
|
7084
5417
|
let propsDecl = '';
|
|
7085
5418
|
if (uses$$props) {
|
|
@@ -7098,30 +5431,24 @@ function createRenderFunction({ str, scriptTag, scriptDestination, slots, events
|
|
|
7098
5431
|
}
|
|
7099
5432
|
const slotsDeclaration = slots.size > 0 && mode !== 'dts'
|
|
7100
5433
|
? '\n' +
|
|
7101
|
-
surroundWithIgnoreComments(
|
|
7102
|
-
? '
|
|
7103
|
-
|
|
7104
|
-
'();'
|
|
7105
|
-
: ';const __sveltets_ensureSlot = __sveltets_1_createEnsureSlot' +
|
|
7106
|
-
(uses$$SlotsInterface ? '<$$Slots>' : '') +
|
|
7107
|
-
'();')
|
|
5434
|
+
surroundWithIgnoreComments(';const __sveltets_createSlot = __sveltets_2_createCreateSlot' +
|
|
5435
|
+
(uses$$SlotsInterface ? '<$$Slots>' : '') +
|
|
5436
|
+
'();')
|
|
7108
5437
|
: '';
|
|
7109
5438
|
if (scriptTag) {
|
|
7110
5439
|
//I couldn't get magicstring to let me put the script before the <> we prepend during conversion of the template to jsx, so we just close it instead
|
|
7111
5440
|
const scriptTagEnd = htmlx.lastIndexOf('>', scriptTag.content.start) + 1;
|
|
7112
|
-
str.overwrite(scriptTag.start, scriptTag.start + 1,
|
|
5441
|
+
str.overwrite(scriptTag.start, scriptTag.start + 1, ';');
|
|
7113
5442
|
str.overwrite(scriptTag.start + 1, scriptTagEnd, `function render${generics.toDefinitionString(true)}() {${propsDecl}\n`);
|
|
7114
5443
|
const scriptEndTagStart = htmlx.lastIndexOf('<', scriptTag.end - 1);
|
|
7115
5444
|
// wrap template with callback
|
|
7116
|
-
str.overwrite(scriptEndTagStart, scriptTag.end,
|
|
7117
|
-
? `${slotsDeclaration};\nasync () => {`
|
|
7118
|
-
: `${slotsDeclaration};\n() => (<>`, {
|
|
5445
|
+
str.overwrite(scriptEndTagStart, scriptTag.end, `${slotsDeclaration};\nasync () => {`, {
|
|
7119
5446
|
contentOnly: true
|
|
7120
5447
|
});
|
|
7121
5448
|
}
|
|
7122
5449
|
else {
|
|
7123
|
-
str.prependRight(scriptDestination,
|
|
7124
|
-
`${propsDecl}${slotsDeclaration}\
|
|
5450
|
+
str.prependRight(scriptDestination, `;function render${generics.toDefinitionString(true)}() {` +
|
|
5451
|
+
`${propsDecl}${slotsDeclaration}\nasync () => {`);
|
|
7125
5452
|
}
|
|
7126
5453
|
const slotsAsDef = uses$$SlotsInterface
|
|
7127
5454
|
? '{} as unknown as $$Slots'
|
|
@@ -7137,23 +5464,17 @@ function createRenderFunction({ str, scriptTag, scriptDestination, slots, events
|
|
|
7137
5464
|
})
|
|
7138
5465
|
.join(', ') +
|
|
7139
5466
|
'}';
|
|
7140
|
-
const returnString = `\nreturn { props: ${exportedNames.createPropsStr(isTsFile, uses$$props)}` +
|
|
5467
|
+
const returnString = `\nreturn { props: ${exportedNames.createPropsStr(isTsFile, uses$$props || uses$$restProps)}` +
|
|
7141
5468
|
`, slots: ${slotsAsDef}` +
|
|
7142
5469
|
`, events: ${events.toDefString()} }}`;
|
|
7143
5470
|
// wrap template with callback
|
|
7144
|
-
|
|
7145
|
-
str.append('};');
|
|
7146
|
-
}
|
|
7147
|
-
else if (scriptTag) {
|
|
7148
|
-
str.append(');');
|
|
7149
|
-
}
|
|
5471
|
+
str.append('};');
|
|
7150
5472
|
str.append(returnString);
|
|
7151
5473
|
}
|
|
7152
5474
|
|
|
7153
5475
|
function processSvelteTemplate(str, options) {
|
|
7154
5476
|
const { htmlxAst, tags } = parseHtmlx(str.original, {
|
|
7155
|
-
...options
|
|
7156
|
-
useNewTransformation: (options === null || options === void 0 ? void 0 : options.mode) === 'ts'
|
|
5477
|
+
...options
|
|
7157
5478
|
});
|
|
7158
5479
|
let uses$$props = false;
|
|
7159
5480
|
let uses$$restProps = false;
|
|
@@ -7337,17 +5658,10 @@ function processSvelteTemplate(str, options) {
|
|
|
7337
5658
|
break;
|
|
7338
5659
|
}
|
|
7339
5660
|
};
|
|
7340
|
-
|
|
7341
|
-
|
|
7342
|
-
|
|
7343
|
-
|
|
7344
|
-
});
|
|
7345
|
-
}
|
|
7346
|
-
else {
|
|
7347
|
-
convertHtmlxToJsx$1(str, htmlxAst, onHtmlxWalk, onHtmlxLeave, {
|
|
7348
|
-
preserveAttributeCase: (options === null || options === void 0 ? void 0 : options.namespace) == 'foreign'
|
|
7349
|
-
});
|
|
7350
|
-
}
|
|
5661
|
+
convertHtmlxToJsx(str, htmlxAst, onHtmlxWalk, onHtmlxLeave, {
|
|
5662
|
+
preserveAttributeCase: (options === null || options === void 0 ? void 0 : options.namespace) == 'foreign',
|
|
5663
|
+
typingsNamespace: options.typingsNamespace
|
|
5664
|
+
});
|
|
7351
5665
|
// resolve scripts
|
|
7352
5666
|
const { scriptTag, moduleScriptTag } = scripts.getTopLevelScriptTags();
|
|
7353
5667
|
if (options.mode !== 'ts') {
|
|
@@ -7371,11 +5685,6 @@ function processSvelteTemplate(str, options) {
|
|
|
7371
5685
|
}
|
|
7372
5686
|
function svelte2tsx(svelte, options = {}) {
|
|
7373
5687
|
options.mode = options.mode || 'ts';
|
|
7374
|
-
// TODO temporary to still keep old transformation around but not expose it anymore.
|
|
7375
|
-
// Remove all old cold once we are sure the new transformation is working
|
|
7376
|
-
if (options.mode === 'tsx') {
|
|
7377
|
-
options.mode = 'ts';
|
|
7378
|
-
}
|
|
7379
5688
|
const str = new MagicString(svelte);
|
|
7380
5689
|
// process the htmlx as a svelte template
|
|
7381
5690
|
let { htmlAst, moduleScriptTag, scriptTag, slots, uses$$props, uses$$slots, uses$$restProps, events, componentDocumentation, resolvedStores, usesAccessors } = processSvelteTemplate(str, options);
|
|
@@ -7433,7 +5742,7 @@ function svelte2tsx(svelte, options = {}) {
|
|
|
7433
5742
|
});
|
|
7434
5743
|
// we need to process the module script after the instance script has moved otherwise we get warnings about moving edited items
|
|
7435
5744
|
if (moduleScriptTag) {
|
|
7436
|
-
processModuleScriptTag(str, moduleScriptTag, new ImplicitStoreValues(implicitStoreValues.getAccessedStores(), renderFunctionStart, scriptTag || options.mode === 'ts' ? undefined : (input) => `</>;${input}<>`)
|
|
5745
|
+
processModuleScriptTag(str, moduleScriptTag, new ImplicitStoreValues(implicitStoreValues.getAccessedStores(), renderFunctionStart, scriptTag || options.mode === 'ts' ? undefined : (input) => `</>;${input}<>`));
|
|
7437
5746
|
}
|
|
7438
5747
|
addComponentExport({
|
|
7439
5748
|
str,
|
|
@@ -7510,7 +5819,7 @@ function loadTsconfig(config, svelteMap) {
|
|
|
7510
5819
|
tsConfig.include = [`${libPathRelative}/**/*`];
|
|
7511
5820
|
tsConfig.files = [];
|
|
7512
5821
|
}
|
|
7513
|
-
const { options, fileNames } = ts.parseJsonConfigFileContent(tsConfig, ts.sys, basepath, { sourceMap: false }, tsconfigFile, undefined, [{ extension: 'svelte', isMixedContent: true, scriptKind: ts.ScriptKind.Deferred }]);
|
|
5822
|
+
const { options, fileNames } = ts.parseJsonConfigFileContent(tsConfig, ts.sys, basepath, { sourceMap: false, rootDir: config.libRoot }, tsconfigFile, undefined, [{ extension: 'svelte', isMixedContent: true, scriptKind: ts.ScriptKind.Deferred }]);
|
|
7514
5823
|
const filenames = fileNames.map((name) => {
|
|
7515
5824
|
if (!isSvelteFilepath(name)) {
|
|
7516
5825
|
return name;
|