@weborigami/language 0.2.1 → 0.2.3
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/LICENSE +21 -0
- package/main.js +1 -0
- package/package.json +7 -7
- package/src/compiler/compile.js +43 -23
- package/src/compiler/origami.pegjs +22 -28
- package/src/compiler/parse.js +135 -153
- package/src/compiler/parserHelpers.js +18 -27
- package/src/runtime/errors.js +34 -12
- package/src/runtime/expressionObject.js +56 -13
- package/src/runtime/ops.js +10 -1
- package/src/runtime/taggedTemplate.js +1 -1
- package/src/runtime/taggedTemplateIndent.js +115 -0
- package/test/compiler/compile.test.js +19 -5
- package/test/compiler/parse.test.js +10 -7
- package/test/runtime/expressionObject.test.js +19 -1
- package/test/runtime/taggedTemplateIndent.test.js +44 -0
package/src/compiler/parse.js
CHANGED
|
@@ -202,7 +202,7 @@ function peg$parse(input, options) {
|
|
|
202
202
|
var peg$FAILED = {};
|
|
203
203
|
var peg$source = options.grammarSource;
|
|
204
204
|
|
|
205
|
-
var peg$startRuleFunctions = { __: peg$parse__, additiveExpression: peg$parseadditiveExpression, additiveOperator: peg$parseadditiveOperator, arguments: peg$parsearguments, arrayLiteral: peg$parsearrayLiteral, arrayEntries: peg$parsearrayEntries, arrayEntry: peg$parsearrayEntry, arrowFunction: peg$parsearrowFunction, bitwiseAndExpression: peg$parsebitwiseAndExpression, bitwiseAndOperator: peg$parsebitwiseAndOperator, bitwiseOrExpression: peg$parsebitwiseOrExpression, bitwiseOrOperator: peg$parsebitwiseOrOperator, bitwiseXorExpression: peg$parsebitwiseXorExpression, bitwiseXorOperator: peg$parsebitwiseXorOperator, callExpression: peg$parsecallExpression, closingBrace: peg$parseclosingBrace, closingBracket: peg$parseclosingBracket, closingParenthesis: peg$parseclosingParenthesis, commaExpression: peg$parsecommaExpression, comment: peg$parsecomment, conditionalExpression: peg$parseconditionalExpression, digits: peg$parsedigits, doubleArrow: peg$parsedoubleArrow, doubleQuoteString: peg$parsedoubleQuoteString, doubleQuoteStringChar: peg$parsedoubleQuoteStringChar, ellipsis: peg$parseellipsis, equalityExpression: peg$parseequalityExpression, equalityOperator: peg$parseequalityOperator, escapedChar: peg$parseescapedChar, exponentiationExpression: peg$parseexponentiationExpression, expression: peg$parseexpression, floatLiteral: peg$parsefloatLiteral, group: peg$parsegroup, guillemetString: peg$parseguillemetString, guillemetStringChar: peg$parseguillemetStringChar, homeDirectory: peg$parsehomeDirectory, host: peg$parsehost, identifier: peg$parseidentifier, identifierChar: peg$parseidentifierChar, identifierList: peg$parseidentifierList, implicitParenthesesCallExpression: peg$parseimplicitParenthesesCallExpression, implicitParensthesesArguments: peg$parseimplicitParensthesesArguments, inlineSpace: peg$parseinlineSpace, integerLiteral: peg$parseintegerLiteral, list: peg$parselist, literal: peg$parseliteral, logicalAndExpression: peg$parselogicalAndExpression, logicalOrExpression: peg$parselogicalOrExpression, multiLineComment: peg$parsemultiLineComment, multiplicativeExpression: peg$parsemultiplicativeExpression, multiplicativeOperator: peg$parsemultiplicativeOperator, namespace: peg$parsenamespace, newLine: peg$parsenewLine, numericLiteral: peg$parsenumericLiteral, nullishCoalescingExpression: peg$parsenullishCoalescingExpression, objectLiteral: peg$parseobjectLiteral, objectEntries: peg$parseobjectEntries, objectEntry: peg$parseobjectEntry, objectGetter: peg$parseobjectGetter, objectHiddenKey: peg$parseobjectHiddenKey, objectKey: peg$parseobjectKey, objectProperty: peg$parseobjectProperty, objectShorthandProperty: peg$parseobjectShorthandProperty, objectPublicKey: peg$parseobjectPublicKey, parenthesesArguments: peg$parseparenthesesArguments, path: peg$parsepath, pathArguments: peg$parsepathArguments, pathKey: peg$parsepathKey, pathSegment: peg$parsepathSegment, pathSegmentChar: peg$parsepathSegmentChar, pipelineExpression: peg$parsepipelineExpression, primary: peg$parseprimary, program: peg$parseprogram, protocolExpression: peg$parseprotocolExpression, qualifiedReference: peg$parsequalifiedReference, reference: peg$parsereference, relationalExpression: peg$parserelationalExpression, relationalOperator: peg$parserelationalOperator, rootDirectory: peg$parserootDirectory, scopeReference: peg$parsescopeReference, separator: peg$parseseparator, slashFollows: peg$parseslashFollows, shebang: peg$parseshebang, shiftExpression: peg$parseshiftExpression, shiftOperator: peg$parseshiftOperator, shorthandFunction: peg$parseshorthandFunction, singleArrow: peg$parsesingleArrow, singleLineComment: peg$parsesingleLineComment, singleQuoteString: peg$parsesingleQuoteString, singleQuoteStringChar: peg$parsesingleQuoteStringChar,
|
|
205
|
+
var peg$startRuleFunctions = { __: peg$parse__, additiveExpression: peg$parseadditiveExpression, additiveOperator: peg$parseadditiveOperator, arguments: peg$parsearguments, arrayLiteral: peg$parsearrayLiteral, arrayEntries: peg$parsearrayEntries, arrayEntry: peg$parsearrayEntry, arrowFunction: peg$parsearrowFunction, bitwiseAndExpression: peg$parsebitwiseAndExpression, bitwiseAndOperator: peg$parsebitwiseAndOperator, bitwiseOrExpression: peg$parsebitwiseOrExpression, bitwiseOrOperator: peg$parsebitwiseOrOperator, bitwiseXorExpression: peg$parsebitwiseXorExpression, bitwiseXorOperator: peg$parsebitwiseXorOperator, callExpression: peg$parsecallExpression, closingBrace: peg$parseclosingBrace, closingBracket: peg$parseclosingBracket, closingParenthesis: peg$parseclosingParenthesis, commaExpression: peg$parsecommaExpression, comment: peg$parsecomment, conditionalExpression: peg$parseconditionalExpression, digits: peg$parsedigits, doubleArrow: peg$parsedoubleArrow, doubleQuoteString: peg$parsedoubleQuoteString, doubleQuoteStringChar: peg$parsedoubleQuoteStringChar, ellipsis: peg$parseellipsis, equalityExpression: peg$parseequalityExpression, equalityOperator: peg$parseequalityOperator, escapedChar: peg$parseescapedChar, exponentiationExpression: peg$parseexponentiationExpression, expression: peg$parseexpression, floatLiteral: peg$parsefloatLiteral, group: peg$parsegroup, guillemetString: peg$parseguillemetString, guillemetStringChar: peg$parseguillemetStringChar, homeDirectory: peg$parsehomeDirectory, host: peg$parsehost, identifier: peg$parseidentifier, identifierChar: peg$parseidentifierChar, identifierList: peg$parseidentifierList, implicitParenthesesCallExpression: peg$parseimplicitParenthesesCallExpression, implicitParensthesesArguments: peg$parseimplicitParensthesesArguments, inlineSpace: peg$parseinlineSpace, integerLiteral: peg$parseintegerLiteral, list: peg$parselist, literal: peg$parseliteral, logicalAndExpression: peg$parselogicalAndExpression, logicalOrExpression: peg$parselogicalOrExpression, multiLineComment: peg$parsemultiLineComment, multiplicativeExpression: peg$parsemultiplicativeExpression, multiplicativeOperator: peg$parsemultiplicativeOperator, namespace: peg$parsenamespace, newLine: peg$parsenewLine, numericLiteral: peg$parsenumericLiteral, nullishCoalescingExpression: peg$parsenullishCoalescingExpression, objectLiteral: peg$parseobjectLiteral, objectEntries: peg$parseobjectEntries, objectEntry: peg$parseobjectEntry, objectGetter: peg$parseobjectGetter, objectHiddenKey: peg$parseobjectHiddenKey, objectKey: peg$parseobjectKey, objectProperty: peg$parseobjectProperty, objectShorthandProperty: peg$parseobjectShorthandProperty, objectPublicKey: peg$parseobjectPublicKey, parenthesesArguments: peg$parseparenthesesArguments, path: peg$parsepath, pathArguments: peg$parsepathArguments, pathKey: peg$parsepathKey, pathSegment: peg$parsepathSegment, pathSegmentChar: peg$parsepathSegmentChar, pipelineExpression: peg$parsepipelineExpression, primary: peg$parseprimary, program: peg$parseprogram, protocolExpression: peg$parseprotocolExpression, qualifiedReference: peg$parsequalifiedReference, reference: peg$parsereference, relationalExpression: peg$parserelationalExpression, relationalOperator: peg$parserelationalOperator, rootDirectory: peg$parserootDirectory, scopeReference: peg$parsescopeReference, separator: peg$parseseparator, slashFollows: peg$parseslashFollows, shebang: peg$parseshebang, shiftExpression: peg$parseshiftExpression, shiftOperator: peg$parseshiftOperator, shorthandFunction: peg$parseshorthandFunction, singleArrow: peg$parsesingleArrow, singleLineComment: peg$parsesingleLineComment, singleQuoteString: peg$parsesingleQuoteString, singleQuoteStringChar: peg$parsesingleQuoteStringChar, spreadElement: peg$parsespreadElement, stringLiteral: peg$parsestringLiteral, templateDocument: peg$parsetemplateDocument, templateDocumentChar: peg$parsetemplateDocumentChar, templateDocumentText: peg$parsetemplateDocumentText, templateLiteral: peg$parsetemplateLiteral, templateLiteralChar: peg$parsetemplateLiteralChar, templateLiteralText: peg$parsetemplateLiteralText, templateSubstitution: peg$parsetemplateSubstitution, textChar: peg$parsetextChar, unaryExpression: peg$parseunaryExpression, unaryOperator: peg$parseunaryOperator, whitespaceWithNewLine: peg$parsewhitespaceWithNewLine };
|
|
206
206
|
var peg$startRuleFunction = peg$parse__;
|
|
207
207
|
|
|
208
208
|
var peg$c0 = "[";
|
|
@@ -412,7 +412,7 @@ function peg$parse(input, options) {
|
|
|
412
412
|
return annotate(tail.reduce(makeCall, head), location());
|
|
413
413
|
};
|
|
414
414
|
var peg$f11 = function() {
|
|
415
|
-
error(
|
|
415
|
+
error(`An object ended without a closing brace, or contained something that wasn't expected.\nThe top level of an object can only contain definitions ("a: b" or "a = b") or spreads ("...a").`);
|
|
416
416
|
};
|
|
417
417
|
var peg$f12 = function() {
|
|
418
418
|
error("Expected right bracket");
|
|
@@ -425,12 +425,15 @@ function peg$parse(input, options) {
|
|
|
425
425
|
? list[0]
|
|
426
426
|
: annotate([ops.comma, ...list], location());
|
|
427
427
|
};
|
|
428
|
-
var peg$f15 = function(condition,
|
|
428
|
+
var peg$f15 = function(condition, tail) {
|
|
429
|
+
if (!tail) {
|
|
430
|
+
return condition;
|
|
431
|
+
}
|
|
429
432
|
return annotate([
|
|
430
433
|
ops.conditional,
|
|
431
434
|
downgradeReference(condition),
|
|
432
|
-
[ops.lambda, [], downgradeReference(
|
|
433
|
-
[ops.lambda, [], downgradeReference(
|
|
435
|
+
[ops.lambda, [], downgradeReference(tail[0])],
|
|
436
|
+
[ops.lambda, [], downgradeReference(tail[1])]
|
|
434
437
|
], location());
|
|
435
438
|
};
|
|
436
439
|
var peg$f16 = function(chars) {
|
|
@@ -447,7 +450,7 @@ function peg$parse(input, options) {
|
|
|
447
450
|
var peg$f23 = function() { return "\t"; };
|
|
448
451
|
var peg$f24 = function() { return "\v"; };
|
|
449
452
|
var peg$f25 = function(left, right) {
|
|
450
|
-
return annotate([ops.exponentiation, left, right], location());
|
|
453
|
+
return right ? annotate([ops.exponentiation, left, right], location()) : left;
|
|
451
454
|
};
|
|
452
455
|
var peg$f26 = function() {
|
|
453
456
|
return annotate([ops.literal, parseFloat(text())], location());
|
|
@@ -600,25 +603,25 @@ function peg$parse(input, options) {
|
|
|
600
603
|
var peg$f68 = function(value) {
|
|
601
604
|
return annotate([ops.spread, value], location());
|
|
602
605
|
};
|
|
603
|
-
var peg$f69 = function(
|
|
604
|
-
return annotate(
|
|
605
|
-
|
|
606
|
-
|
|
607
|
-
|
|
606
|
+
var peg$f69 = function(head, tail) {
|
|
607
|
+
return annotate(
|
|
608
|
+
[ops.lambda, ["_"], makeTemplate(ops.templateIndent, head, tail)],
|
|
609
|
+
location()
|
|
610
|
+
);
|
|
608
611
|
};
|
|
609
|
-
var peg$
|
|
612
|
+
var peg$f70 = function(chars) {
|
|
610
613
|
return chars.join("");
|
|
611
614
|
};
|
|
612
|
-
var peg$
|
|
613
|
-
return annotate(makeTemplate(ops.template,
|
|
615
|
+
var peg$f71 = function(head, tail) {
|
|
616
|
+
return annotate(makeTemplate(ops.template, head, tail), location());
|
|
614
617
|
};
|
|
615
|
-
var peg$
|
|
618
|
+
var peg$f72 = function(chars) {
|
|
616
619
|
return chars.join("");
|
|
617
620
|
};
|
|
618
|
-
var peg$
|
|
621
|
+
var peg$f73 = function(expression) {
|
|
619
622
|
return annotate(expression, location());
|
|
620
623
|
};
|
|
621
|
-
var peg$
|
|
624
|
+
var peg$f74 = function(operator, expression) {
|
|
622
625
|
return annotate(makeUnaryOperation(operator, expression), location());
|
|
623
626
|
};
|
|
624
627
|
var peg$currPos = options.peg$currPos | 0;
|
|
@@ -985,7 +988,7 @@ function peg$parse(input, options) {
|
|
|
985
988
|
function peg$parsearrayEntry() {
|
|
986
989
|
var s0, s1, s2, s3;
|
|
987
990
|
|
|
988
|
-
s0 = peg$
|
|
991
|
+
s0 = peg$parsespreadElement();
|
|
989
992
|
if (s0 === peg$FAILED) {
|
|
990
993
|
s0 = peg$parsepipelineExpression();
|
|
991
994
|
if (s0 === peg$FAILED) {
|
|
@@ -1546,60 +1549,62 @@ function peg$parse(input, options) {
|
|
|
1546
1549
|
}
|
|
1547
1550
|
|
|
1548
1551
|
function peg$parseconditionalExpression() {
|
|
1549
|
-
var s0, s1, s2, s3, s4, s5, s6, s7, s8, s9;
|
|
1552
|
+
var s0, s1, s2, s3, s4, s5, s6, s7, s8, s9, s10;
|
|
1550
1553
|
|
|
1551
1554
|
s0 = peg$currPos;
|
|
1552
1555
|
s1 = peg$parselogicalOrExpression();
|
|
1553
1556
|
if (s1 !== peg$FAILED) {
|
|
1554
|
-
s2 = peg$
|
|
1557
|
+
s2 = peg$currPos;
|
|
1558
|
+
s3 = peg$parse__();
|
|
1555
1559
|
if (input.charCodeAt(peg$currPos) === 63) {
|
|
1556
|
-
|
|
1560
|
+
s4 = peg$c9;
|
|
1557
1561
|
peg$currPos++;
|
|
1558
1562
|
} else {
|
|
1559
|
-
|
|
1563
|
+
s4 = peg$FAILED;
|
|
1560
1564
|
if (peg$silentFails === 0) { peg$fail(peg$e15); }
|
|
1561
1565
|
}
|
|
1562
|
-
if (
|
|
1563
|
-
|
|
1564
|
-
|
|
1565
|
-
if (
|
|
1566
|
-
|
|
1566
|
+
if (s4 !== peg$FAILED) {
|
|
1567
|
+
s5 = peg$parse__();
|
|
1568
|
+
s6 = peg$parsepipelineExpression();
|
|
1569
|
+
if (s6 !== peg$FAILED) {
|
|
1570
|
+
s7 = peg$parse__();
|
|
1567
1571
|
if (input.charCodeAt(peg$currPos) === 58) {
|
|
1568
|
-
|
|
1572
|
+
s8 = peg$c10;
|
|
1569
1573
|
peg$currPos++;
|
|
1570
1574
|
} else {
|
|
1571
|
-
|
|
1575
|
+
s8 = peg$FAILED;
|
|
1572
1576
|
if (peg$silentFails === 0) { peg$fail(peg$e16); }
|
|
1573
1577
|
}
|
|
1574
|
-
if (
|
|
1575
|
-
|
|
1576
|
-
|
|
1577
|
-
if (
|
|
1578
|
-
|
|
1579
|
-
s0 = peg$f15(s1, s5, s9);
|
|
1578
|
+
if (s8 !== peg$FAILED) {
|
|
1579
|
+
s9 = peg$parse__();
|
|
1580
|
+
s10 = peg$parsepipelineExpression();
|
|
1581
|
+
if (s10 !== peg$FAILED) {
|
|
1582
|
+
s2 = [ s6, s10 ];
|
|
1580
1583
|
} else {
|
|
1581
|
-
peg$currPos =
|
|
1582
|
-
|
|
1584
|
+
peg$currPos = s2;
|
|
1585
|
+
s2 = peg$FAILED;
|
|
1583
1586
|
}
|
|
1584
1587
|
} else {
|
|
1585
|
-
peg$currPos =
|
|
1586
|
-
|
|
1588
|
+
peg$currPos = s2;
|
|
1589
|
+
s2 = peg$FAILED;
|
|
1587
1590
|
}
|
|
1588
1591
|
} else {
|
|
1589
|
-
peg$currPos =
|
|
1590
|
-
|
|
1592
|
+
peg$currPos = s2;
|
|
1593
|
+
s2 = peg$FAILED;
|
|
1591
1594
|
}
|
|
1592
1595
|
} else {
|
|
1593
|
-
peg$currPos =
|
|
1594
|
-
|
|
1596
|
+
peg$currPos = s2;
|
|
1597
|
+
s2 = peg$FAILED;
|
|
1598
|
+
}
|
|
1599
|
+
if (s2 === peg$FAILED) {
|
|
1600
|
+
s2 = null;
|
|
1595
1601
|
}
|
|
1602
|
+
peg$savedPos = s0;
|
|
1603
|
+
s0 = peg$f15(s1, s2);
|
|
1596
1604
|
} else {
|
|
1597
1605
|
peg$currPos = s0;
|
|
1598
1606
|
s0 = peg$FAILED;
|
|
1599
1607
|
}
|
|
1600
|
-
if (s0 === peg$FAILED) {
|
|
1601
|
-
s0 = peg$parselogicalOrExpression();
|
|
1602
|
-
}
|
|
1603
1608
|
|
|
1604
1609
|
return s0;
|
|
1605
1610
|
}
|
|
@@ -2009,40 +2014,42 @@ function peg$parse(input, options) {
|
|
|
2009
2014
|
}
|
|
2010
2015
|
|
|
2011
2016
|
function peg$parseexponentiationExpression() {
|
|
2012
|
-
var s0, s1, s2, s3, s4, s5;
|
|
2017
|
+
var s0, s1, s2, s3, s4, s5, s6;
|
|
2013
2018
|
|
|
2014
2019
|
s0 = peg$currPos;
|
|
2015
2020
|
s1 = peg$parseunaryExpression();
|
|
2016
2021
|
if (s1 !== peg$FAILED) {
|
|
2017
|
-
s2 = peg$
|
|
2022
|
+
s2 = peg$currPos;
|
|
2023
|
+
s3 = peg$parse__();
|
|
2018
2024
|
if (input.substr(peg$currPos, 2) === peg$c28) {
|
|
2019
|
-
|
|
2025
|
+
s4 = peg$c28;
|
|
2020
2026
|
peg$currPos += 2;
|
|
2021
2027
|
} else {
|
|
2022
|
-
|
|
2028
|
+
s4 = peg$FAILED;
|
|
2023
2029
|
if (peg$silentFails === 0) { peg$fail(peg$e37); }
|
|
2024
2030
|
}
|
|
2025
|
-
if (
|
|
2026
|
-
|
|
2027
|
-
|
|
2028
|
-
if (
|
|
2029
|
-
|
|
2030
|
-
s0 = peg$f25(s1, s5);
|
|
2031
|
+
if (s4 !== peg$FAILED) {
|
|
2032
|
+
s5 = peg$parse__();
|
|
2033
|
+
s6 = peg$parseexponentiationExpression();
|
|
2034
|
+
if (s6 !== peg$FAILED) {
|
|
2035
|
+
s2 = s6;
|
|
2031
2036
|
} else {
|
|
2032
|
-
peg$currPos =
|
|
2033
|
-
|
|
2037
|
+
peg$currPos = s2;
|
|
2038
|
+
s2 = peg$FAILED;
|
|
2034
2039
|
}
|
|
2035
2040
|
} else {
|
|
2036
|
-
peg$currPos =
|
|
2037
|
-
|
|
2041
|
+
peg$currPos = s2;
|
|
2042
|
+
s2 = peg$FAILED;
|
|
2043
|
+
}
|
|
2044
|
+
if (s2 === peg$FAILED) {
|
|
2045
|
+
s2 = null;
|
|
2038
2046
|
}
|
|
2047
|
+
peg$savedPos = s0;
|
|
2048
|
+
s0 = peg$f25(s1, s2);
|
|
2039
2049
|
} else {
|
|
2040
2050
|
peg$currPos = s0;
|
|
2041
2051
|
s0 = peg$FAILED;
|
|
2042
2052
|
}
|
|
2043
|
-
if (s0 === peg$FAILED) {
|
|
2044
|
-
s0 = peg$parseunaryExpression();
|
|
2045
|
-
}
|
|
2046
2053
|
|
|
2047
2054
|
return s0;
|
|
2048
2055
|
}
|
|
@@ -3173,7 +3180,7 @@ function peg$parse(input, options) {
|
|
|
3173
3180
|
function peg$parseobjectEntry() {
|
|
3174
3181
|
var s0;
|
|
3175
3182
|
|
|
3176
|
-
s0 = peg$
|
|
3183
|
+
s0 = peg$parsespreadElement();
|
|
3177
3184
|
if (s0 === peg$FAILED) {
|
|
3178
3185
|
s0 = peg$parseobjectProperty();
|
|
3179
3186
|
if (s0 === peg$FAILED) {
|
|
@@ -4307,14 +4314,14 @@ function peg$parse(input, options) {
|
|
|
4307
4314
|
return s0;
|
|
4308
4315
|
}
|
|
4309
4316
|
|
|
4310
|
-
function peg$
|
|
4317
|
+
function peg$parsespreadElement() {
|
|
4311
4318
|
var s0, s1, s2, s3;
|
|
4312
4319
|
|
|
4313
4320
|
s0 = peg$currPos;
|
|
4314
4321
|
s1 = peg$parseellipsis();
|
|
4315
4322
|
if (s1 !== peg$FAILED) {
|
|
4316
4323
|
s2 = peg$parse__();
|
|
4317
|
-
s3 = peg$
|
|
4324
|
+
s3 = peg$parsepipelineExpression();
|
|
4318
4325
|
if (s3 !== peg$FAILED) {
|
|
4319
4326
|
peg$savedPos = s0;
|
|
4320
4327
|
s0 = peg$f68(s3);
|
|
@@ -4351,14 +4358,37 @@ function peg$parse(input, options) {
|
|
|
4351
4358
|
}
|
|
4352
4359
|
|
|
4353
4360
|
function peg$parsetemplateDocument() {
|
|
4354
|
-
var s0, s1;
|
|
4361
|
+
var s0, s1, s2, s3, s4, s5;
|
|
4355
4362
|
|
|
4356
4363
|
peg$silentFails++;
|
|
4357
4364
|
s0 = peg$currPos;
|
|
4358
|
-
s1 = peg$
|
|
4365
|
+
s1 = peg$parsetemplateDocumentText();
|
|
4366
|
+
s2 = [];
|
|
4367
|
+
s3 = peg$currPos;
|
|
4368
|
+
s4 = peg$parsetemplateSubstitution();
|
|
4369
|
+
if (s4 !== peg$FAILED) {
|
|
4370
|
+
s5 = peg$parsetemplateDocumentText();
|
|
4371
|
+
s4 = [s4, s5];
|
|
4372
|
+
s3 = s4;
|
|
4373
|
+
} else {
|
|
4374
|
+
peg$currPos = s3;
|
|
4375
|
+
s3 = peg$FAILED;
|
|
4376
|
+
}
|
|
4377
|
+
while (s3 !== peg$FAILED) {
|
|
4378
|
+
s2.push(s3);
|
|
4379
|
+
s3 = peg$currPos;
|
|
4380
|
+
s4 = peg$parsetemplateSubstitution();
|
|
4381
|
+
if (s4 !== peg$FAILED) {
|
|
4382
|
+
s5 = peg$parsetemplateDocumentText();
|
|
4383
|
+
s4 = [s4, s5];
|
|
4384
|
+
s3 = s4;
|
|
4385
|
+
} else {
|
|
4386
|
+
peg$currPos = s3;
|
|
4387
|
+
s3 = peg$FAILED;
|
|
4388
|
+
}
|
|
4389
|
+
}
|
|
4359
4390
|
peg$savedPos = s0;
|
|
4360
|
-
|
|
4361
|
-
s0 = s1;
|
|
4391
|
+
s0 = peg$f69(s1, s2);
|
|
4362
4392
|
peg$silentFails--;
|
|
4363
4393
|
s1 = peg$FAILED;
|
|
4364
4394
|
if (peg$silentFails === 0) { peg$fail(peg$e94); }
|
|
@@ -4402,41 +4432,6 @@ function peg$parse(input, options) {
|
|
|
4402
4432
|
return s0;
|
|
4403
4433
|
}
|
|
4404
4434
|
|
|
4405
|
-
function peg$parsetemplateDocumentContents() {
|
|
4406
|
-
var s0, s1, s2, s3, s4, s5;
|
|
4407
|
-
|
|
4408
|
-
s0 = peg$currPos;
|
|
4409
|
-
s1 = peg$parsetemplateDocumentText();
|
|
4410
|
-
s2 = [];
|
|
4411
|
-
s3 = peg$currPos;
|
|
4412
|
-
s4 = peg$parsetemplateSubstitution();
|
|
4413
|
-
if (s4 !== peg$FAILED) {
|
|
4414
|
-
s5 = peg$parsetemplateDocumentText();
|
|
4415
|
-
s4 = [s4, s5];
|
|
4416
|
-
s3 = s4;
|
|
4417
|
-
} else {
|
|
4418
|
-
peg$currPos = s3;
|
|
4419
|
-
s3 = peg$FAILED;
|
|
4420
|
-
}
|
|
4421
|
-
while (s3 !== peg$FAILED) {
|
|
4422
|
-
s2.push(s3);
|
|
4423
|
-
s3 = peg$currPos;
|
|
4424
|
-
s4 = peg$parsetemplateSubstitution();
|
|
4425
|
-
if (s4 !== peg$FAILED) {
|
|
4426
|
-
s5 = peg$parsetemplateDocumentText();
|
|
4427
|
-
s4 = [s4, s5];
|
|
4428
|
-
s3 = s4;
|
|
4429
|
-
} else {
|
|
4430
|
-
peg$currPos = s3;
|
|
4431
|
-
s3 = peg$FAILED;
|
|
4432
|
-
}
|
|
4433
|
-
}
|
|
4434
|
-
peg$savedPos = s0;
|
|
4435
|
-
s0 = peg$f70(s1, s2);
|
|
4436
|
-
|
|
4437
|
-
return s0;
|
|
4438
|
-
}
|
|
4439
|
-
|
|
4440
4435
|
function peg$parsetemplateDocumentText() {
|
|
4441
4436
|
var s0, s1, s2;
|
|
4442
4437
|
|
|
@@ -4449,7 +4444,7 @@ function peg$parse(input, options) {
|
|
|
4449
4444
|
s2 = peg$parsetemplateDocumentChar();
|
|
4450
4445
|
}
|
|
4451
4446
|
peg$savedPos = s0;
|
|
4452
|
-
s1 = peg$
|
|
4447
|
+
s1 = peg$f70(s1);
|
|
4453
4448
|
s0 = s1;
|
|
4454
4449
|
peg$silentFails--;
|
|
4455
4450
|
s1 = peg$FAILED;
|
|
@@ -4459,7 +4454,7 @@ function peg$parse(input, options) {
|
|
|
4459
4454
|
}
|
|
4460
4455
|
|
|
4461
4456
|
function peg$parsetemplateLiteral() {
|
|
4462
|
-
var s0, s1, s2, s3;
|
|
4457
|
+
var s0, s1, s2, s3, s4, s5, s6;
|
|
4463
4458
|
|
|
4464
4459
|
peg$silentFails++;
|
|
4465
4460
|
s0 = peg$currPos;
|
|
@@ -4471,17 +4466,41 @@ function peg$parse(input, options) {
|
|
|
4471
4466
|
if (peg$silentFails === 0) { peg$fail(peg$e98); }
|
|
4472
4467
|
}
|
|
4473
4468
|
if (s1 !== peg$FAILED) {
|
|
4474
|
-
s2 = peg$
|
|
4469
|
+
s2 = peg$parsetemplateLiteralText();
|
|
4470
|
+
s3 = [];
|
|
4471
|
+
s4 = peg$currPos;
|
|
4472
|
+
s5 = peg$parsetemplateSubstitution();
|
|
4473
|
+
if (s5 !== peg$FAILED) {
|
|
4474
|
+
s6 = peg$parsetemplateLiteralText();
|
|
4475
|
+
s5 = [s5, s6];
|
|
4476
|
+
s4 = s5;
|
|
4477
|
+
} else {
|
|
4478
|
+
peg$currPos = s4;
|
|
4479
|
+
s4 = peg$FAILED;
|
|
4480
|
+
}
|
|
4481
|
+
while (s4 !== peg$FAILED) {
|
|
4482
|
+
s3.push(s4);
|
|
4483
|
+
s4 = peg$currPos;
|
|
4484
|
+
s5 = peg$parsetemplateSubstitution();
|
|
4485
|
+
if (s5 !== peg$FAILED) {
|
|
4486
|
+
s6 = peg$parsetemplateLiteralText();
|
|
4487
|
+
s5 = [s5, s6];
|
|
4488
|
+
s4 = s5;
|
|
4489
|
+
} else {
|
|
4490
|
+
peg$currPos = s4;
|
|
4491
|
+
s4 = peg$FAILED;
|
|
4492
|
+
}
|
|
4493
|
+
}
|
|
4475
4494
|
if (input.charCodeAt(peg$currPos) === 96) {
|
|
4476
|
-
|
|
4495
|
+
s4 = peg$c59;
|
|
4477
4496
|
peg$currPos++;
|
|
4478
4497
|
} else {
|
|
4479
|
-
|
|
4498
|
+
s4 = peg$FAILED;
|
|
4480
4499
|
if (peg$silentFails === 0) { peg$fail(peg$e98); }
|
|
4481
4500
|
}
|
|
4482
|
-
if (
|
|
4501
|
+
if (s4 !== peg$FAILED) {
|
|
4483
4502
|
peg$savedPos = s0;
|
|
4484
|
-
s0 = peg$
|
|
4503
|
+
s0 = peg$f71(s2, s3);
|
|
4485
4504
|
} else {
|
|
4486
4505
|
peg$currPos = s0;
|
|
4487
4506
|
s0 = peg$FAILED;
|
|
@@ -4544,41 +4563,6 @@ function peg$parse(input, options) {
|
|
|
4544
4563
|
return s0;
|
|
4545
4564
|
}
|
|
4546
4565
|
|
|
4547
|
-
function peg$parsetemplateLiteralContents() {
|
|
4548
|
-
var s0, s1, s2, s3, s4, s5;
|
|
4549
|
-
|
|
4550
|
-
s0 = peg$currPos;
|
|
4551
|
-
s1 = peg$parsetemplateLiteralText();
|
|
4552
|
-
s2 = [];
|
|
4553
|
-
s3 = peg$currPos;
|
|
4554
|
-
s4 = peg$parsetemplateSubstitution();
|
|
4555
|
-
if (s4 !== peg$FAILED) {
|
|
4556
|
-
s5 = peg$parsetemplateLiteralText();
|
|
4557
|
-
s4 = [s4, s5];
|
|
4558
|
-
s3 = s4;
|
|
4559
|
-
} else {
|
|
4560
|
-
peg$currPos = s3;
|
|
4561
|
-
s3 = peg$FAILED;
|
|
4562
|
-
}
|
|
4563
|
-
while (s3 !== peg$FAILED) {
|
|
4564
|
-
s2.push(s3);
|
|
4565
|
-
s3 = peg$currPos;
|
|
4566
|
-
s4 = peg$parsetemplateSubstitution();
|
|
4567
|
-
if (s4 !== peg$FAILED) {
|
|
4568
|
-
s5 = peg$parsetemplateLiteralText();
|
|
4569
|
-
s4 = [s4, s5];
|
|
4570
|
-
s3 = s4;
|
|
4571
|
-
} else {
|
|
4572
|
-
peg$currPos = s3;
|
|
4573
|
-
s3 = peg$FAILED;
|
|
4574
|
-
}
|
|
4575
|
-
}
|
|
4576
|
-
s1 = [s1, s2];
|
|
4577
|
-
s0 = s1;
|
|
4578
|
-
|
|
4579
|
-
return s0;
|
|
4580
|
-
}
|
|
4581
|
-
|
|
4582
4566
|
function peg$parsetemplateLiteralText() {
|
|
4583
4567
|
var s0, s1, s2;
|
|
4584
4568
|
|
|
@@ -4590,7 +4574,7 @@ function peg$parse(input, options) {
|
|
|
4590
4574
|
s2 = peg$parsetemplateLiteralChar();
|
|
4591
4575
|
}
|
|
4592
4576
|
peg$savedPos = s0;
|
|
4593
|
-
s1 = peg$
|
|
4577
|
+
s1 = peg$f72(s1);
|
|
4594
4578
|
s0 = s1;
|
|
4595
4579
|
|
|
4596
4580
|
return s0;
|
|
@@ -4620,7 +4604,7 @@ function peg$parse(input, options) {
|
|
|
4620
4604
|
}
|
|
4621
4605
|
if (s3 !== peg$FAILED) {
|
|
4622
4606
|
peg$savedPos = s0;
|
|
4623
|
-
s0 = peg$
|
|
4607
|
+
s0 = peg$f73(s2);
|
|
4624
4608
|
} else {
|
|
4625
4609
|
peg$currPos = s0;
|
|
4626
4610
|
s0 = peg$FAILED;
|
|
@@ -4669,7 +4653,7 @@ function peg$parse(input, options) {
|
|
|
4669
4653
|
s3 = peg$parseunaryExpression();
|
|
4670
4654
|
if (s3 !== peg$FAILED) {
|
|
4671
4655
|
peg$savedPos = s0;
|
|
4672
|
-
s0 = peg$
|
|
4656
|
+
s0 = peg$f74(s1, s3);
|
|
4673
4657
|
} else {
|
|
4674
4658
|
peg$currPos = s0;
|
|
4675
4659
|
s0 = peg$FAILED;
|
|
@@ -4845,15 +4829,13 @@ const peg$allowedStartRules = [
|
|
|
4845
4829
|
"singleLineComment",
|
|
4846
4830
|
"singleQuoteString",
|
|
4847
4831
|
"singleQuoteStringChar",
|
|
4848
|
-
"
|
|
4832
|
+
"spreadElement",
|
|
4849
4833
|
"stringLiteral",
|
|
4850
4834
|
"templateDocument",
|
|
4851
4835
|
"templateDocumentChar",
|
|
4852
|
-
"templateDocumentContents",
|
|
4853
4836
|
"templateDocumentText",
|
|
4854
4837
|
"templateLiteral",
|
|
4855
4838
|
"templateLiteralChar",
|
|
4856
|
-
"templateLiteralContents",
|
|
4857
4839
|
"templateLiteralText",
|
|
4858
4840
|
"templateSubstitution",
|
|
4859
4841
|
"textChar",
|
|
@@ -76,22 +76,6 @@ export function downgradeReference(code) {
|
|
|
76
76
|
}
|
|
77
77
|
}
|
|
78
78
|
|
|
79
|
-
// Return true if the code will generate an async object.
|
|
80
|
-
function isCodeForAsyncObject(code) {
|
|
81
|
-
if (!(code instanceof Array)) {
|
|
82
|
-
return false;
|
|
83
|
-
}
|
|
84
|
-
if (code[0] !== ops.object) {
|
|
85
|
-
return false;
|
|
86
|
-
}
|
|
87
|
-
// Are any of the properties getters?
|
|
88
|
-
const entries = code.slice(1);
|
|
89
|
-
const hasGetter = entries.some(([key, value]) => {
|
|
90
|
-
return value instanceof Array && value[0] === ops.getter;
|
|
91
|
-
});
|
|
92
|
-
return hasGetter;
|
|
93
|
-
}
|
|
94
|
-
|
|
95
79
|
export function makeArray(entries) {
|
|
96
80
|
let currentEntries = [];
|
|
97
81
|
const spreads = [];
|
|
@@ -260,17 +244,24 @@ export function makeObject(entries, op) {
|
|
|
260
244
|
continue;
|
|
261
245
|
}
|
|
262
246
|
|
|
263
|
-
if (
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
//
|
|
273
|
-
|
|
247
|
+
if (value instanceof Array) {
|
|
248
|
+
if (
|
|
249
|
+
value[0] === ops.getter &&
|
|
250
|
+
value[1] instanceof Array &&
|
|
251
|
+
value[1][0] === ops.literal
|
|
252
|
+
) {
|
|
253
|
+
// Optimize a getter for a primitive value to a regular property
|
|
254
|
+
value = value[1];
|
|
255
|
+
}
|
|
256
|
+
// else if (
|
|
257
|
+
// value[0] === ops.object ||
|
|
258
|
+
// (value[0] === ops.getter &&
|
|
259
|
+
// value[1] instanceof Array &&
|
|
260
|
+
// (value[1][0] === ops.object || value[1][0] === ops.merge))
|
|
261
|
+
// ) {
|
|
262
|
+
// // Add a trailing slash to key to indicate value is a subtree
|
|
263
|
+
// key = trailingSlash.add(key);
|
|
264
|
+
// }
|
|
274
265
|
}
|
|
275
266
|
|
|
276
267
|
currentEntries.push([key, value]);
|
package/src/runtime/errors.js
CHANGED
|
@@ -1,6 +1,10 @@
|
|
|
1
1
|
// Text we look for in an error stack to guess whether a given line represents a
|
|
2
2
|
|
|
3
|
-
import {
|
|
3
|
+
import {
|
|
4
|
+
scope as scopeFn,
|
|
5
|
+
trailingSlash,
|
|
6
|
+
TraverseError,
|
|
7
|
+
} from "@weborigami/async-tree";
|
|
4
8
|
import codeFragment from "./codeFragment.js";
|
|
5
9
|
import { typos } from "./typos.js";
|
|
6
10
|
|
|
@@ -13,19 +17,24 @@ const origamiSourceSignals = [
|
|
|
13
17
|
];
|
|
14
18
|
|
|
15
19
|
export async function builtinReferenceError(tree, builtins, key) {
|
|
16
|
-
const messages = [
|
|
17
|
-
`"${key}" is being called as if it were a builtin function, but it's not.`,
|
|
18
|
-
];
|
|
19
20
|
// See if the key is in scope (but not as a builtin)
|
|
20
21
|
const scope = scopeFn(tree);
|
|
21
22
|
const value = await scope.get(key);
|
|
23
|
+
let message;
|
|
22
24
|
if (value === undefined) {
|
|
25
|
+
const messages = [
|
|
26
|
+
`"${key}" is being called as if it were a builtin function, but it's not.`,
|
|
27
|
+
];
|
|
23
28
|
const typos = await formatScopeTypos(builtins, key);
|
|
24
29
|
messages.push(typos);
|
|
30
|
+
message = messages.join(" ");
|
|
25
31
|
} else {
|
|
26
|
-
messages
|
|
32
|
+
const messages = [
|
|
33
|
+
`To call a function like "${key}" that's not a builtin, include a slash: ${key}/( )`,
|
|
34
|
+
`Details: https://weborigami.org/language/syntax.html#shorthand-for-builtin-functions`,
|
|
35
|
+
];
|
|
36
|
+
message = messages.join("\n");
|
|
27
37
|
}
|
|
28
|
-
const message = messages.join(" ");
|
|
29
38
|
return new ReferenceError(message);
|
|
30
39
|
}
|
|
31
40
|
|
|
@@ -36,37 +45,50 @@ export async function builtinReferenceError(tree, builtins, key) {
|
|
|
36
45
|
*/
|
|
37
46
|
export function formatError(error) {
|
|
38
47
|
let message;
|
|
48
|
+
|
|
49
|
+
let location = /** @type {any} */ (error).location;
|
|
50
|
+
const fragment = location ? codeFragment(location) : null;
|
|
51
|
+
let fragmentInMessage = false;
|
|
52
|
+
|
|
39
53
|
if (error.stack) {
|
|
40
54
|
// Display the stack only until we reach the Origami source code.
|
|
41
55
|
message = "";
|
|
42
56
|
let lines = error.stack.split("\n");
|
|
43
57
|
for (let i = 0; i < lines.length; i++) {
|
|
44
|
-
|
|
58
|
+
let line = lines[i];
|
|
45
59
|
if (maybeOrigamiSourceCode(line)) {
|
|
46
60
|
break;
|
|
47
61
|
}
|
|
62
|
+
if (
|
|
63
|
+
error instanceof TraverseError &&
|
|
64
|
+
error.message === "A null or undefined value can't be traversed"
|
|
65
|
+
) {
|
|
66
|
+
// Provide more meaningful message for TraverseError
|
|
67
|
+
line = `TraverseError: This part of the path is null or undefined: ${fragment}`;
|
|
68
|
+
fragmentInMessage = true;
|
|
69
|
+
}
|
|
48
70
|
if (message) {
|
|
49
71
|
message += "\n";
|
|
50
72
|
}
|
|
51
|
-
message +=
|
|
73
|
+
message += line;
|
|
52
74
|
}
|
|
53
75
|
} else {
|
|
54
76
|
message = error.toString();
|
|
55
77
|
}
|
|
56
78
|
|
|
57
79
|
// Add location
|
|
58
|
-
let location = /** @type {any} */ (error).location;
|
|
59
80
|
if (location) {
|
|
60
|
-
const fragment = codeFragment(location);
|
|
61
81
|
let { source, start } = location;
|
|
62
|
-
|
|
63
|
-
|
|
82
|
+
if (!fragmentInMessage) {
|
|
83
|
+
message += `\nevaluating: ${fragment}`;
|
|
84
|
+
}
|
|
64
85
|
if (typeof source === "object" && source.url) {
|
|
65
86
|
message += `\n at ${source.url.href}:${start.line}:${start.column}`;
|
|
66
87
|
} else if (source.text.includes("\n")) {
|
|
67
88
|
message += `\n at line ${start.line}, column ${start.column}`;
|
|
68
89
|
}
|
|
69
90
|
}
|
|
91
|
+
|
|
70
92
|
return message;
|
|
71
93
|
}
|
|
72
94
|
|