@hyperfixi/core 2.8.0 → 2.9.1
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/CHANGELOG.md +52 -0
- package/dist/ast-utils/index.js +1201 -891
- package/dist/ast-utils/index.mjs +1201 -891
- package/dist/chunks/{bridge-DHj-SYm2.js → bridge-BYhqTOnL.js} +2 -2
- package/dist/chunks/browser-modular-D2BHzZFB.js +2 -0
- package/dist/chunks/feature-eventsource-Bxg_UNZo.js +2 -0
- package/dist/chunks/feature-sockets-CcTxD5sT.js +2 -0
- package/dist/chunks/feature-webworker-DoqZ0Grg.js +2 -0
- package/dist/chunks/{index-CuPeasRm.js → index-DXgJaDj-.js} +2 -2
- package/dist/commands/index.js +168 -112
- package/dist/commands/index.mjs +168 -112
- package/dist/hyperfixi-browser-classic-i18n.js +1 -1
- package/dist/hyperfixi-browser-minimal.js +1 -1
- package/dist/hyperfixi-browser-standard.js +1 -1
- package/dist/hyperfixi-browser.js +1 -1
- package/dist/hyperfixi-classic-i18n.js +1 -1
- package/dist/hyperfixi-hx-v4.js +1 -1
- package/dist/hyperfixi-minimal.js +1 -1
- package/dist/hyperfixi-multilingual.js +1 -1
- package/dist/hyperfixi-standard.js +1 -1
- package/dist/hyperfixi.js +1 -1
- package/dist/hyperfixi.mjs +1 -1
- package/dist/index.js +2119 -1538
- package/dist/index.min.js +1 -1
- package/dist/index.mjs +2119 -1538
- package/dist/lokascript-browser-classic-i18n.js +1 -1
- package/dist/lokascript-browser-minimal.js +1 -1
- package/dist/lokascript-browser-standard.js +1 -1
- package/dist/lokascript-browser.js +1 -1
- package/dist/lokascript-multilingual.js +1 -1
- package/dist/lsp-metadata.js +5 -5
- package/dist/lsp-metadata.mjs +5 -5
- package/dist/metadata.js +25 -25
- package/dist/metadata.mjs +25 -25
- package/dist/multilingual/index.js +17 -17
- package/dist/multilingual/index.mjs +17 -17
- package/dist/parser/command-parsers/utility-commands.d.ts +1 -0
- package/dist/parser/full-parser.js +155 -106
- package/dist/parser/full-parser.mjs +155 -106
- package/dist/parser/parser.d.ts +1 -0
- package/dist/reference/index.js +1 -0
- package/dist/reference/index.mjs +1 -0
- package/dist/registry/index.js +155 -106
- package/dist/registry/index.mjs +155 -106
- package/dist/types/base-types.d.ts +3 -0
- package/package.json +7 -6
- package/dist/chunks/browser-modular-D1m0Eikh.js +0 -2
- package/dist/chunks/feature-eventsource-BpZvPy_K.js +0 -2
- package/dist/chunks/feature-sockets-CrYvjZ4j.js +0 -2
- package/dist/chunks/feature-webworker-BSYguEIW.js +0 -2
package/dist/commands/index.mjs
CHANGED
|
@@ -151,7 +151,7 @@ function resolveElement(target, context, commandName) {
|
|
|
151
151
|
if (!target) {
|
|
152
152
|
const me = context.me;
|
|
153
153
|
if (!me) {
|
|
154
|
-
throw new Error(withCmd(commandName, 'No target element
|
|
154
|
+
throw new Error(withCmd(commandName, 'No target element \u2014 provide explicit target or ensure context.me is set'));
|
|
155
155
|
}
|
|
156
156
|
return asHTMLElement(me);
|
|
157
157
|
}
|
|
@@ -177,7 +177,7 @@ function resolveElement(target, context, commandName) {
|
|
|
177
177
|
}
|
|
178
178
|
const doc = context.me?.ownerDocument ?? (typeof document !== 'undefined' ? document : null);
|
|
179
179
|
if (!doc) {
|
|
180
|
-
throw new Error(withCmd(commandName, 'DOM not available
|
|
180
|
+
throw new Error(withCmd(commandName, 'DOM not available \u2014 cannot resolve element selector'));
|
|
181
181
|
}
|
|
182
182
|
const element = doc.querySelector(trimmed);
|
|
183
183
|
if (!element) {
|
|
@@ -633,39 +633,39 @@ const DEBUG = {
|
|
|
633
633
|
const debug = {
|
|
634
634
|
command: (...args) => {
|
|
635
635
|
if (DEBUG.commands)
|
|
636
|
-
console.log('
|
|
636
|
+
console.log('\ud83d\udd27', ...args);
|
|
637
637
|
},
|
|
638
638
|
event: (...args) => {
|
|
639
639
|
if (DEBUG.events)
|
|
640
|
-
console.log('
|
|
640
|
+
console.log('\ud83c\udfaf', ...args);
|
|
641
641
|
},
|
|
642
642
|
parse: (...args) => {
|
|
643
643
|
if (DEBUG.parsing)
|
|
644
|
-
console.log('
|
|
644
|
+
console.log('\ud83d\udcdd', ...args);
|
|
645
645
|
},
|
|
646
646
|
expr: (...args) => {
|
|
647
647
|
if (DEBUG.expressions)
|
|
648
|
-
console.log('
|
|
648
|
+
console.log('\ud83d\udd0d', ...args);
|
|
649
649
|
},
|
|
650
650
|
expressions: (...args) => {
|
|
651
651
|
if (DEBUG.expressions)
|
|
652
|
-
console.log('
|
|
652
|
+
console.log('\ud83d\udd0d', ...args);
|
|
653
653
|
},
|
|
654
654
|
style: (...args) => {
|
|
655
655
|
if (DEBUG.styles)
|
|
656
|
-
console.log('
|
|
656
|
+
console.log('\ud83c\udfa8', ...args);
|
|
657
657
|
},
|
|
658
658
|
runtime: (...args) => {
|
|
659
659
|
if (DEBUG.runtime)
|
|
660
|
-
console.log('
|
|
660
|
+
console.log('\ud83d\ude80', ...args);
|
|
661
661
|
},
|
|
662
662
|
loop: (...args) => {
|
|
663
663
|
if (DEBUG.loops)
|
|
664
|
-
console.log('
|
|
664
|
+
console.log('\ud83d\udd01', ...args);
|
|
665
665
|
},
|
|
666
666
|
async: (...args) => {
|
|
667
667
|
if (DEBUG.async)
|
|
668
|
-
console.log('
|
|
668
|
+
console.log('\u23f3', ...args);
|
|
669
669
|
},
|
|
670
670
|
};
|
|
671
671
|
|
|
@@ -6218,6 +6218,7 @@ function tokenize(input) {
|
|
|
6218
6218
|
const prevToken = tokenizer.tokens[tokenizer.tokens.length - 1];
|
|
6219
6219
|
const isPossessive = nextChar === 's' &&
|
|
6220
6220
|
prevToken &&
|
|
6221
|
+
!/\s/.test(tokenizer.input[tokenizer.position - 1] ?? ' ') &&
|
|
6221
6222
|
(prevToken.kind === TokenKind.IDENTIFIER ||
|
|
6222
6223
|
prevToken.kind === TokenKind.SELECTOR ||
|
|
6223
6224
|
prevToken.value === ']' ||
|
|
@@ -7942,9 +7943,9 @@ function createPartialCommandNode(name, pos) {
|
|
|
7942
7943
|
};
|
|
7943
7944
|
}
|
|
7944
7945
|
function createProgramNode(statements) {
|
|
7945
|
-
debug.parse(
|
|
7946
|
+
debug.parse(`\u2705 createProgramNode: Called with ${statements.length} statements`);
|
|
7946
7947
|
if (statements.length === 0) {
|
|
7947
|
-
debug.parse(
|
|
7948
|
+
debug.parse(`\u2705 createProgramNode: Returning error node (0 statements)`);
|
|
7948
7949
|
return {
|
|
7949
7950
|
type: 'identifier',
|
|
7950
7951
|
name: '__ERROR__',
|
|
@@ -7955,7 +7956,7 @@ function createProgramNode(statements) {
|
|
|
7955
7956
|
};
|
|
7956
7957
|
}
|
|
7957
7958
|
if (statements.length === 1) {
|
|
7958
|
-
debug.parse(
|
|
7959
|
+
debug.parse(`\u2705 createProgramNode: Returning single statement (type=${statements[0].type})`);
|
|
7959
7960
|
return statements[0];
|
|
7960
7961
|
}
|
|
7961
7962
|
const programNode = {
|
|
@@ -7966,7 +7967,7 @@ function createProgramNode(statements) {
|
|
|
7966
7967
|
line: statements[0]?.line || 1,
|
|
7967
7968
|
column: statements[0]?.column || 1,
|
|
7968
7969
|
};
|
|
7969
|
-
debug.parse(
|
|
7970
|
+
debug.parse(`\u2705 createProgramNode: Returning Program node with ${statements.length} statements, type=${programNode.type}`);
|
|
7970
7971
|
return programNode;
|
|
7971
7972
|
}
|
|
7972
7973
|
|
|
@@ -8355,37 +8356,37 @@ function parseRepeatCommand(ctx, commandToken) {
|
|
|
8355
8356
|
ctx.advance();
|
|
8356
8357
|
loopType = 'until-event';
|
|
8357
8358
|
const eventToken = ctx.peek();
|
|
8358
|
-
debug.parse('
|
|
8359
|
+
debug.parse('\ud83d\udccd Parsing event name, current token:', {
|
|
8359
8360
|
value: eventToken.value,
|
|
8360
8361
|
kind: eventToken.kind,
|
|
8361
8362
|
});
|
|
8362
8363
|
if (isIdentifierLike(eventToken) || isEvent(eventToken)) {
|
|
8363
8364
|
eventName = eventToken.value;
|
|
8364
8365
|
ctx.advance();
|
|
8365
|
-
debug.parse('
|
|
8366
|
+
debug.parse('\u2705 Got event name:', eventName, 'Next token:', ctx.peek().value);
|
|
8366
8367
|
}
|
|
8367
8368
|
else {
|
|
8368
8369
|
throw new Error('Expected event name after "event"');
|
|
8369
8370
|
}
|
|
8370
|
-
debug.parse('
|
|
8371
|
+
debug.parse('\ud83d\udd0d Checking for "from", current token:', ctx.peek().value);
|
|
8371
8372
|
if (ctx.check(KEYWORDS$1.FROM)) {
|
|
8372
|
-
debug.parse('
|
|
8373
|
+
debug.parse('\u2705 Found "from", advancing...');
|
|
8373
8374
|
ctx.advance();
|
|
8374
|
-
debug.parse('
|
|
8375
|
+
debug.parse('\ud83d\udccd After consuming "from", current token:', ctx.peek().value);
|
|
8375
8376
|
if (consumeOptionalKeyword(ctx, KEYWORDS$1.THE)) {
|
|
8376
|
-
debug.parse('
|
|
8377
|
+
debug.parse('\u2705 Found "the", advancing...');
|
|
8377
8378
|
}
|
|
8378
8379
|
const beforePrimary = ctx.peek();
|
|
8379
|
-
debug.parse('
|
|
8380
|
+
debug.parse('\ud83d\udd0d Before parsePrimary for event target:', {
|
|
8380
8381
|
value: beforePrimary.value,
|
|
8381
8382
|
kind: beforePrimary.kind,
|
|
8382
8383
|
position: beforePrimary.start,
|
|
8383
8384
|
});
|
|
8384
8385
|
eventTarget = ctx.parsePrimary();
|
|
8385
|
-
debug.parse('
|
|
8386
|
+
debug.parse('\u2705 After parsePrimary, eventTarget:', eventTarget);
|
|
8386
8387
|
}
|
|
8387
8388
|
else {
|
|
8388
|
-
debug.parse('
|
|
8389
|
+
debug.parse('\u274c No "from" found, skipping target parsing');
|
|
8389
8390
|
}
|
|
8390
8391
|
}
|
|
8391
8392
|
else {
|
|
@@ -9486,16 +9487,6 @@ function stringNode(value, tok) {
|
|
|
9486
9487
|
column: tok.column,
|
|
9487
9488
|
};
|
|
9488
9489
|
}
|
|
9489
|
-
function isNakedURLStart(ctx) {
|
|
9490
|
-
const tok = ctx.peek();
|
|
9491
|
-
if (tok.value === '/')
|
|
9492
|
-
return true;
|
|
9493
|
-
if (ctx.checkIdentifierLike()) {
|
|
9494
|
-
const next = ctx.peekAt(1);
|
|
9495
|
-
return !!next && next.value === ':' && next.start === tok.end;
|
|
9496
|
-
}
|
|
9497
|
-
return false;
|
|
9498
|
-
}
|
|
9499
9490
|
function parseGoCommand(ctx, identifierNode) {
|
|
9500
9491
|
const args = [];
|
|
9501
9492
|
while (!isCommandBoundary(ctx, ['when', 'where', 'catch', 'finally'])) {
|
|
@@ -9654,6 +9645,16 @@ function isFetchURLTerminator(ctx) {
|
|
|
9654
9645
|
return (['as', 'with', '{', 'then', 'end', 'else', 'otherwise', ')'].includes(val) ||
|
|
9655
9646
|
isCommandBoundary(ctx));
|
|
9656
9647
|
}
|
|
9648
|
+
function isNakedURLStart(ctx) {
|
|
9649
|
+
const tok = ctx.peek();
|
|
9650
|
+
if (tok.value === '/')
|
|
9651
|
+
return true;
|
|
9652
|
+
if (ctx.checkIdentifierLike()) {
|
|
9653
|
+
const next = ctx.peekAt(1);
|
|
9654
|
+
return !!next && next.value === ':' && next.start === tok.end;
|
|
9655
|
+
}
|
|
9656
|
+
return false;
|
|
9657
|
+
}
|
|
9657
9658
|
function parseBareURLPath(ctx, isTerminator = isFetchURLTerminator) {
|
|
9658
9659
|
const startPos = ctx.savePosition();
|
|
9659
9660
|
let path = '';
|
|
@@ -9675,7 +9676,7 @@ function parseBareURLPath(ctx, isTerminator = isFetchURLTerminator) {
|
|
|
9675
9676
|
function parseFetchCommand(ctx, commandToken) {
|
|
9676
9677
|
const modifiers = {};
|
|
9677
9678
|
let url = null;
|
|
9678
|
-
if (!ctx.isAtEnd() && ctx
|
|
9679
|
+
if (!ctx.isAtEnd() && isNakedURLStart(ctx)) {
|
|
9679
9680
|
url = parseBareURLPath(ctx);
|
|
9680
9681
|
}
|
|
9681
9682
|
if (!url) {
|
|
@@ -10241,26 +10242,26 @@ class Parser {
|
|
|
10241
10242
|
const commandSequence = this.parseCommandSequence();
|
|
10242
10243
|
if (commandSequence) {
|
|
10243
10244
|
if (!this.isAtEnd() && this.check('on')) {
|
|
10244
|
-
debug.parse('
|
|
10245
|
+
debug.parse('\u2705 PARSER: Found event handlers after command sequence, parsing as program');
|
|
10245
10246
|
const statements = [commandSequence];
|
|
10246
|
-
debug.parse(
|
|
10247
|
+
debug.parse(`\u2705 PARSER: Starting with ${statements.length} statement(s) from command sequence`);
|
|
10247
10248
|
let eventHandlerCount = 0;
|
|
10248
10249
|
while (!this.isAtEnd() && this.check('on')) {
|
|
10249
|
-
debug.parse(
|
|
10250
|
+
debug.parse(`\u2705 PARSER: Parsing event handler #${eventHandlerCount + 1}, current token: ${this.peek().value}`);
|
|
10250
10251
|
this.advance();
|
|
10251
10252
|
const eventHandler = this.parseEventHandler();
|
|
10252
|
-
debug.parse(
|
|
10253
|
+
debug.parse(`\u2705 PARSER: parseEventHandler returned:`, eventHandler
|
|
10253
10254
|
? `type=${eventHandler.type}, event=${eventHandler.event}`
|
|
10254
10255
|
: 'null');
|
|
10255
10256
|
if (eventHandler) {
|
|
10256
10257
|
statements.push(eventHandler);
|
|
10257
10258
|
eventHandlerCount++;
|
|
10258
|
-
debug.parse(
|
|
10259
|
+
debug.parse(`\u2705 PARSER: Added event handler, now have ${statements.length} statements total`);
|
|
10259
10260
|
}
|
|
10260
|
-
debug.parse(
|
|
10261
|
+
debug.parse(`\u2705 PARSER: After parsing event handler, current token: ${this.isAtEnd() ? 'END' : this.peek().value}, isAtEnd=${this.isAtEnd()}, check('on')=${this.check('on')}`);
|
|
10261
10262
|
if (!this.isAtEnd() && !this.check('on')) {
|
|
10262
10263
|
if (!this.isAtEnd()) {
|
|
10263
|
-
debug.parse(
|
|
10264
|
+
debug.parse(`\u26a0\ufe0f PARSER: Unexpected token after event handlers: ${this.peek().value}`);
|
|
10264
10265
|
this.addError(`Unexpected token after event handlers: ${this.peek().value}`);
|
|
10265
10266
|
return {
|
|
10266
10267
|
success: false,
|
|
@@ -10269,11 +10270,11 @@ class Parser {
|
|
|
10269
10270
|
error: this.error,
|
|
10270
10271
|
};
|
|
10271
10272
|
}
|
|
10272
|
-
debug.parse(
|
|
10273
|
+
debug.parse(`\u2705 PARSER: No more event handlers, at end of input`);
|
|
10273
10274
|
break;
|
|
10274
10275
|
}
|
|
10275
10276
|
}
|
|
10276
|
-
debug.parse(
|
|
10277
|
+
debug.parse(`\u2705 PARSER: Finished parsing, creating Program node with ${statements.length} statements`);
|
|
10277
10278
|
if (this.error) {
|
|
10278
10279
|
return {
|
|
10279
10280
|
success: false,
|
|
@@ -10668,41 +10669,41 @@ class Parser {
|
|
|
10668
10669
|
parseCommandListUntilTerminator(extraStops) {
|
|
10669
10670
|
const commands = [];
|
|
10670
10671
|
const isStop = () => this.check('end') || extraStops.some(s => this.check(s));
|
|
10671
|
-
debug.parse('
|
|
10672
|
+
debug.parse('\ud83d\udd04 parseCommandListUntilTerminator: Starting (extraStops:', extraStops.join(','), ')');
|
|
10672
10673
|
while (!this.isAtEnd() && !isStop()) {
|
|
10673
|
-
debug.parse('
|
|
10674
|
+
debug.parse('\ud83d\udccd Loop iteration, current token:', this.peek().value, 'kind:', this.peek().kind);
|
|
10674
10675
|
let parsedCommand = false;
|
|
10675
10676
|
const isCommandToken = this.checkIsCommand();
|
|
10676
10677
|
const isCommandIdentifier = !isCommandToken && this.checkIdentifier() && this.isCommand(this.peek().value);
|
|
10677
10678
|
if (isCommandToken || isCommandIdentifier) {
|
|
10678
|
-
debug.parse(isCommandToken ? '
|
|
10679
|
+
debug.parse(isCommandToken ? '\u2705 Found COMMAND token:' : '\u2705 Found IDENTIFIER that is a command:', this.peek().value);
|
|
10679
10680
|
this.advance();
|
|
10680
10681
|
const savedError = this.error;
|
|
10681
10682
|
try {
|
|
10682
10683
|
const cmd = this.parseCommand();
|
|
10683
10684
|
if (this.error && this.error !== savedError) {
|
|
10684
|
-
debug.parse('
|
|
10685
|
+
debug.parse('\u26a0\ufe0f parseCommandListUntilTerminator: Command parsing added error, restoring. Error was:', this.error.message);
|
|
10685
10686
|
this.error = savedError;
|
|
10686
10687
|
}
|
|
10687
10688
|
if (cmd) {
|
|
10688
|
-
debug.parse('
|
|
10689
|
+
debug.parse('\u2705 Parsed command:', cmd.name);
|
|
10689
10690
|
commands.push(cmd);
|
|
10690
10691
|
parsedCommand = true;
|
|
10691
10692
|
}
|
|
10692
10693
|
}
|
|
10693
10694
|
catch (error) {
|
|
10694
|
-
debug.parse('
|
|
10695
|
+
debug.parse('\u26a0\ufe0f parseCommandListUntilTerminator: Command parsing threw, restoring:', error instanceof Error ? error.message : String(error));
|
|
10695
10696
|
this.error = savedError;
|
|
10696
10697
|
}
|
|
10697
10698
|
}
|
|
10698
10699
|
else if (this.checkIdentifier()) {
|
|
10699
|
-
debug.parse('
|
|
10700
|
+
debug.parse('\u274c IDENTIFIER is not a command:', this.peek().value);
|
|
10700
10701
|
}
|
|
10701
10702
|
if (!parsedCommand) {
|
|
10702
|
-
debug.parse('
|
|
10703
|
+
debug.parse('\u274c No command parsed, breaking. Current token:', this.peek().value);
|
|
10703
10704
|
break;
|
|
10704
10705
|
}
|
|
10705
|
-
debug.parse('
|
|
10706
|
+
debug.parse('\ud83d\udccd After parsing command, current token:', this.peek().value);
|
|
10706
10707
|
while (!this.isAtEnd() &&
|
|
10707
10708
|
!isStop() &&
|
|
10708
10709
|
!this.checkIsCommand() &&
|
|
@@ -10710,19 +10711,19 @@ class Parser {
|
|
|
10710
10711
|
!this.check('then') &&
|
|
10711
10712
|
!this.check('and') &&
|
|
10712
10713
|
!this.check(',')) {
|
|
10713
|
-
debug.parse('
|
|
10714
|
+
debug.parse('\u26a0\ufe0f Skipping unexpected token:', this.peek().value);
|
|
10714
10715
|
this.advance();
|
|
10715
10716
|
}
|
|
10716
10717
|
if (this.match('then', 'and', ',')) {
|
|
10717
|
-
debug.parse('
|
|
10718
|
+
debug.parse('\u2705 Found separator, continuing');
|
|
10718
10719
|
continue;
|
|
10719
10720
|
}
|
|
10720
10721
|
else if (this.checkIsCommand() || this.isCommand(this.peek().value)) {
|
|
10721
|
-
debug.parse('
|
|
10722
|
+
debug.parse('\u2705 Next token is a command, continuing without separator');
|
|
10722
10723
|
continue;
|
|
10723
10724
|
}
|
|
10724
10725
|
else {
|
|
10725
|
-
debug.parse('
|
|
10726
|
+
debug.parse('\ud83d\udccd No separator and no command, breaking. Current token:', this.peek().value);
|
|
10726
10727
|
break;
|
|
10727
10728
|
}
|
|
10728
10729
|
}
|
|
@@ -10736,18 +10737,18 @@ class Parser {
|
|
|
10736
10737
|
if (!this.check('end') && !extraStops.some(s => this.check(s))) {
|
|
10737
10738
|
terminator = '';
|
|
10738
10739
|
}
|
|
10739
|
-
debug.parse('
|
|
10740
|
+
debug.parse('\u2705 parseCommandListUntilTerminator: parsed', commands.length, 'commands (terminator:', terminator, ')');
|
|
10740
10741
|
return { commands, terminator };
|
|
10741
10742
|
}
|
|
10742
10743
|
parseCommandListUntilEnd() {
|
|
10743
10744
|
const { commands } = this.parseCommandListUntilTerminator([]);
|
|
10744
|
-
debug.parse('
|
|
10745
|
+
debug.parse('\ud83d\udd0d After loop, checking for "end". Current token:', this.peek().value);
|
|
10745
10746
|
if (this.check('end')) {
|
|
10746
|
-
debug.parse('
|
|
10747
|
+
debug.parse('\u2705 Found "end", consuming it');
|
|
10747
10748
|
this.advance();
|
|
10748
10749
|
}
|
|
10749
10750
|
else {
|
|
10750
|
-
debug.parse('
|
|
10751
|
+
debug.parse('\u274c ERROR: Expected "end" but got:', this.peek().value, 'at position:', this.peek().start);
|
|
10751
10752
|
throw new Error('Expected "end" to close repeat block');
|
|
10752
10753
|
}
|
|
10753
10754
|
return commands;
|
|
@@ -11420,6 +11421,23 @@ class Parser {
|
|
|
11420
11421
|
this.consume(')', "Expected ')' after parameter list");
|
|
11421
11422
|
}
|
|
11422
11423
|
const bodyCommands = this.parseCommandBlock(['end', 'catch', 'finally']);
|
|
11424
|
+
const { errorSymbol, errorHandler, finallyHandler } = this.parseErrorAndFinallyBlocks();
|
|
11425
|
+
this.consume('end', "Expected 'end' after function definition");
|
|
11426
|
+
return {
|
|
11427
|
+
type: 'def',
|
|
11428
|
+
name: funcName,
|
|
11429
|
+
params,
|
|
11430
|
+
body: bodyCommands,
|
|
11431
|
+
...(errorSymbol !== undefined && { errorSymbol }),
|
|
11432
|
+
...(errorHandler !== undefined && { errorHandler }),
|
|
11433
|
+
...(finallyHandler !== undefined && { finallyHandler }),
|
|
11434
|
+
start: pos.start,
|
|
11435
|
+
end: this.getPosition().end,
|
|
11436
|
+
line: pos.line,
|
|
11437
|
+
column: pos.column,
|
|
11438
|
+
};
|
|
11439
|
+
}
|
|
11440
|
+
parseErrorAndFinallyBlocks() {
|
|
11423
11441
|
let errorSymbol;
|
|
11424
11442
|
let errorHandler;
|
|
11425
11443
|
if (this.check('catch')) {
|
|
@@ -11434,19 +11452,10 @@ class Parser {
|
|
|
11434
11452
|
this.advance();
|
|
11435
11453
|
finallyHandler = this.parseCommandBlock(['end']);
|
|
11436
11454
|
}
|
|
11437
|
-
this.consume('end', "Expected 'end' after function definition");
|
|
11438
11455
|
return {
|
|
11439
|
-
type: 'def',
|
|
11440
|
-
name: funcName,
|
|
11441
|
-
params,
|
|
11442
|
-
body: bodyCommands,
|
|
11443
11456
|
...(errorSymbol !== undefined && { errorSymbol }),
|
|
11444
11457
|
...(errorHandler !== undefined && { errorHandler }),
|
|
11445
11458
|
...(finallyHandler !== undefined && { finallyHandler }),
|
|
11446
|
-
start: pos.start,
|
|
11447
|
-
end: this.getPosition().end,
|
|
11448
|
-
line: pos.line,
|
|
11449
|
-
column: pos.column,
|
|
11450
11459
|
};
|
|
11451
11460
|
}
|
|
11452
11461
|
parseEventNameWithNamespace(errorMessage) {
|
|
@@ -11591,13 +11600,13 @@ class Parser {
|
|
|
11591
11600
|
try {
|
|
11592
11601
|
const cmd = this.parseCommand();
|
|
11593
11602
|
if (this.error && this.error !== savedError) {
|
|
11594
|
-
debug.parse('
|
|
11603
|
+
debug.parse('\u26a0\ufe0f Command parsing added error, restoring error state. Error was:', this.error.message);
|
|
11595
11604
|
this.error = savedError;
|
|
11596
11605
|
}
|
|
11597
11606
|
return cmd;
|
|
11598
11607
|
}
|
|
11599
11608
|
catch (error) {
|
|
11600
|
-
debug.parse('
|
|
11609
|
+
debug.parse('\u26a0\ufe0f Command parsing threw exception, restoring error state:', error instanceof Error ? error.message : String(error));
|
|
11601
11610
|
this.error = savedError;
|
|
11602
11611
|
return null;
|
|
11603
11612
|
}
|
|
@@ -11614,12 +11623,12 @@ class Parser {
|
|
|
11614
11623
|
const timeToken = this.advance();
|
|
11615
11624
|
const delayMs = parseTimeToMs(timeToken.value);
|
|
11616
11625
|
modifiers[modifierKey] = delayMs;
|
|
11617
|
-
debug.parse(
|
|
11626
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed '${modName} at ${timeToken.value}' (${delayMs}ms)`);
|
|
11618
11627
|
}
|
|
11619
11628
|
else if (this.matchNumber()) {
|
|
11620
11629
|
const delayMs = parseInt(this.previous().value, 10);
|
|
11621
11630
|
modifiers[modifierKey] = delayMs;
|
|
11622
|
-
debug.parse(
|
|
11631
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed '${modName} at ${delayMs}'`);
|
|
11623
11632
|
}
|
|
11624
11633
|
else {
|
|
11625
11634
|
this.addError(`Expected time expression after '${modName} at', got: ${this.peek().value}`);
|
|
@@ -11630,7 +11639,7 @@ class Parser {
|
|
|
11630
11639
|
}
|
|
11631
11640
|
}
|
|
11632
11641
|
parseEventHandler() {
|
|
11633
|
-
debug.parse(
|
|
11642
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: ENTRY - parsing event handler`);
|
|
11634
11643
|
const eventNames = [];
|
|
11635
11644
|
let firstOnceAlias = false;
|
|
11636
11645
|
if (this.check('first') && !this.checkIsCommand() && this.current + 1 < this.tokens.length) {
|
|
@@ -11639,27 +11648,27 @@ class Parser {
|
|
|
11639
11648
|
if (peek2Value && peek2Value !== 'of' && peek2Value !== 'in' && peek2Value !== 'from') {
|
|
11640
11649
|
this.advance();
|
|
11641
11650
|
firstOnceAlias = true;
|
|
11642
|
-
debug.parse(
|
|
11651
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed 'first' as .once alias`);
|
|
11643
11652
|
}
|
|
11644
11653
|
}
|
|
11645
11654
|
const event = this.parseEventNameWithNamespace("Expected event name after 'on'");
|
|
11646
11655
|
eventNames.push(event);
|
|
11647
|
-
debug.parse(
|
|
11656
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed first event name: ${event}`);
|
|
11648
11657
|
while (this.check('or')) {
|
|
11649
11658
|
this.advance();
|
|
11650
|
-
debug.parse(
|
|
11659
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Found 'or', parsing additional event name`);
|
|
11651
11660
|
const additionalEvent = this.parseEventNameWithNamespace("Expected event name after 'or'");
|
|
11652
11661
|
eventNames.push(additionalEvent);
|
|
11653
|
-
debug.parse(
|
|
11662
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed additional event name: ${additionalEvent}`);
|
|
11654
11663
|
}
|
|
11655
|
-
debug.parse(
|
|
11664
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Total events parsed: ${eventNames.join(', ')}`);
|
|
11656
11665
|
let customEventSource;
|
|
11657
11666
|
if (this.registryIntegration) {
|
|
11658
11667
|
const firstEvent = eventNames[0];
|
|
11659
11668
|
if (this.registryIntegration.hasEventSource(firstEvent)) {
|
|
11660
11669
|
const source = this.registryIntegration.getEventSource(firstEvent);
|
|
11661
11670
|
customEventSource = source?.name;
|
|
11662
|
-
debug.parse(
|
|
11671
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Detected custom event source '${customEventSource}' for event '${firstEvent}'`);
|
|
11663
11672
|
}
|
|
11664
11673
|
}
|
|
11665
11674
|
const eventParams = [];
|
|
@@ -11671,7 +11680,7 @@ class Parser {
|
|
|
11671
11680
|
} while (this.match(','));
|
|
11672
11681
|
}
|
|
11673
11682
|
this.consume(')', "Expected ')' after event parameters");
|
|
11674
|
-
debug.parse(
|
|
11683
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed event parameters: ${eventParams.join(', ')}`);
|
|
11675
11684
|
}
|
|
11676
11685
|
const modifiers = {};
|
|
11677
11686
|
while (this.check('.')) {
|
|
@@ -11680,15 +11689,15 @@ class Parser {
|
|
|
11680
11689
|
const modName = modToken.value.toLowerCase();
|
|
11681
11690
|
if (modName === 'once') {
|
|
11682
11691
|
modifiers.once = true;
|
|
11683
|
-
debug.parse(
|
|
11692
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed modifier '.once'`);
|
|
11684
11693
|
}
|
|
11685
11694
|
else if (modName === 'prevent') {
|
|
11686
11695
|
modifiers.prevent = true;
|
|
11687
|
-
debug.parse(
|
|
11696
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed modifier '.prevent'`);
|
|
11688
11697
|
}
|
|
11689
11698
|
else if (modName === 'stop') {
|
|
11690
11699
|
modifiers.stop = true;
|
|
11691
|
-
debug.parse(
|
|
11700
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed modifier '.stop'`);
|
|
11692
11701
|
}
|
|
11693
11702
|
else if (modName === 'debounce' || modName === 'throttle') {
|
|
11694
11703
|
if (this.check('(')) {
|
|
@@ -11700,11 +11709,11 @@ class Parser {
|
|
|
11700
11709
|
}
|
|
11701
11710
|
if (modName === 'debounce') {
|
|
11702
11711
|
modifiers.debounce = delayMs;
|
|
11703
|
-
debug.parse(
|
|
11712
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed modifier '.debounce(${delayMs})'`);
|
|
11704
11713
|
}
|
|
11705
11714
|
else {
|
|
11706
11715
|
modifiers.throttle = delayMs;
|
|
11707
|
-
debug.parse(
|
|
11716
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed modifier '.throttle(${delayMs})'`);
|
|
11708
11717
|
}
|
|
11709
11718
|
this.consume(')', `Expected ')' after ${modName} delay`);
|
|
11710
11719
|
}
|
|
@@ -11713,7 +11722,7 @@ class Parser {
|
|
|
11713
11722
|
}
|
|
11714
11723
|
}
|
|
11715
11724
|
else {
|
|
11716
|
-
debug.parse(
|
|
11725
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Warning - unknown modifier '.${modName}'`);
|
|
11717
11726
|
}
|
|
11718
11727
|
}
|
|
11719
11728
|
this.parseTemporalKeywordModifiers(modifiers);
|
|
@@ -11721,7 +11730,7 @@ class Parser {
|
|
|
11721
11730
|
modifiers.once = true;
|
|
11722
11731
|
}
|
|
11723
11732
|
if (Object.keys(modifiers).length > 0) {
|
|
11724
|
-
debug.parse(
|
|
11733
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed modifiers:`, modifiers);
|
|
11725
11734
|
}
|
|
11726
11735
|
let condition;
|
|
11727
11736
|
if (this.match('[')) {
|
|
@@ -11732,7 +11741,7 @@ class Parser {
|
|
|
11732
11741
|
if (this.match('from')) {
|
|
11733
11742
|
const targetToken = this.advance();
|
|
11734
11743
|
target = targetToken.value;
|
|
11735
|
-
debug.parse(
|
|
11744
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed 'from' target: ${target} (kind: ${targetToken.kind})`);
|
|
11736
11745
|
this.parseTemporalKeywordModifiers(modifiers);
|
|
11737
11746
|
}
|
|
11738
11747
|
let attributeName;
|
|
@@ -11744,32 +11753,36 @@ class Parser {
|
|
|
11744
11753
|
else {
|
|
11745
11754
|
attributeName = attrToken.value;
|
|
11746
11755
|
}
|
|
11747
|
-
debug.parse(
|
|
11756
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed attribute name: ${attributeName}`);
|
|
11748
11757
|
}
|
|
11749
11758
|
let watchTarget;
|
|
11750
11759
|
if (this.match('in')) {
|
|
11751
|
-
debug.parse(
|
|
11760
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Found 'in' keyword, parsing watch target`);
|
|
11752
11761
|
watchTarget = this.parseExpression();
|
|
11753
|
-
debug.parse(
|
|
11762
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Parsed watch target expression`);
|
|
11754
11763
|
}
|
|
11755
11764
|
const commands = [];
|
|
11756
|
-
debug.parse(
|
|
11765
|
+
debug.parse(`\u2705 parseEventHandler: About to parse commands, current token: ${this.isAtEnd() ? 'END' : this.peek().value}, isAtEnd: ${this.isAtEnd()}`);
|
|
11757
11766
|
while (!this.isAtEnd()) {
|
|
11758
|
-
debug.parse(
|
|
11767
|
+
debug.parse(`\u2705 parseEventHandler: Loop iteration, current token: ${this.peek().value}, kind: ${this.peek().kind}`);
|
|
11759
11768
|
if (this.check('on')) {
|
|
11760
|
-
debug.parse(
|
|
11769
|
+
debug.parse(`\u2705 parseEventHandler: Stopping command parsing, found next event handler 'on'`);
|
|
11761
11770
|
break;
|
|
11762
11771
|
}
|
|
11763
11772
|
if (this.checkComment()) {
|
|
11764
|
-
debug.parse(
|
|
11773
|
+
debug.parse(`\u2705 parseEventHandler: Skipping comment token: ${this.peek().value}`);
|
|
11765
11774
|
this.advance();
|
|
11766
11775
|
continue;
|
|
11767
11776
|
}
|
|
11768
11777
|
if (this.check('end')) {
|
|
11769
|
-
debug.parse(
|
|
11778
|
+
debug.parse(`\u2705 parseEventHandler: Stopping command parsing, found 'end' keyword`);
|
|
11770
11779
|
this.advance();
|
|
11771
11780
|
break;
|
|
11772
11781
|
}
|
|
11782
|
+
if (this.check('catch') || this.check('finally')) {
|
|
11783
|
+
debug.parse(`\u2705 parseEventHandler: Stopping command parsing, found '${this.peek().value}'`);
|
|
11784
|
+
break;
|
|
11785
|
+
}
|
|
11773
11786
|
if (this.checkIsCommand()) {
|
|
11774
11787
|
const nextIsOpenParen = this.tokens[this.current + 1]?.value === '(';
|
|
11775
11788
|
const commandName = this.peek().value.toLowerCase();
|
|
@@ -11798,7 +11811,7 @@ class Parser {
|
|
|
11798
11811
|
const cmd = this.parseCommandWithErrorRecovery();
|
|
11799
11812
|
if (cmd) {
|
|
11800
11813
|
commands.push(cmd);
|
|
11801
|
-
debug.parse(
|
|
11814
|
+
debug.parse(`\u2705 parseEventHandler: Parsed command, next token: ${this.isAtEnd() ? 'END' : this.peek().value}`);
|
|
11802
11815
|
}
|
|
11803
11816
|
}
|
|
11804
11817
|
}
|
|
@@ -11816,7 +11829,7 @@ class Parser {
|
|
|
11816
11829
|
expr = this.parseExpression();
|
|
11817
11830
|
}
|
|
11818
11831
|
catch (error) {
|
|
11819
|
-
debug.parse('
|
|
11832
|
+
debug.parse('\u26a0\ufe0f Expression parsing error, restoring error state:', error instanceof Error ? error.message : String(error));
|
|
11820
11833
|
this.error = savedError;
|
|
11821
11834
|
break;
|
|
11822
11835
|
}
|
|
@@ -11863,7 +11876,9 @@ class Parser {
|
|
|
11863
11876
|
!this.check('then') &&
|
|
11864
11877
|
!this.check('and') &&
|
|
11865
11878
|
!this.check(',') &&
|
|
11866
|
-
!this.check('on')
|
|
11879
|
+
!this.check('on') &&
|
|
11880
|
+
!this.check('catch') &&
|
|
11881
|
+
!this.check('finally')) {
|
|
11867
11882
|
this.advance();
|
|
11868
11883
|
}
|
|
11869
11884
|
if (this.match('then', 'and', ',')) {
|
|
@@ -11876,12 +11891,24 @@ class Parser {
|
|
|
11876
11891
|
break;
|
|
11877
11892
|
}
|
|
11878
11893
|
}
|
|
11894
|
+
let errorSymbol;
|
|
11895
|
+
let errorHandler;
|
|
11896
|
+
let finallyHandler;
|
|
11897
|
+
if (!this.isAtEnd() && (this.check('catch') || this.check('finally'))) {
|
|
11898
|
+
({ errorSymbol, errorHandler, finallyHandler } = this.parseErrorAndFinallyBlocks());
|
|
11899
|
+
if (this.check('end')) {
|
|
11900
|
+
this.advance();
|
|
11901
|
+
}
|
|
11902
|
+
}
|
|
11879
11903
|
const pos = this.getPosition();
|
|
11880
11904
|
const node = {
|
|
11881
11905
|
type: 'eventHandler',
|
|
11882
11906
|
event: eventNames.length === 1 ? eventNames[0] : eventNames.join('|'),
|
|
11883
11907
|
events: eventNames,
|
|
11884
11908
|
commands,
|
|
11909
|
+
...(errorSymbol !== undefined && { errorSymbol }),
|
|
11910
|
+
...(errorHandler !== undefined && { errorHandler }),
|
|
11911
|
+
...(finallyHandler !== undefined && { finallyHandler }),
|
|
11885
11912
|
...(eventParams.length > 0 && { args: eventParams }),
|
|
11886
11913
|
...(condition && { condition }),
|
|
11887
11914
|
...(target && { target }),
|
|
@@ -11894,7 +11921,7 @@ class Parser {
|
|
|
11894
11921
|
line: pos.line,
|
|
11895
11922
|
column: pos.column,
|
|
11896
11923
|
};
|
|
11897
|
-
debug.parse(
|
|
11924
|
+
debug.parse(`\ud83d\udd27 parseEventHandler: Created node with events: ${eventNames.join(', ')}, attributeName: ${attributeName || 'none'}, watchTarget: ${watchTarget ? 'yes' : 'none'}`);
|
|
11898
11925
|
return node;
|
|
11899
11926
|
}
|
|
11900
11927
|
parseBehaviorDefinition() {
|
|
@@ -11959,11 +11986,33 @@ class Parser {
|
|
|
11959
11986
|
}
|
|
11960
11987
|
}
|
|
11961
11988
|
}
|
|
11962
|
-
const handlerCommands = this.
|
|
11989
|
+
const { commands: handlerCommands, terminator } = this.parseCommandListUntilTerminator([
|
|
11990
|
+
'catch',
|
|
11991
|
+
'finally',
|
|
11992
|
+
]);
|
|
11993
|
+
let handlerErrorSymbol;
|
|
11994
|
+
let handlerErrorHandler;
|
|
11995
|
+
let handlerFinallyHandler;
|
|
11996
|
+
if (terminator === 'catch' || terminator === 'finally') {
|
|
11997
|
+
({
|
|
11998
|
+
errorSymbol: handlerErrorSymbol,
|
|
11999
|
+
errorHandler: handlerErrorHandler,
|
|
12000
|
+
finallyHandler: handlerFinallyHandler,
|
|
12001
|
+
} = this.parseErrorAndFinallyBlocks());
|
|
12002
|
+
}
|
|
12003
|
+
if (this.check('end')) {
|
|
12004
|
+
this.advance();
|
|
12005
|
+
}
|
|
12006
|
+
else {
|
|
12007
|
+
throw new Error('Expected "end" to close behavior event handler');
|
|
12008
|
+
}
|
|
11963
12009
|
const handlerNode = {
|
|
11964
12010
|
type: 'eventHandler',
|
|
11965
12011
|
event: eventName,
|
|
11966
12012
|
commands: handlerCommands,
|
|
12013
|
+
...(handlerErrorSymbol !== undefined && { errorSymbol: handlerErrorSymbol }),
|
|
12014
|
+
...(handlerErrorHandler !== undefined && { errorHandler: handlerErrorHandler }),
|
|
12015
|
+
...(handlerFinallyHandler !== undefined && { finallyHandler: handlerFinallyHandler }),
|
|
11967
12016
|
...(eventSource !== undefined && { target: eventSource }),
|
|
11968
12017
|
...(eventArgs.length > 0 && { args: eventArgs }),
|
|
11969
12018
|
start: handlerPos.start,
|
|
@@ -12018,7 +12067,7 @@ class Parser {
|
|
|
12018
12067
|
this.error.message.includes('unclosed parenthes') ||
|
|
12019
12068
|
this.error.message.includes('Unclosed parenthes');
|
|
12020
12069
|
if (!isCriticalError) {
|
|
12021
|
-
debug.parse('
|
|
12070
|
+
debug.parse('\u26a0\ufe0f parseCommandSequence: Command parsing added non-critical error, restoring error state. Error was:', this.error.message);
|
|
12022
12071
|
this.error = savedError;
|
|
12023
12072
|
}
|
|
12024
12073
|
}
|
|
@@ -12028,11 +12077,11 @@ class Parser {
|
|
|
12028
12077
|
!this.isCommand(this.peek().value) &&
|
|
12029
12078
|
!this.check('then') &&
|
|
12030
12079
|
!this.check('on')) {
|
|
12031
|
-
debug.parse('
|
|
12080
|
+
debug.parse('\u26a0\ufe0f parseCommandSequence: Skipping unexpected token:', this.peek().value);
|
|
12032
12081
|
this.advance();
|
|
12033
12082
|
}
|
|
12034
12083
|
if (this.check('on')) {
|
|
12035
|
-
debug.parse('
|
|
12084
|
+
debug.parse('\u2705 parseCommandSequence: Found "on" token, stopping command sequence to allow event handler parsing');
|
|
12036
12085
|
break;
|
|
12037
12086
|
}
|
|
12038
12087
|
if (this.match('then')) {
|
|
@@ -12476,7 +12525,7 @@ class Parser {
|
|
|
12476
12525
|
if (!this.check(')') && callee.type === 'identifier') {
|
|
12477
12526
|
const funcName = callee.name;
|
|
12478
12527
|
if (CommandClassification.isCSSFunction(funcName)) {
|
|
12479
|
-
debug.parse(
|
|
12528
|
+
debug.parse(`\ud83d\udca1 Tip: CSS functions like ${funcName}() should be quoted for clean parsing. ` +
|
|
12480
12529
|
`Use '${funcName}(...)' or \`${funcName}(...)\` instead.`);
|
|
12481
12530
|
}
|
|
12482
12531
|
}
|
|
@@ -12778,7 +12827,7 @@ class Parser {
|
|
|
12778
12827
|
if (this.checkIsCommand() || (this.isCommand(token.value) && !this.isKeyword(token.value))) {
|
|
12779
12828
|
return;
|
|
12780
12829
|
}
|
|
12781
|
-
debug.parse('
|
|
12830
|
+
debug.parse('\u26a0\ufe0f synchronize: Skipping token:', token.value);
|
|
12782
12831
|
this.advance();
|
|
12783
12832
|
}
|
|
12784
12833
|
}
|
|
@@ -16765,8 +16814,15 @@ let FetchCommand = (() => {
|
|
|
16765
16814
|
}
|
|
16766
16815
|
async parseURL(arg, evaluator, context) {
|
|
16767
16816
|
const v = await evaluator.evaluate(arg, context);
|
|
16768
|
-
if (typeof v !== 'string' || !v)
|
|
16817
|
+
if (typeof v !== 'string' || !v) {
|
|
16818
|
+
const node = arg;
|
|
16819
|
+
if ((v === undefined || v === null) && node?.type === 'identifier' && node.name) {
|
|
16820
|
+
throw new Error(`fetch: URL expression "${node.name}" evaluated to ${String(v)} \u2014 ` +
|
|
16821
|
+
`check the variable is set, or quote it if you meant a literal URL ` +
|
|
16822
|
+
`(fetch 'https://example.com/path')`);
|
|
16823
|
+
}
|
|
16769
16824
|
throw new Error('fetch: URL must be a non-empty string');
|
|
16825
|
+
}
|
|
16770
16826
|
return v;
|
|
16771
16827
|
}
|
|
16772
16828
|
parseResponseType(asNode) {
|
|
@@ -16985,7 +17041,7 @@ let SetCommand = (() => {
|
|
|
16985
17041
|
if (typeof firstValue !== 'string') {
|
|
16986
17042
|
const isMember = firstArg?.type === 'memberExpression' || firstArg?.type === 'propertyAccess';
|
|
16987
17043
|
const hint = isMember
|
|
16988
|
-
? ` (a property chain evaluated to ${firstValue === null ? 'null' : typeof firstValue}
|
|
17044
|
+
? ` (a property chain evaluated to ${firstValue === null ? 'null' : typeof firstValue} \u2014 check that all intermediate objects exist)`
|
|
16989
17045
|
: '';
|
|
16990
17046
|
throw new Error(`set command target must be a string or object literal${hint}`);
|
|
16991
17047
|
}
|
|
@@ -18063,7 +18119,7 @@ let BeepCommand = (() => {
|
|
|
18063
18119
|
return { expressionCount: 0, debugged: true, outputs: [] };
|
|
18064
18120
|
}
|
|
18065
18121
|
const outputs = [];
|
|
18066
|
-
console.group('
|
|
18122
|
+
console.group('\ud83d\udd14 beep! Debug Output');
|
|
18067
18123
|
for (const expression of expressions) {
|
|
18068
18124
|
const output = this.debugExpression(expression);
|
|
18069
18125
|
outputs.push(output);
|
|
@@ -18076,7 +18132,7 @@ let BeepCommand = (() => {
|
|
|
18076
18132
|
return { expressionCount: expressions.length, debugged: true, outputs };
|
|
18077
18133
|
}
|
|
18078
18134
|
debugContext(context) {
|
|
18079
|
-
console.group('
|
|
18135
|
+
console.group('\ud83d\udd14 beep! Context Debug');
|
|
18080
18136
|
console.log('me:', context.me);
|
|
18081
18137
|
console.log('it:', context.it);
|
|
18082
18138
|
console.log('you:', context.you);
|