starlight-cli 1.0.3 → 1.0.5

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/dist/index.js ADDED
@@ -0,0 +1,2556 @@
1
+ /******/ (() => { // webpackBootstrap
2
+ /******/ var __webpack_modules__ = ({
3
+
4
+ /***/ 552:
5
+ /***/ ((__unused_webpack_module, exports, __nccwpck_require__) => {
6
+
7
+ "use strict";
8
+ /*
9
+ * readlineSync
10
+ * https://github.com/anseki/readline-sync
11
+ *
12
+ * Copyright (c) 2019 anseki
13
+ * Licensed under the MIT license.
14
+ */
15
+
16
+
17
+
18
+ var
19
+ IS_WIN = process.platform === 'win32',
20
+
21
+ ALGORITHM_CIPHER = 'aes-256-cbc',
22
+ ALGORITHM_HASH = 'sha256',
23
+ DEFAULT_ERR_MSG = 'The current environment doesn\'t support interactive reading from TTY.',
24
+
25
+ fs = __nccwpck_require__(896),
26
+ TTY = process.binding('tty_wrap').TTY,
27
+ childProc = __nccwpck_require__(317),
28
+ pathUtil = __nccwpck_require__(928),
29
+
30
+ defaultOptions = {
31
+ /* eslint-disable key-spacing */
32
+ prompt: '> ',
33
+ hideEchoBack: false,
34
+ mask: '*',
35
+ limit: [],
36
+ limitMessage: 'Input another, please.$<( [)limit(])>',
37
+ defaultInput: '',
38
+ trueValue: [],
39
+ falseValue: [],
40
+ caseSensitive: false,
41
+ keepWhitespace: false,
42
+ encoding: 'utf8',
43
+ bufferSize: 1024,
44
+ print: void 0,
45
+ history: true,
46
+ cd: false,
47
+ phContent: void 0,
48
+ preCheck: void 0
49
+ /* eslint-enable key-spacing */
50
+ },
51
+
52
+ fdR = 'none',
53
+ isRawMode = false,
54
+ salt = 0,
55
+ lastInput = '',
56
+ inputHistory = [],
57
+ _DBG_useExt = false,
58
+ _DBG_checkOptions = false,
59
+ _DBG_checkMethod = false,
60
+ fdW, ttyR, extHostPath, extHostArgs, tempdir, rawInput;
61
+
62
+ function getHostArgs(options) {
63
+ // Send any text to crazy Windows shell safely.
64
+ function encodeArg(arg) {
65
+ return arg.replace(/[^\w\u0080-\uFFFF]/g, function(chr) {
66
+ return '#' + chr.charCodeAt(0) + ';';
67
+ });
68
+ }
69
+
70
+ return extHostArgs.concat((function(conf) {
71
+ var args = [];
72
+ Object.keys(conf).forEach(function(optionName) {
73
+ if (conf[optionName] === 'boolean') {
74
+ if (options[optionName]) { args.push('--' + optionName); }
75
+ } else if (conf[optionName] === 'string') {
76
+ if (options[optionName]) {
77
+ args.push('--' + optionName, encodeArg(options[optionName]));
78
+ }
79
+ }
80
+ });
81
+ return args;
82
+ })({
83
+ /* eslint-disable key-spacing */
84
+ display: 'string',
85
+ displayOnly: 'boolean',
86
+ keyIn: 'boolean',
87
+ hideEchoBack: 'boolean',
88
+ mask: 'string',
89
+ limit: 'string',
90
+ caseSensitive: 'boolean'
91
+ /* eslint-enable key-spacing */
92
+ }));
93
+ }
94
+
95
+ // piping via files (for Node.js v0.10-)
96
+ function _execFileSync(options, execOptions) {
97
+
98
+ function getTempfile(name) {
99
+ var suffix = '',
100
+ filepath, fd;
101
+ tempdir = tempdir || (__nccwpck_require__(857).tmpdir)();
102
+
103
+ while (true) {
104
+ filepath = pathUtil.join(tempdir, name + suffix);
105
+ try {
106
+ fd = fs.openSync(filepath, 'wx');
107
+ } catch (e) {
108
+ if (e.code === 'EEXIST') {
109
+ suffix++;
110
+ continue;
111
+ } else {
112
+ throw e;
113
+ }
114
+ }
115
+ fs.closeSync(fd);
116
+ break;
117
+ }
118
+ return filepath;
119
+ }
120
+
121
+ var res = {},
122
+ pathStdout = getTempfile('readline-sync.stdout'),
123
+ pathStderr = getTempfile('readline-sync.stderr'),
124
+ pathExit = getTempfile('readline-sync.exit'),
125
+ pathDone = getTempfile('readline-sync.done'),
126
+ crypto = __nccwpck_require__(982),
127
+ hostArgs, shellPath, shellArgs, exitCode, extMessage, shasum, decipher, password;
128
+
129
+ shasum = crypto.createHash(ALGORITHM_HASH);
130
+ shasum.update('' + process.pid + (salt++) + Math.random());
131
+ password = shasum.digest('hex');
132
+ decipher = crypto.createDecipher(ALGORITHM_CIPHER, password);
133
+
134
+ hostArgs = getHostArgs(options);
135
+ if (IS_WIN) {
136
+ shellPath = process.env.ComSpec || 'cmd.exe';
137
+ process.env.Q = '"'; // The quote (") that isn't escaped.
138
+ // `()` for ignore space by echo
139
+ shellArgs = ['/V:ON', '/S', '/C',
140
+ '(%Q%' + shellPath + '%Q% /V:ON /S /C %Q%' + /* ESLint bug? */ // eslint-disable-line no-path-concat
141
+ '%Q%' + extHostPath + '%Q%' +
142
+ hostArgs.map(function(arg) { return ' %Q%' + arg + '%Q%'; }).join('') +
143
+ ' & (echo !ERRORLEVEL!)>%Q%' + pathExit + '%Q%%Q%) 2>%Q%' + pathStderr + '%Q%' +
144
+ ' |%Q%' + process.execPath + '%Q% %Q%' + __dirname + '\\encrypt.js%Q%' +
145
+ ' %Q%' + ALGORITHM_CIPHER + '%Q% %Q%' + password + '%Q%' +
146
+ ' >%Q%' + pathStdout + '%Q%' +
147
+ ' & (echo 1)>%Q%' + pathDone + '%Q%'];
148
+ } else {
149
+ shellPath = '/bin/sh';
150
+ shellArgs = ['-c',
151
+ // Use `()`, not `{}` for `-c` (text param)
152
+ '("' + extHostPath + '"' + /* ESLint bug? */ // eslint-disable-line no-path-concat
153
+ hostArgs.map(function(arg) { return " '" + arg.replace(/'/g, "'\\''") + "'"; }).join('') +
154
+ '; echo $?>"' + pathExit + '") 2>"' + pathStderr + '"' +
155
+ ' |"' + process.execPath + '" "' + __dirname + '/encrypt.js"' +
156
+ ' "' + ALGORITHM_CIPHER + '" "' + password + '"' +
157
+ ' >"' + pathStdout + '"' +
158
+ '; echo 1 >"' + pathDone + '"'];
159
+ }
160
+ if (_DBG_checkMethod) { _DBG_checkMethod('_execFileSync', hostArgs); }
161
+ try {
162
+ childProc.spawn(shellPath, shellArgs, execOptions);
163
+ } catch (e) {
164
+ res.error = new Error(e.message);
165
+ res.error.method = '_execFileSync - spawn';
166
+ res.error.program = shellPath;
167
+ res.error.args = shellArgs;
168
+ }
169
+
170
+ while (fs.readFileSync(pathDone, {encoding: options.encoding}).trim() !== '1') {} // eslint-disable-line no-empty
171
+ if ((exitCode =
172
+ fs.readFileSync(pathExit, {encoding: options.encoding}).trim()) === '0') {
173
+ res.input =
174
+ decipher.update(fs.readFileSync(pathStdout, {encoding: 'binary'}),
175
+ 'hex', options.encoding) +
176
+ decipher.final(options.encoding);
177
+ } else {
178
+ extMessage = fs.readFileSync(pathStderr, {encoding: options.encoding}).trim();
179
+ res.error = new Error(DEFAULT_ERR_MSG + (extMessage ? '\n' + extMessage : ''));
180
+ res.error.method = '_execFileSync';
181
+ res.error.program = shellPath;
182
+ res.error.args = shellArgs;
183
+ res.error.extMessage = extMessage;
184
+ res.error.exitCode = +exitCode;
185
+ }
186
+
187
+ fs.unlinkSync(pathStdout);
188
+ fs.unlinkSync(pathStderr);
189
+ fs.unlinkSync(pathExit);
190
+ fs.unlinkSync(pathDone);
191
+
192
+ return res;
193
+ }
194
+
195
+ function readlineExt(options) {
196
+ var res = {},
197
+ execOptions = {env: process.env, encoding: options.encoding},
198
+ hostArgs, extMessage;
199
+
200
+ if (!extHostPath) {
201
+ if (IS_WIN) {
202
+ if (process.env.PSModulePath) { // Windows PowerShell
203
+ extHostPath = 'powershell.exe';
204
+ extHostArgs = ['-ExecutionPolicy', 'Bypass',
205
+ '-File', __nccwpck_require__.ab + "read.ps1"]; // eslint-disable-line no-path-concat
206
+ } else { // Windows Script Host
207
+ extHostPath = 'cscript.exe';
208
+ extHostArgs = ['//nologo', __nccwpck_require__.ab + "read.cs.js"]; // eslint-disable-line no-path-concat
209
+ }
210
+ } else {
211
+ extHostPath = '/bin/sh';
212
+ extHostArgs = [__nccwpck_require__.ab + "read.sh"]; // eslint-disable-line no-path-concat
213
+ }
214
+ }
215
+ if (IS_WIN && !process.env.PSModulePath) { // Windows Script Host
216
+ // ScriptPW (Win XP and Server2003) needs TTY stream as STDIN.
217
+ // In this case, If STDIN isn't TTY, an error is thrown.
218
+ execOptions.stdio = [process.stdin];
219
+ }
220
+
221
+ if (childProc.execFileSync) {
222
+ hostArgs = getHostArgs(options);
223
+ if (_DBG_checkMethod) { _DBG_checkMethod('execFileSync', hostArgs); }
224
+ try {
225
+ res.input = childProc.execFileSync(extHostPath, hostArgs, execOptions);
226
+ } catch (e) { // non-zero exit code
227
+ extMessage = e.stderr ? (e.stderr + '').trim() : '';
228
+ res.error = new Error(DEFAULT_ERR_MSG + (extMessage ? '\n' + extMessage : ''));
229
+ res.error.method = 'execFileSync';
230
+ res.error.program = extHostPath;
231
+ res.error.args = hostArgs;
232
+ res.error.extMessage = extMessage;
233
+ res.error.exitCode = e.status;
234
+ res.error.code = e.code;
235
+ res.error.signal = e.signal;
236
+ }
237
+ } else {
238
+ res = _execFileSync(options, execOptions);
239
+ }
240
+ if (!res.error) {
241
+ res.input = res.input.replace(/^\s*'|'\s*$/g, '');
242
+ options.display = '';
243
+ }
244
+
245
+ return res;
246
+ }
247
+
248
+ /*
249
+ display: string
250
+ displayOnly: boolean
251
+ keyIn: boolean
252
+ hideEchoBack: boolean
253
+ mask: string
254
+ limit: string (pattern)
255
+ caseSensitive: boolean
256
+ keepWhitespace: boolean
257
+ encoding, bufferSize, print
258
+ */
259
+ function _readlineSync(options) {
260
+ var input = '',
261
+ displaySave = options.display,
262
+ silent = !options.display && options.keyIn && options.hideEchoBack && !options.mask;
263
+
264
+ function tryExt() {
265
+ var res = readlineExt(options);
266
+ if (res.error) { throw res.error; }
267
+ return res.input;
268
+ }
269
+
270
+ if (_DBG_checkOptions) { _DBG_checkOptions(options); }
271
+
272
+ (function() { // open TTY
273
+ var fsB, constants, verNum;
274
+
275
+ function getFsB() {
276
+ if (!fsB) {
277
+ fsB = process.binding('fs'); // For raw device path
278
+ constants = process.binding('constants');
279
+ // for v6.3.0+
280
+ constants = constants && constants.fs && typeof constants.fs.O_RDWR === 'number'
281
+ ? constants.fs : constants;
282
+ }
283
+ return fsB;
284
+ }
285
+
286
+ if (typeof fdR !== 'string') { return; }
287
+ fdR = null;
288
+
289
+ if (IS_WIN) {
290
+ // iojs-v2.3.2+ input stream can't read first line. (#18)
291
+ // ** Don't get process.stdin before check! **
292
+ // Fixed v5.1.0
293
+ // Fixed v4.2.4
294
+ // It regressed again in v5.6.0, it is fixed in v6.2.0.
295
+ verNum = (function(ver) { // getVerNum
296
+ var nums = ver.replace(/^\D+/, '').split('.');
297
+ var verNum = 0;
298
+ if ((nums[0] = +nums[0])) { verNum += nums[0] * 10000; }
299
+ if ((nums[1] = +nums[1])) { verNum += nums[1] * 100; }
300
+ if ((nums[2] = +nums[2])) { verNum += nums[2]; }
301
+ return verNum;
302
+ })(process.version);
303
+ if (!(verNum >= 20302 && verNum < 40204 || verNum >= 50000 && verNum < 50100 || verNum >= 50600 && verNum < 60200) &&
304
+ process.stdin.isTTY) {
305
+ process.stdin.pause();
306
+ fdR = process.stdin.fd;
307
+ ttyR = process.stdin._handle;
308
+ } else {
309
+ try {
310
+ // The stream by fs.openSync('\\\\.\\CON', 'r') can't switch to raw mode.
311
+ // 'CONIN$' might fail on XP, 2000, 7 (x86).
312
+ fdR = getFsB().open('CONIN$', constants.O_RDWR, parseInt('0666', 8));
313
+ ttyR = new TTY(fdR, true);
314
+ } catch (e) { /* ignore */ }
315
+ }
316
+
317
+ if (process.stdout.isTTY) {
318
+ fdW = process.stdout.fd;
319
+ } else {
320
+ try {
321
+ fdW = fs.openSync('\\\\.\\CON', 'w');
322
+ } catch (e) { /* ignore */ }
323
+ if (typeof fdW !== 'number') { // Retry
324
+ try {
325
+ fdW = getFsB().open('CONOUT$', constants.O_RDWR, parseInt('0666', 8));
326
+ } catch (e) { /* ignore */ }
327
+ }
328
+ }
329
+
330
+ } else {
331
+ if (process.stdin.isTTY) {
332
+ process.stdin.pause();
333
+ try {
334
+ fdR = fs.openSync('/dev/tty', 'r'); // device file, not process.stdin
335
+ ttyR = process.stdin._handle;
336
+ } catch (e) { /* ignore */ }
337
+ } else {
338
+ // Node.js v0.12 read() fails.
339
+ try {
340
+ fdR = fs.openSync('/dev/tty', 'r');
341
+ ttyR = new TTY(fdR, false);
342
+ } catch (e) { /* ignore */ }
343
+ }
344
+
345
+ if (process.stdout.isTTY) {
346
+ fdW = process.stdout.fd;
347
+ } else {
348
+ try {
349
+ fdW = fs.openSync('/dev/tty', 'w');
350
+ } catch (e) { /* ignore */ }
351
+ }
352
+ }
353
+ })();
354
+
355
+ (function() { // try read
356
+ var isCooked = !options.hideEchoBack && !options.keyIn,
357
+ atEol, limit, buffer, reqSize, readSize, chunk, line;
358
+ rawInput = '';
359
+
360
+ // Node.js v0.10- returns an error if same mode is set.
361
+ function setRawMode(mode) {
362
+ if (mode === isRawMode) { return true; }
363
+ if (ttyR.setRawMode(mode) !== 0) { return false; }
364
+ isRawMode = mode;
365
+ return true;
366
+ }
367
+
368
+ if (_DBG_useExt || !ttyR ||
369
+ typeof fdW !== 'number' && (options.display || !isCooked)) {
370
+ input = tryExt();
371
+ return;
372
+ }
373
+
374
+ if (options.display) {
375
+ fs.writeSync(fdW, options.display);
376
+ options.display = '';
377
+ }
378
+ if (options.displayOnly) { return; }
379
+
380
+ if (!setRawMode(!isCooked)) {
381
+ input = tryExt();
382
+ return;
383
+ }
384
+
385
+ reqSize = options.keyIn ? 1 : options.bufferSize;
386
+ // Check `allocUnsafe` to make sure of the new API.
387
+ buffer = Buffer.allocUnsafe && Buffer.alloc ? Buffer.alloc(reqSize) : new Buffer(reqSize);
388
+
389
+ if (options.keyIn && options.limit) {
390
+ limit = new RegExp('[^' + options.limit + ']',
391
+ 'g' + (options.caseSensitive ? '' : 'i'));
392
+ }
393
+
394
+ while (true) {
395
+ readSize = 0;
396
+ try {
397
+ readSize = fs.readSync(fdR, buffer, 0, reqSize);
398
+ } catch (e) {
399
+ if (e.code !== 'EOF') {
400
+ setRawMode(false);
401
+ input += tryExt();
402
+ return;
403
+ }
404
+ }
405
+ if (readSize > 0) {
406
+ chunk = buffer.toString(options.encoding, 0, readSize);
407
+ rawInput += chunk;
408
+ } else {
409
+ chunk = '\n';
410
+ rawInput += String.fromCharCode(0);
411
+ }
412
+
413
+ if (chunk && typeof (line = (chunk.match(/^(.*?)[\r\n]/) || [])[1]) === 'string') {
414
+ chunk = line;
415
+ atEol = true;
416
+ }
417
+
418
+ // other ctrl-chars
419
+ // eslint-disable-next-line no-control-regex
420
+ if (chunk) { chunk = chunk.replace(/[\x00-\x08\x0b\x0c\x0e-\x1f\x7f]/g, ''); }
421
+ if (chunk && limit) { chunk = chunk.replace(limit, ''); }
422
+
423
+ if (chunk) {
424
+ if (!isCooked) {
425
+ if (!options.hideEchoBack) {
426
+ fs.writeSync(fdW, chunk);
427
+ } else if (options.mask) {
428
+ fs.writeSync(fdW, (new Array(chunk.length + 1)).join(options.mask));
429
+ }
430
+ }
431
+ input += chunk;
432
+ }
433
+
434
+ if (!options.keyIn && atEol ||
435
+ options.keyIn && input.length >= reqSize) { break; }
436
+ }
437
+
438
+ if (!isCooked && !silent) { fs.writeSync(fdW, '\n'); }
439
+ setRawMode(false);
440
+ })();
441
+
442
+ if (options.print && !silent) {
443
+ options.print(
444
+ displaySave + (
445
+ options.displayOnly ? '' : (
446
+ options.hideEchoBack ? (new Array(input.length + 1)).join(options.mask) : input
447
+ ) + '\n' // must at least write '\n'
448
+ ),
449
+ options.encoding);
450
+ }
451
+
452
+ return options.displayOnly ? '' :
453
+ (lastInput = options.keepWhitespace || options.keyIn ? input : input.trim());
454
+ }
455
+
456
+ function flattenArray(array, validator) {
457
+ var flatArray = [];
458
+ function _flattenArray(array) {
459
+ if (array == null) { return; }
460
+ if (Array.isArray(array)) {
461
+ array.forEach(_flattenArray);
462
+ } else if (!validator || validator(array)) {
463
+ flatArray.push(array);
464
+ }
465
+ }
466
+ _flattenArray(array);
467
+ return flatArray;
468
+ }
469
+
470
+ function escapePattern(pattern) {
471
+ return pattern.replace(/[\x00-\x7f]/g, // eslint-disable-line no-control-regex
472
+ function(s) { return '\\x' + ('00' + s.charCodeAt().toString(16)).substr(-2); });
473
+ }
474
+
475
+ // margeOptions(options1, options2 ... )
476
+ // margeOptions(true, options1, options2 ... )
477
+ // arg1=true : Start from defaultOptions and pick elements of that.
478
+ function margeOptions() {
479
+ var optionsList = Array.prototype.slice.call(arguments),
480
+ optionNames, fromDefault;
481
+
482
+ if (optionsList.length && typeof optionsList[0] === 'boolean') {
483
+ fromDefault = optionsList.shift();
484
+ if (fromDefault) {
485
+ optionNames = Object.keys(defaultOptions);
486
+ optionsList.unshift(defaultOptions);
487
+ }
488
+ }
489
+
490
+ return optionsList.reduce(function(options, optionsPart) {
491
+ if (optionsPart == null) { return options; }
492
+
493
+ // ======== DEPRECATED ========
494
+ if (optionsPart.hasOwnProperty('noEchoBack') &&
495
+ !optionsPart.hasOwnProperty('hideEchoBack')) {
496
+ optionsPart.hideEchoBack = optionsPart.noEchoBack;
497
+ delete optionsPart.noEchoBack;
498
+ }
499
+ if (optionsPart.hasOwnProperty('noTrim') &&
500
+ !optionsPart.hasOwnProperty('keepWhitespace')) {
501
+ optionsPart.keepWhitespace = optionsPart.noTrim;
502
+ delete optionsPart.noTrim;
503
+ }
504
+ // ======== /DEPRECATED ========
505
+
506
+ if (!fromDefault) { optionNames = Object.keys(optionsPart); }
507
+ optionNames.forEach(function(optionName) {
508
+ var value;
509
+ if (!optionsPart.hasOwnProperty(optionName)) { return; }
510
+ value = optionsPart[optionName];
511
+ /* eslint-disable no-multi-spaces */
512
+ switch (optionName) {
513
+ // _readlineSync <- * * -> defaultOptions
514
+ // ================ string
515
+ case 'mask': // * *
516
+ case 'limitMessage': // *
517
+ case 'defaultInput': // *
518
+ case 'encoding': // * *
519
+ value = value != null ? value + '' : '';
520
+ if (value && optionName !== 'limitMessage') { value = value.replace(/[\r\n]/g, ''); }
521
+ options[optionName] = value;
522
+ break;
523
+ // ================ number(int)
524
+ case 'bufferSize': // * *
525
+ if (!isNaN(value = parseInt(value, 10)) && typeof value === 'number') {
526
+ options[optionName] = value; // limited updating (number is needed)
527
+ }
528
+ break;
529
+ // ================ boolean
530
+ case 'displayOnly': // *
531
+ case 'keyIn': // *
532
+ case 'hideEchoBack': // * *
533
+ case 'caseSensitive': // * *
534
+ case 'keepWhitespace': // * *
535
+ case 'history': // *
536
+ case 'cd': // *
537
+ options[optionName] = !!value;
538
+ break;
539
+ // ================ array
540
+ case 'limit': // * * to string for readlineExt
541
+ case 'trueValue': // *
542
+ case 'falseValue': // *
543
+ options[optionName] = flattenArray(value, function(value) {
544
+ var type = typeof value;
545
+ return type === 'string' || type === 'number' ||
546
+ type === 'function' || value instanceof RegExp;
547
+ }).map(function(value) {
548
+ return typeof value === 'string' ? value.replace(/[\r\n]/g, '') : value;
549
+ });
550
+ break;
551
+ // ================ function
552
+ case 'print': // * *
553
+ case 'phContent': // *
554
+ case 'preCheck': // *
555
+ options[optionName] = typeof value === 'function' ? value : void 0;
556
+ break;
557
+ // ================ other
558
+ case 'prompt': // *
559
+ case 'display': // *
560
+ options[optionName] = value != null ? value : '';
561
+ break;
562
+ // no default
563
+ }
564
+ /* eslint-enable no-multi-spaces */
565
+ });
566
+ return options;
567
+ }, {});
568
+ }
569
+
570
+ function isMatched(res, comps, caseSensitive) {
571
+ return comps.some(function(comp) {
572
+ var type = typeof comp;
573
+ return type === 'string'
574
+ ? (caseSensitive ? res === comp : res.toLowerCase() === comp.toLowerCase()) :
575
+ type === 'number' ? parseFloat(res) === comp :
576
+ type === 'function' ? comp(res) :
577
+ comp instanceof RegExp ? comp.test(res) : false;
578
+ });
579
+ }
580
+
581
+ function replaceHomePath(path, expand) {
582
+ var homePath = pathUtil.normalize(
583
+ IS_WIN ? (process.env.HOMEDRIVE || '') + (process.env.HOMEPATH || '') :
584
+ process.env.HOME || '').replace(/[/\\]+$/, '');
585
+ path = pathUtil.normalize(path);
586
+ return expand ? path.replace(/^~(?=\/|\\|$)/, homePath) :
587
+ path.replace(new RegExp('^' + escapePattern(homePath) +
588
+ '(?=\\/|\\\\|$)', IS_WIN ? 'i' : ''), '~');
589
+ }
590
+
591
+ function replacePlaceholder(text, generator) {
592
+ var PTN_INNER = '(?:\\(([\\s\\S]*?)\\))?(\\w+|.-.)(?:\\(([\\s\\S]*?)\\))?',
593
+ rePlaceholder = new RegExp('(\\$)?(\\$<' + PTN_INNER + '>)', 'g'),
594
+ rePlaceholderCompat = new RegExp('(\\$)?(\\$\\{' + PTN_INNER + '\\})', 'g');
595
+
596
+ function getPlaceholderText(s, escape, placeholder, pre, param, post) {
597
+ var text;
598
+ return escape || typeof (text = generator(param)) !== 'string' ? placeholder :
599
+ text ? (pre || '') + text + (post || '') : '';
600
+ }
601
+
602
+ return text.replace(rePlaceholder, getPlaceholderText)
603
+ .replace(rePlaceholderCompat, getPlaceholderText);
604
+ }
605
+
606
+ function array2charlist(array, caseSensitive, collectSymbols) {
607
+ var group = [],
608
+ groupClass = -1,
609
+ charCode = 0,
610
+ symbols = '',
611
+ values, suppressed;
612
+ function addGroup(groups, group) {
613
+ if (group.length > 3) { // ellipsis
614
+ groups.push(group[0] + '...' + group[group.length - 1]);
615
+ suppressed = true;
616
+ } else if (group.length) {
617
+ groups = groups.concat(group);
618
+ }
619
+ return groups;
620
+ }
621
+
622
+ values = array.reduce(function(chars, value) {
623
+ return chars.concat((value + '').split(''));
624
+ }, []).reduce(function(groups, curChar) {
625
+ var curGroupClass, curCharCode;
626
+ if (!caseSensitive) { curChar = curChar.toLowerCase(); }
627
+ curGroupClass = /^\d$/.test(curChar) ? 1 :
628
+ /^[A-Z]$/.test(curChar) ? 2 : /^[a-z]$/.test(curChar) ? 3 : 0;
629
+ if (collectSymbols && curGroupClass === 0) {
630
+ symbols += curChar;
631
+ } else {
632
+ curCharCode = curChar.charCodeAt(0);
633
+ if (curGroupClass && curGroupClass === groupClass &&
634
+ curCharCode === charCode + 1) {
635
+ group.push(curChar);
636
+ } else {
637
+ groups = addGroup(groups, group);
638
+ group = [curChar];
639
+ groupClass = curGroupClass;
640
+ }
641
+ charCode = curCharCode;
642
+ }
643
+ return groups;
644
+ }, []);
645
+ values = addGroup(values, group); // last group
646
+ if (symbols) { values.push(symbols); suppressed = true; }
647
+ return {values: values, suppressed: suppressed};
648
+ }
649
+
650
+ function joinChunks(chunks, suppressed) {
651
+ return chunks.join(chunks.length > 2 ? ', ' : suppressed ? ' / ' : '/');
652
+ }
653
+
654
+ function getPhContent(param, options) {
655
+ var resCharlist = {},
656
+ text, values, arg;
657
+ if (options.phContent) {
658
+ text = options.phContent(param, options);
659
+ }
660
+ if (typeof text !== 'string') {
661
+ switch (param) {
662
+ case 'hideEchoBack':
663
+ case 'mask':
664
+ case 'defaultInput':
665
+ case 'caseSensitive':
666
+ case 'keepWhitespace':
667
+ case 'encoding':
668
+ case 'bufferSize':
669
+ case 'history':
670
+ case 'cd':
671
+ text = !options.hasOwnProperty(param) ? '' :
672
+ typeof options[param] === 'boolean' ? (options[param] ? 'on' : 'off') :
673
+ options[param] + '';
674
+ break;
675
+ // case 'prompt':
676
+ // case 'query':
677
+ // case 'display':
678
+ // text = options.hasOwnProperty('displaySrc') ? options.displaySrc + '' : '';
679
+ // break;
680
+ case 'limit':
681
+ case 'trueValue':
682
+ case 'falseValue':
683
+ values = options[options.hasOwnProperty(param + 'Src') ? param + 'Src' : param];
684
+ if (options.keyIn) { // suppress
685
+ resCharlist = array2charlist(values, options.caseSensitive);
686
+ values = resCharlist.values;
687
+ } else {
688
+ values = values.filter(function(value) {
689
+ var type = typeof value;
690
+ return type === 'string' || type === 'number';
691
+ });
692
+ }
693
+ text = joinChunks(values, resCharlist.suppressed);
694
+ break;
695
+ case 'limitCount':
696
+ case 'limitCountNotZero':
697
+ text = options[options.hasOwnProperty('limitSrc') ? 'limitSrc' : 'limit'].length;
698
+ text = text || param !== 'limitCountNotZero' ? text + '' : '';
699
+ break;
700
+ case 'lastInput':
701
+ text = lastInput;
702
+ break;
703
+ case 'cwd':
704
+ case 'CWD':
705
+ case 'cwdHome':
706
+ text = process.cwd();
707
+ if (param === 'CWD') {
708
+ text = pathUtil.basename(text);
709
+ } else if (param === 'cwdHome') {
710
+ text = replaceHomePath(text);
711
+ }
712
+ break;
713
+ case 'date':
714
+ case 'time':
715
+ case 'localeDate':
716
+ case 'localeTime':
717
+ text = (new Date())['to' +
718
+ param.replace(/^./, function(str) { return str.toUpperCase(); }) +
719
+ 'String']();
720
+ break;
721
+ default: // with arg
722
+ if (typeof (arg = (param.match(/^history_m(\d+)$/) || [])[1]) === 'string') {
723
+ text = inputHistory[inputHistory.length - arg] || '';
724
+ }
725
+ }
726
+ }
727
+ return text;
728
+ }
729
+
730
+ function getPhCharlist(param) {
731
+ var matches = /^(.)-(.)$/.exec(param),
732
+ text = '',
733
+ from, to, code, step;
734
+ if (!matches) { return null; }
735
+ from = matches[1].charCodeAt(0);
736
+ to = matches[2].charCodeAt(0);
737
+ step = from < to ? 1 : -1;
738
+ for (code = from; code !== to + step; code += step) { text += String.fromCharCode(code); }
739
+ return text;
740
+ }
741
+
742
+ // cmd "arg" " a r g " "" 'a"r"g' "a""rg" "arg
743
+ function parseCl(cl) {
744
+ var reToken = new RegExp(/(\s*)(?:("|')(.*?)(?:\2|$)|(\S+))/g),
745
+ taken = '',
746
+ args = [],
747
+ matches, part;
748
+ cl = cl.trim();
749
+ while ((matches = reToken.exec(cl))) {
750
+ part = matches[3] || matches[4] || '';
751
+ if (matches[1]) {
752
+ args.push(taken);
753
+ taken = '';
754
+ }
755
+ taken += part;
756
+ }
757
+ if (taken) { args.push(taken); }
758
+ return args;
759
+ }
760
+
761
+ function toBool(res, options) {
762
+ return (
763
+ (options.trueValue.length &&
764
+ isMatched(res, options.trueValue, options.caseSensitive)) ? true :
765
+ (options.falseValue.length &&
766
+ isMatched(res, options.falseValue, options.caseSensitive)) ? false : res);
767
+ }
768
+
769
+ function getValidLine(options) {
770
+ var res, forceNext, limitMessage,
771
+ matches, histInput, args, resCheck;
772
+
773
+ function _getPhContent(param) { return getPhContent(param, options); }
774
+ function addDisplay(text) { options.display += (/[^\r\n]$/.test(options.display) ? '\n' : '') + text; }
775
+
776
+ options.limitSrc = options.limit;
777
+ options.displaySrc = options.display;
778
+ options.limit = ''; // for readlineExt
779
+ options.display = replacePlaceholder(options.display + '', _getPhContent);
780
+
781
+ while (true) {
782
+ res = _readlineSync(options);
783
+ forceNext = false;
784
+ limitMessage = '';
785
+
786
+ if (options.defaultInput && !res) { res = options.defaultInput; }
787
+
788
+ if (options.history) {
789
+ if ((matches = /^\s*!(?:!|-1)(:p)?\s*$/.exec(res))) { // `!!` `!-1` +`:p`
790
+ histInput = inputHistory[0] || '';
791
+ if (matches[1]) { // only display
792
+ forceNext = true;
793
+ } else { // replace input
794
+ res = histInput;
795
+ }
796
+ // Show it even if it is empty (NL only).
797
+ addDisplay(histInput + '\n');
798
+ if (!forceNext) { // Loop may break
799
+ options.displayOnly = true;
800
+ _readlineSync(options);
801
+ options.displayOnly = false;
802
+ }
803
+ } else if (res && res !== inputHistory[inputHistory.length - 1]) {
804
+ inputHistory = [res];
805
+ }
806
+ }
807
+
808
+ if (!forceNext && options.cd && res) {
809
+ args = parseCl(res);
810
+ switch (args[0].toLowerCase()) {
811
+ case 'cd':
812
+ if (args[1]) {
813
+ try {
814
+ process.chdir(replaceHomePath(args[1], true));
815
+ } catch (e) {
816
+ addDisplay(e + '');
817
+ }
818
+ }
819
+ forceNext = true;
820
+ break;
821
+ case 'pwd':
822
+ addDisplay(process.cwd());
823
+ forceNext = true;
824
+ break;
825
+ // no default
826
+ }
827
+ }
828
+
829
+ if (!forceNext && options.preCheck) {
830
+ resCheck = options.preCheck(res, options);
831
+ res = resCheck.res;
832
+ if (resCheck.forceNext) { forceNext = true; } // Don't switch to false.
833
+ }
834
+
835
+ if (!forceNext) {
836
+ if (!options.limitSrc.length ||
837
+ isMatched(res, options.limitSrc, options.caseSensitive)) { break; }
838
+ if (options.limitMessage) {
839
+ limitMessage = replacePlaceholder(options.limitMessage, _getPhContent);
840
+ }
841
+ }
842
+
843
+ addDisplay((limitMessage ? limitMessage + '\n' : '') +
844
+ replacePlaceholder(options.displaySrc + '', _getPhContent));
845
+ }
846
+ return toBool(res, options);
847
+ }
848
+
849
+ // for dev
850
+ exports._DBG_set_useExt = function(val) { _DBG_useExt = val; };
851
+ exports._DBG_set_checkOptions = function(val) { _DBG_checkOptions = val; };
852
+ exports._DBG_set_checkMethod = function(val) { _DBG_checkMethod = val; };
853
+ exports._DBG_clearHistory = function() { lastInput = ''; inputHistory = []; };
854
+
855
+ // ------------------------------------
856
+
857
+ exports.setDefaultOptions = function(options) {
858
+ defaultOptions = margeOptions(true, options);
859
+ return margeOptions(true); // copy
860
+ };
861
+
862
+ exports.question = function(query, options) {
863
+ /* eslint-disable key-spacing */
864
+ return getValidLine(margeOptions(margeOptions(true, options), {
865
+ display: query
866
+ }));
867
+ /* eslint-enable key-spacing */
868
+ };
869
+
870
+ exports.prompt = function(options) {
871
+ var readOptions = margeOptions(true, options);
872
+ readOptions.display = readOptions.prompt;
873
+ return getValidLine(readOptions);
874
+ };
875
+
876
+ exports.keyIn = function(query, options) {
877
+ /* eslint-disable key-spacing */
878
+ var readOptions = margeOptions(margeOptions(true, options), {
879
+ display: query,
880
+ keyIn: true,
881
+ keepWhitespace: true
882
+ });
883
+ /* eslint-enable key-spacing */
884
+
885
+ // char list
886
+ readOptions.limitSrc = readOptions.limit.filter(function(value) {
887
+ var type = typeof value;
888
+ return type === 'string' || type === 'number';
889
+ }).map(function(text) {
890
+ return replacePlaceholder(text + '', getPhCharlist);
891
+ });
892
+ // pattern
893
+ readOptions.limit = escapePattern(readOptions.limitSrc.join(''));
894
+
895
+ ['trueValue', 'falseValue'].forEach(function(optionName) {
896
+ readOptions[optionName] = readOptions[optionName].reduce(function(comps, comp) {
897
+ var type = typeof comp;
898
+ if (type === 'string' || type === 'number') {
899
+ comps = comps.concat((comp + '').split(''));
900
+ } else { comps.push(comp); }
901
+ return comps;
902
+ }, []);
903
+ });
904
+
905
+ readOptions.display = replacePlaceholder(readOptions.display + '',
906
+ function(param) { return getPhContent(param, readOptions); });
907
+
908
+ return toBool(_readlineSync(readOptions), readOptions);
909
+ };
910
+
911
+ // ------------------------------------
912
+
913
+ exports.questionEMail = function(query, options) {
914
+ if (query == null) { query = 'Input e-mail address: '; }
915
+ /* eslint-disable key-spacing */
916
+ return exports.question(query, margeOptions({
917
+ // -------- default
918
+ hideEchoBack: false,
919
+ // http://www.w3.org/TR/html5/forms.html#valid-e-mail-address
920
+ limit: /^[a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*$/,
921
+ limitMessage: 'Input valid e-mail address, please.',
922
+ trueValue: null,
923
+ falseValue: null
924
+ }, options, {
925
+ // -------- forced
926
+ keepWhitespace: false,
927
+ cd: false
928
+ }));
929
+ /* eslint-enable key-spacing */
930
+ };
931
+
932
+ exports.questionNewPassword = function(query, options) {
933
+ /* eslint-disable key-spacing */
934
+ var resCharlist, min, max,
935
+ readOptions = margeOptions({
936
+ // -------- default
937
+ hideEchoBack: true,
938
+ mask: '*',
939
+ limitMessage: 'It can include: $<charlist>\n' +
940
+ 'And the length must be: $<length>',
941
+ trueValue: null,
942
+ falseValue: null,
943
+ caseSensitive: true
944
+ }, options, {
945
+ // -------- forced
946
+ history: false,
947
+ cd: false,
948
+ // limit (by charlist etc.),
949
+ phContent: function(param) {
950
+ return param === 'charlist' ? resCharlist.text :
951
+ param === 'length' ? min + '...' + max : null;
952
+ }
953
+ }),
954
+ // added: charlist, min, max, confirmMessage, unmatchMessage
955
+ charlist, confirmMessage, unmatchMessage,
956
+ limit, limitMessage, res1, res2;
957
+ /* eslint-enable key-spacing */
958
+ options = options || {};
959
+
960
+ charlist = replacePlaceholder(
961
+ options.charlist ? options.charlist + '' : '$<!-~>', getPhCharlist);
962
+ if (isNaN(min = parseInt(options.min, 10)) || typeof min !== 'number') { min = 12; }
963
+ if (isNaN(max = parseInt(options.max, 10)) || typeof max !== 'number') { max = 24; }
964
+ limit = new RegExp('^[' + escapePattern(charlist) +
965
+ ']{' + min + ',' + max + '}$');
966
+ resCharlist = array2charlist([charlist], readOptions.caseSensitive, true);
967
+ resCharlist.text = joinChunks(resCharlist.values, resCharlist.suppressed);
968
+
969
+ confirmMessage = options.confirmMessage != null ? options.confirmMessage :
970
+ 'Reinput a same one to confirm it: ';
971
+ unmatchMessage = options.unmatchMessage != null ? options.unmatchMessage :
972
+ 'It differs from first one.' +
973
+ ' Hit only the Enter key if you want to retry from first one.';
974
+
975
+ if (query == null) { query = 'Input new password: '; }
976
+
977
+ limitMessage = readOptions.limitMessage;
978
+ while (!res2) {
979
+ readOptions.limit = limit;
980
+ readOptions.limitMessage = limitMessage;
981
+ res1 = exports.question(query, readOptions);
982
+
983
+ readOptions.limit = [res1, ''];
984
+ readOptions.limitMessage = unmatchMessage;
985
+ res2 = exports.question(confirmMessage, readOptions);
986
+ }
987
+
988
+ return res1;
989
+ };
990
+
991
+ function _questionNum(query, options, parser) {
992
+ var validValue;
993
+ function getValidValue(value) {
994
+ validValue = parser(value);
995
+ return !isNaN(validValue) && typeof validValue === 'number';
996
+ }
997
+ /* eslint-disable key-spacing */
998
+ exports.question(query, margeOptions({
999
+ // -------- default
1000
+ limitMessage: 'Input valid number, please.'
1001
+ }, options, {
1002
+ // -------- forced
1003
+ limit: getValidValue,
1004
+ cd: false
1005
+ // trueValue, falseValue, caseSensitive, keepWhitespace don't work.
1006
+ }));
1007
+ /* eslint-enable key-spacing */
1008
+ return validValue;
1009
+ }
1010
+ exports.questionInt = function(query, options) {
1011
+ return _questionNum(query, options, function(value) { return parseInt(value, 10); });
1012
+ };
1013
+ exports.questionFloat = function(query, options) {
1014
+ return _questionNum(query, options, parseFloat);
1015
+ };
1016
+
1017
+ exports.questionPath = function(query, options) {
1018
+ /* eslint-disable key-spacing */
1019
+ var error = '',
1020
+ validPath, // before readOptions
1021
+ readOptions = margeOptions({
1022
+ // -------- default
1023
+ hideEchoBack: false,
1024
+ limitMessage: '$<error(\n)>Input valid path, please.' +
1025
+ '$<( Min:)min>$<( Max:)max>',
1026
+ history: true,
1027
+ cd: true
1028
+ }, options, {
1029
+ // -------- forced
1030
+ keepWhitespace: false,
1031
+ limit: function(value) {
1032
+ var exists, stat, res;
1033
+ value = replaceHomePath(value, true);
1034
+ error = ''; // for validate
1035
+ // mkdir -p
1036
+ function mkdirParents(dirPath) {
1037
+ dirPath.split(/\/|\\/).reduce(function(parents, dir) {
1038
+ var path = pathUtil.resolve((parents += dir + pathUtil.sep));
1039
+ if (!fs.existsSync(path)) {
1040
+ fs.mkdirSync(path);
1041
+ } else if (!fs.statSync(path).isDirectory()) {
1042
+ throw new Error('Non directory already exists: ' + path);
1043
+ }
1044
+ return parents;
1045
+ }, '');
1046
+ }
1047
+
1048
+ try {
1049
+ exists = fs.existsSync(value);
1050
+ validPath = exists ? fs.realpathSync(value) : pathUtil.resolve(value);
1051
+ // options.exists default: true, not-bool: no-check
1052
+ if (!options.hasOwnProperty('exists') && !exists ||
1053
+ typeof options.exists === 'boolean' && options.exists !== exists) {
1054
+ error = (exists ? 'Already exists' : 'No such file or directory') +
1055
+ ': ' + validPath;
1056
+ return false;
1057
+ }
1058
+ if (!exists && options.create) {
1059
+ if (options.isDirectory) {
1060
+ mkdirParents(validPath);
1061
+ } else {
1062
+ mkdirParents(pathUtil.dirname(validPath));
1063
+ fs.closeSync(fs.openSync(validPath, 'w')); // touch
1064
+ }
1065
+ validPath = fs.realpathSync(validPath);
1066
+ }
1067
+ if (exists && (options.min || options.max ||
1068
+ options.isFile || options.isDirectory)) {
1069
+ stat = fs.statSync(validPath);
1070
+ // type check first (directory has zero size)
1071
+ if (options.isFile && !stat.isFile()) {
1072
+ error = 'Not file: ' + validPath;
1073
+ return false;
1074
+ } else if (options.isDirectory && !stat.isDirectory()) {
1075
+ error = 'Not directory: ' + validPath;
1076
+ return false;
1077
+ } else if (options.min && stat.size < +options.min ||
1078
+ options.max && stat.size > +options.max) {
1079
+ error = 'Size ' + stat.size + ' is out of range: ' + validPath;
1080
+ return false;
1081
+ }
1082
+ }
1083
+ if (typeof options.validate === 'function' &&
1084
+ (res = options.validate(validPath)) !== true) {
1085
+ if (typeof res === 'string') { error = res; }
1086
+ return false;
1087
+ }
1088
+ } catch (e) {
1089
+ error = e + '';
1090
+ return false;
1091
+ }
1092
+ return true;
1093
+ },
1094
+ // trueValue, falseValue, caseSensitive don't work.
1095
+ phContent: function(param) {
1096
+ return param === 'error' ? error :
1097
+ param !== 'min' && param !== 'max' ? null :
1098
+ options.hasOwnProperty(param) ? options[param] + '' : '';
1099
+ }
1100
+ });
1101
+ // added: exists, create, min, max, isFile, isDirectory, validate
1102
+ /* eslint-enable key-spacing */
1103
+ options = options || {};
1104
+
1105
+ if (query == null) { query = 'Input path (you can "cd" and "pwd"): '; }
1106
+
1107
+ exports.question(query, readOptions);
1108
+ return validPath;
1109
+ };
1110
+
1111
+ // props: preCheck, args, hRes, limit
1112
+ function getClHandler(commandHandler, options) {
1113
+ var clHandler = {},
1114
+ hIndex = {};
1115
+ if (typeof commandHandler === 'object') {
1116
+ Object.keys(commandHandler).forEach(function(cmd) {
1117
+ if (typeof commandHandler[cmd] === 'function') {
1118
+ hIndex[options.caseSensitive ? cmd : cmd.toLowerCase()] = commandHandler[cmd];
1119
+ }
1120
+ });
1121
+ clHandler.preCheck = function(res) {
1122
+ var cmdKey;
1123
+ clHandler.args = parseCl(res);
1124
+ cmdKey = clHandler.args[0] || '';
1125
+ if (!options.caseSensitive) { cmdKey = cmdKey.toLowerCase(); }
1126
+ clHandler.hRes =
1127
+ cmdKey !== '_' && hIndex.hasOwnProperty(cmdKey)
1128
+ ? hIndex[cmdKey].apply(res, clHandler.args.slice(1)) :
1129
+ hIndex.hasOwnProperty('_') ? hIndex._.apply(res, clHandler.args) : null;
1130
+ return {res: res, forceNext: false};
1131
+ };
1132
+ if (!hIndex.hasOwnProperty('_')) {
1133
+ clHandler.limit = function() { // It's called after preCheck.
1134
+ var cmdKey = clHandler.args[0] || '';
1135
+ if (!options.caseSensitive) { cmdKey = cmdKey.toLowerCase(); }
1136
+ return hIndex.hasOwnProperty(cmdKey);
1137
+ };
1138
+ }
1139
+ } else {
1140
+ clHandler.preCheck = function(res) {
1141
+ clHandler.args = parseCl(res);
1142
+ clHandler.hRes = typeof commandHandler === 'function'
1143
+ ? commandHandler.apply(res, clHandler.args) : true; // true for break loop
1144
+ return {res: res, forceNext: false};
1145
+ };
1146
+ }
1147
+ return clHandler;
1148
+ }
1149
+
1150
+ exports.promptCL = function(commandHandler, options) {
1151
+ /* eslint-disable key-spacing */
1152
+ var readOptions = margeOptions({
1153
+ // -------- default
1154
+ hideEchoBack: false,
1155
+ limitMessage: 'Requested command is not available.',
1156
+ caseSensitive: false,
1157
+ history: true
1158
+ }, options),
1159
+ // -------- forced
1160
+ // trueValue, falseValue, keepWhitespace don't work.
1161
+ // preCheck, limit (by clHandler)
1162
+ clHandler = getClHandler(commandHandler, readOptions);
1163
+ /* eslint-enable key-spacing */
1164
+ readOptions.limit = clHandler.limit;
1165
+ readOptions.preCheck = clHandler.preCheck;
1166
+ exports.prompt(readOptions);
1167
+ return clHandler.args;
1168
+ };
1169
+
1170
+ exports.promptLoop = function(inputHandler, options) {
1171
+ /* eslint-disable key-spacing */
1172
+ var readOptions = margeOptions({
1173
+ // -------- default
1174
+ hideEchoBack: false,
1175
+ trueValue: null,
1176
+ falseValue: null,
1177
+ caseSensitive: false,
1178
+ history: true
1179
+ }, options);
1180
+ /* eslint-enable key-spacing */
1181
+ while (true) { if (inputHandler(exports.prompt(readOptions))) { break; } }
1182
+ // return; // nothing is returned
1183
+ };
1184
+
1185
+ exports.promptCLLoop = function(commandHandler, options) {
1186
+ /* eslint-disable key-spacing */
1187
+ var readOptions = margeOptions({
1188
+ // -------- default
1189
+ hideEchoBack: false,
1190
+ limitMessage: 'Requested command is not available.',
1191
+ caseSensitive: false,
1192
+ history: true
1193
+ }, options),
1194
+ // -------- forced
1195
+ // trueValue, falseValue, keepWhitespace don't work.
1196
+ // preCheck, limit (by clHandler)
1197
+ clHandler = getClHandler(commandHandler, readOptions);
1198
+ /* eslint-enable key-spacing */
1199
+ readOptions.limit = clHandler.limit;
1200
+ readOptions.preCheck = clHandler.preCheck;
1201
+ while (true) {
1202
+ exports.prompt(readOptions);
1203
+ if (clHandler.hRes) { break; }
1204
+ }
1205
+ // return; // nothing is returned
1206
+ };
1207
+
1208
+ exports.promptSimShell = function(options) {
1209
+ /* eslint-disable key-spacing */
1210
+ return exports.prompt(margeOptions({
1211
+ // -------- default
1212
+ hideEchoBack: false,
1213
+ history: true
1214
+ }, options, {
1215
+ // -------- forced
1216
+ prompt: (function() {
1217
+ return IS_WIN ? '$<cwd>>' :
1218
+ // 'user@host:cwd$ '
1219
+ (process.env.USER || '') +
1220
+ (process.env.HOSTNAME ? '@' + process.env.HOSTNAME.replace(/\..*$/, '') : '') +
1221
+ ':$<cwdHome>$ ';
1222
+ })()
1223
+ }));
1224
+ /* eslint-enable key-spacing */
1225
+ };
1226
+
1227
+ function _keyInYN(query, options, limit) {
1228
+ var res;
1229
+ if (query == null) { query = 'Are you sure? '; }
1230
+ if ((!options || options.guide !== false) && (query += '')) {
1231
+ query = query.replace(/\s*:?\s*$/, '') + ' [y/n]: ';
1232
+ }
1233
+ /* eslint-disable key-spacing */
1234
+ res = exports.keyIn(query, margeOptions(options, {
1235
+ // -------- forced
1236
+ hideEchoBack: false,
1237
+ limit: limit,
1238
+ trueValue: 'y',
1239
+ falseValue: 'n',
1240
+ caseSensitive: false
1241
+ // mask doesn't work.
1242
+ }));
1243
+ // added: guide
1244
+ /* eslint-enable key-spacing */
1245
+ return typeof res === 'boolean' ? res : '';
1246
+ }
1247
+ exports.keyInYN = function(query, options) { return _keyInYN(query, options); };
1248
+ exports.keyInYNStrict = function(query, options) { return _keyInYN(query, options, 'yn'); };
1249
+
1250
+ exports.keyInPause = function(query, options) {
1251
+ if (query == null) { query = 'Continue...'; }
1252
+ if ((!options || options.guide !== false) && (query += '')) {
1253
+ query = query.replace(/\s+$/, '') + ' (Hit any key)';
1254
+ }
1255
+ /* eslint-disable key-spacing */
1256
+ exports.keyIn(query, margeOptions({
1257
+ // -------- default
1258
+ limit: null
1259
+ }, options, {
1260
+ // -------- forced
1261
+ hideEchoBack: true,
1262
+ mask: ''
1263
+ }));
1264
+ // added: guide
1265
+ /* eslint-enable key-spacing */
1266
+ // return; // nothing is returned
1267
+ };
1268
+
1269
+ exports.keyInSelect = function(items, query, options) {
1270
+ /* eslint-disable key-spacing */
1271
+ var readOptions = margeOptions({
1272
+ // -------- default
1273
+ hideEchoBack: false
1274
+ }, options, {
1275
+ // -------- forced
1276
+ trueValue: null,
1277
+ falseValue: null,
1278
+ caseSensitive: false,
1279
+ // limit (by items),
1280
+ phContent: function(param) {
1281
+ return param === 'itemsCount' ? items.length + '' :
1282
+ param === 'firstItem' ? (items[0] + '').trim() :
1283
+ param === 'lastItem' ? (items[items.length - 1] + '').trim() : null;
1284
+ }
1285
+ }),
1286
+ // added: guide, cancel
1287
+ keylist = '',
1288
+ key2i = {},
1289
+ charCode = 49 /* '1' */,
1290
+ display = '\n';
1291
+ /* eslint-enable key-spacing */
1292
+ if (!Array.isArray(items) || !items.length || items.length > 35) {
1293
+ throw '`items` must be Array (max length: 35).';
1294
+ }
1295
+
1296
+ items.forEach(function(item, i) {
1297
+ var key = String.fromCharCode(charCode);
1298
+ keylist += key;
1299
+ key2i[key] = i;
1300
+ display += '[' + key + '] ' + (item + '').trim() + '\n';
1301
+ charCode = charCode === 57 /* '9' */ ? 97 /* 'a' */ : charCode + 1;
1302
+ });
1303
+ if (!options || options.cancel !== false) {
1304
+ keylist += '0';
1305
+ key2i['0'] = -1;
1306
+ display += '[0] ' +
1307
+ (options && options.cancel != null && typeof options.cancel !== 'boolean'
1308
+ ? (options.cancel + '').trim() : 'CANCEL') + '\n';
1309
+ }
1310
+ readOptions.limit = keylist;
1311
+ display += '\n';
1312
+
1313
+ if (query == null) { query = 'Choose one from list: '; }
1314
+ if ((query += '')) {
1315
+ if (!options || options.guide !== false) {
1316
+ query = query.replace(/\s*:?\s*$/, '') + ' [$<limit>]: ';
1317
+ }
1318
+ display += query;
1319
+ }
1320
+
1321
+ return key2i[exports.keyIn(display, readOptions).toLowerCase()];
1322
+ };
1323
+
1324
+ exports.getRawInput = function() { return rawInput; };
1325
+
1326
+ // ======== DEPRECATED ========
1327
+ function _setOption(optionName, args) {
1328
+ var options;
1329
+ if (args.length) { options = {}; options[optionName] = args[0]; }
1330
+ return exports.setDefaultOptions(options)[optionName];
1331
+ }
1332
+ exports.setPrint = function() { return _setOption('print', arguments); };
1333
+ exports.setPrompt = function() { return _setOption('prompt', arguments); };
1334
+ exports.setEncoding = function() { return _setOption('encoding', arguments); };
1335
+ exports.setMask = function() { return _setOption('mask', arguments); };
1336
+ exports.setBufferSize = function() { return _setOption('bufferSize', arguments); };
1337
+
1338
+
1339
+ /***/ }),
1340
+
1341
+ /***/ 112:
1342
+ /***/ ((module, __unused_webpack_exports, __nccwpck_require__) => {
1343
+
1344
+ const readlineSync = __nccwpck_require__(552);
1345
+ const fs = __nccwpck_require__(896);
1346
+ const Lexer = __nccwpck_require__(211);
1347
+ const Parser = __nccwpck_require__(222);
1348
+
1349
+ class ReturnValue {
1350
+ constructor(value) { this.value = value; }
1351
+ }
1352
+ class BreakSignal {}
1353
+ class ContinueSignal {}
1354
+
1355
+ class Environment {
1356
+ constructor(parent = null) {
1357
+ this.store = Object.create(null);
1358
+ this.parent = parent;
1359
+ }
1360
+
1361
+ has(name) {
1362
+ if (name in this.store) return true;
1363
+ if (this.parent) return this.parent.has(name);
1364
+ return false;
1365
+ }
1366
+
1367
+ get(name) {
1368
+ if (name in this.store) return this.store[name];
1369
+ if (this.parent) return this.parent.get(name);
1370
+ throw new Error(`Undefined variable: ${name}`);
1371
+ }
1372
+
1373
+ set(name, value) {
1374
+ if (name in this.store) { this.store[name] = value; return value; }
1375
+ if (this.parent && this.parent.has(name)) { return this.parent.set(name, value); }
1376
+ this.store[name] = value;
1377
+ return value;
1378
+ }
1379
+
1380
+ define(name, value) {
1381
+ this.store[name] = value;
1382
+ return value;
1383
+ }
1384
+ }
1385
+
1386
+ class Evaluator {
1387
+ constructor() {
1388
+ this.global = new Environment();
1389
+ this.setupBuiltins();
1390
+ }
1391
+
1392
+ setupBuiltins() {
1393
+ this.global.define('len', arg => {
1394
+ if (Array.isArray(arg) || typeof arg === 'string') return arg.length;
1395
+ if (arg && typeof arg === 'object') return Object.keys(arg).length;
1396
+ return 0;
1397
+ });
1398
+
1399
+ this.global.define('print', arg => { console.log(arg); return null; });
1400
+ this.global.define('type', arg => {
1401
+ if (Array.isArray(arg)) return 'array';
1402
+ return typeof arg;
1403
+ });
1404
+ this.global.define('keys', arg => arg && typeof arg === 'object' ? Object.keys(arg) : []);
1405
+ this.global.define('values', arg => arg && typeof arg === 'object' ? Object.values(arg) : []);
1406
+
1407
+ this.global.define('ask', prompt => {
1408
+ const readlineSync = __nccwpck_require__(552);
1409
+ return readlineSync.question(prompt + ' ');
1410
+ });
1411
+ this.global.define('num', arg => {
1412
+ const n = Number(arg);
1413
+ if (Number.isNaN(n)) {
1414
+ throw new Error('Cannot convert value to number');
1415
+ }
1416
+ return n;
1417
+ });
1418
+
1419
+ this.global.define('str', arg => {
1420
+ return String(arg);
1421
+ });
1422
+
1423
+ }
1424
+
1425
+
1426
+ evaluate(node, env = this.global) {
1427
+ switch (node.type) {
1428
+ case 'Program': return this.evalProgram(node, env);
1429
+ case 'BlockStatement': return this.evalBlock(node, new Environment(env));
1430
+ case 'VarDeclaration': return this.evalVarDeclaration(node, env);
1431
+ case 'AssignmentExpression': return this.evalAssignment(node, env);
1432
+ case 'CompoundAssignment': return this.evalCompoundAssignment(node, env);
1433
+ case 'SldeployStatement': return this.evalSldeploy(node, env);
1434
+ case 'AskStatement': return this.evalAsk(node, env);
1435
+ case 'DefineStatement': return this.evalDefine(node, env);
1436
+ case 'ExpressionStatement': return this.evaluate(node.expression, env);
1437
+ case 'BinaryExpression': return this.evalBinary(node, env);
1438
+ case 'LogicalExpression': return this.evalLogical(node, env);
1439
+ case 'UnaryExpression': return this.evalUnary(node, env);
1440
+ case 'Literal': return node.value;
1441
+ case 'Identifier': return env.get(node.name);
1442
+ case 'IfStatement': return this.evalIf(node, env);
1443
+ case 'WhileStatement': return this.evalWhile(node, env);
1444
+ case 'ForStatement': return this.evalFor(node, env);
1445
+ case 'BreakStatement': throw new BreakSignal();
1446
+ case 'ContinueStatement': throw new ContinueSignal();
1447
+ case 'ImportStatement': return this.evalImport(node, env);
1448
+ case 'FunctionDeclaration': return this.evalFunctionDeclaration(node, env);
1449
+ case 'CallExpression': return this.evalCall(node, env);
1450
+ case 'ReturnStatement': {
1451
+ const val = node.argument ? this.evaluate(node.argument, env) : null;
1452
+ throw new ReturnValue(val);
1453
+ }
1454
+ case 'ArrayExpression': return node.elements.map(el => this.evaluate(el, env));
1455
+ case 'IndexExpression': return this.evalIndex(node, env);
1456
+ case 'ObjectExpression': return this.evalObject(node, env);
1457
+ case 'MemberExpression': return this.evalMember(node, env);
1458
+ case 'UpdateExpression': return this.evalUpdate(node, env);
1459
+ default:
1460
+ throw new Error(`Unknown node type in evaluator: ${node.type}`);
1461
+ }
1462
+ }
1463
+
1464
+ evalProgram(node, env) {
1465
+ let result = null;
1466
+ for (const stmt of node.body) {
1467
+ result = this.evaluate(stmt, env);
1468
+ }
1469
+ return result;
1470
+ }
1471
+ evalImport(node, env) {
1472
+ const path = node.path;
1473
+ let lib;
1474
+
1475
+ try {
1476
+ lib = require(path);
1477
+ } catch (e) {
1478
+ const fullPath = path.endsWith('.sl') ? path : path + '.sl';
1479
+
1480
+ if (!fs.existsSync(fullPath)) {
1481
+ throw new Error(`Import not found: ${path}`);
1482
+ }
1483
+
1484
+ const code = fs.readFileSync(fullPath, 'utf-8');
1485
+ const tokens = new Lexer(code).getTokens();
1486
+ const ast = new Parser(tokens).parse();
1487
+
1488
+ const moduleEnv = new Environment(env);
1489
+ this.evaluate(ast, moduleEnv);
1490
+
1491
+ lib = {};
1492
+ for (const key of Object.keys(moduleEnv.store)) {
1493
+ lib[key] = moduleEnv.store[key];
1494
+ }
1495
+
1496
+ // JS-style default export fallback
1497
+ lib.default = lib;
1498
+ }
1499
+
1500
+ for (const spec of node.specifiers) {
1501
+ if (spec.type === 'DefaultImport') {
1502
+ env.define(spec.local, lib.default ?? lib);
1503
+ }
1504
+
1505
+ if (spec.type === 'NamespaceImport') {
1506
+ env.define(spec.local, lib);
1507
+ }
1508
+
1509
+ if (spec.type === 'NamedImport') {
1510
+ if (!(spec.imported in lib)) {
1511
+ throw new Error(`Module '${path}' has no export '${spec.imported}'`);
1512
+ }
1513
+ env.define(spec.local, lib[spec.imported]);
1514
+ }
1515
+ }
1516
+
1517
+ return null;
1518
+ }
1519
+
1520
+ evalBlock(node, env) {
1521
+ let result = null;
1522
+ for (const stmt of node.body) {
1523
+ try {
1524
+ result = this.evaluate(stmt, env);
1525
+ } catch (e) {
1526
+ if (e instanceof ReturnValue || e instanceof BreakSignal || e instanceof ContinueSignal) throw e;
1527
+ throw e;
1528
+ }
1529
+ }
1530
+ return result;
1531
+ }
1532
+
1533
+ evalVarDeclaration(node, env) {
1534
+ const val = this.evaluate(node.expr, env);
1535
+ return env.define(node.id, val);
1536
+ }
1537
+
1538
+ evalAssignment(node, env) {
1539
+ const rightVal = this.evaluate(node.right, env);
1540
+ const left = node.left;
1541
+
1542
+ if (left.type === 'Identifier') return env.set(left.name, rightVal);
1543
+ if (left.type === 'MemberExpression') {
1544
+ const obj = this.evaluate(left.object, env);
1545
+ obj[left.property] = rightVal;
1546
+ return rightVal;
1547
+ }
1548
+ if (left.type === 'IndexExpression') {
1549
+ const obj = this.evaluate(left.object, env);
1550
+ const idx = this.evaluate(left.indexer, env);
1551
+ obj[idx] = rightVal;
1552
+ return rightVal;
1553
+ }
1554
+
1555
+ throw new Error('Invalid assignment target');
1556
+ }
1557
+
1558
+ evalCompoundAssignment(node, env) {
1559
+ const left = node.left;
1560
+ let current;
1561
+
1562
+ if (left.type === 'Identifier') current = env.get(left.name);
1563
+ else if (left.type === 'MemberExpression') current = this.evalMember(left, env);
1564
+ else if (left.type === 'IndexExpression') current = this.evalIndex(left, env);
1565
+ else throw new Error('Invalid compound assignment target');
1566
+
1567
+ const rhs = this.evaluate(node.right, env);
1568
+ let computed;
1569
+ switch (node.operator) {
1570
+ case 'PLUSEQ': computed = current + rhs; break;
1571
+ case 'MINUSEQ': computed = current - rhs; break;
1572
+ case 'STAREQ': computed = current * rhs; break;
1573
+ case 'SLASHEQ': computed = current / rhs; break;
1574
+ case 'MODEQ': computed = current % rhs; break;
1575
+ default: throw new Error('Unknown compound operator');
1576
+ }
1577
+
1578
+ if (left.type === 'Identifier') env.set(left.name, computed);
1579
+ else if (left.type === 'MemberExpression') this.evalAssignment({ left, right: { type: 'Literal', value: computed }, type: 'AssignmentExpression' }, env);
1580
+ else this.evalAssignment({ left, right: { type: 'Literal', value: computed }, type: 'AssignmentExpression' }, env);
1581
+
1582
+ return computed;
1583
+ }
1584
+
1585
+ evalSldeploy(node, env) {
1586
+ const val = this.evaluate(node.expr, env);
1587
+ console.log(val);
1588
+ return val;
1589
+ }
1590
+
1591
+ evalAsk(node, env) {
1592
+ const prompt = this.evaluate(node.prompt, env);
1593
+ const input = readlineSync.question(prompt + ' ');
1594
+ return input;
1595
+ }
1596
+
1597
+ evalDefine(node, env) {
1598
+ const val = node.expr ? this.evaluate(node.expr, env) : null;
1599
+ return this.global.define(node.id, val);
1600
+ }
1601
+
1602
+ evalBinary(node, env) {
1603
+ const l = this.evaluate(node.left, env);
1604
+ const r = this.evaluate(node.right, env);
1605
+ switch (node.operator) {
1606
+ case 'PLUS': return l + r;
1607
+ case 'MINUS': return l - r;
1608
+ case 'STAR': return l * r;
1609
+ case 'SLASH': return l / r;
1610
+ case 'MOD': return l % r;
1611
+ case 'EQEQ': return l === r;
1612
+ case 'NOTEQ': return l !== r;
1613
+ case 'LT': return l < r;
1614
+ case 'LTE': return l <= r;
1615
+ case 'GT': return l > r;
1616
+ case 'GTE': return l >= r;
1617
+ default: throw new Error(`Unknown binary operator ${node.operator}`);
1618
+ }
1619
+ }
1620
+
1621
+ evalLogical(node, env) {
1622
+ const l = this.evaluate(node.left, env);
1623
+ if (node.operator === 'AND') return l && this.evaluate(node.right, env);
1624
+ if (node.operator === 'OR') return l || this.evaluate(node.right, env);
1625
+ throw new Error(`Unknown logical operator ${node.operator}`);
1626
+ }
1627
+
1628
+ evalUnary(node, env) {
1629
+ const val = this.evaluate(node.argument, env);
1630
+ switch (node.operator) {
1631
+ case 'NOT': return !val;
1632
+ case 'MINUS': return -val;
1633
+ case 'PLUS': return +val;
1634
+ default: throw new Error(`Unknown unary operator ${node.operator}`);
1635
+ }
1636
+ }
1637
+
1638
+ evalIf(node, env) {
1639
+ const test = this.evaluate(node.test, env);
1640
+ if (test) return this.evaluate(node.consequent, env);
1641
+ if (node.alternate) return this.evaluate(node.alternate, env);
1642
+ return null;
1643
+ }
1644
+
1645
+ evalWhile(node, env) {
1646
+ while (this.evaluate(node.test, env)) {
1647
+ try { this.evaluate(node.body, env); }
1648
+ catch (e) {
1649
+ if (e instanceof BreakSignal) break;
1650
+ if (e instanceof ContinueSignal) continue;
1651
+ throw e;
1652
+ }
1653
+ }
1654
+ return null;
1655
+ }
1656
+
1657
+ evalFor(node, env) {
1658
+ const local = new Environment(env);
1659
+ if (node.init) this.evaluate(node.init, local);
1660
+ while (!node.test || this.evaluate(node.test, local)) {
1661
+ try { this.evaluate(node.body, local); }
1662
+ catch (e) {
1663
+ if (e instanceof BreakSignal) break;
1664
+ if (e instanceof ContinueSignal) { if (node.update) this.evaluate(node.update, local); continue; }
1665
+ throw e;
1666
+ }
1667
+ if (node.update) this.evaluate(node.update, local);
1668
+ }
1669
+ return null;
1670
+ }
1671
+
1672
+ evalFunctionDeclaration(node, env) {
1673
+ const fn = { params: node.params, body: node.body, env };
1674
+ env.define(node.name, fn);
1675
+ return null;
1676
+ }
1677
+
1678
+ evalCall(node, env) {
1679
+ const calleeEvaluated = this.evaluate(node.callee, env);
1680
+ if (typeof calleeEvaluated === 'function') {
1681
+ const args = node.arguments.map(a => this.evaluate(a, env));
1682
+ return calleeEvaluated(...args);
1683
+ }
1684
+ if (!calleeEvaluated || typeof calleeEvaluated !== 'object' || !calleeEvaluated.body) {
1685
+ throw new Error('Call to non-function');
1686
+ }
1687
+ const fn = calleeEvaluated;
1688
+ const callEnv = new Environment(fn.env);
1689
+ fn.params.forEach((p, i) => {
1690
+ const argVal = node.arguments[i] ? this.evaluate(node.arguments[i], env) : null;
1691
+ callEnv.define(p, argVal);
1692
+ });
1693
+ try { return this.evaluate(fn.body, callEnv); }
1694
+ catch (e) { if (e instanceof ReturnValue) return e.value; throw e; }
1695
+ }
1696
+
1697
+ evalIndex(node, env) {
1698
+ const obj = this.evaluate(node.object, env);
1699
+ const idx = this.evaluate(node.indexer, env);
1700
+ if (obj == null) throw new Error('Indexing null/undefined');
1701
+ return obj[idx];
1702
+ }
1703
+
1704
+ evalObject(node, env) {
1705
+ const out = {};
1706
+ for (const p of node.props) out[p.key] = this.evaluate(p.value, env);
1707
+ return out;
1708
+ }
1709
+
1710
+ evalMember(node, env) {
1711
+ const obj = this.evaluate(node.object, env);
1712
+ if (obj == null) throw new Error('Member access of null/undefined');
1713
+ return obj[node.property];
1714
+ }
1715
+
1716
+ evalUpdate(node, env) {
1717
+ const arg = node.argument;
1718
+ const getCurrent = () => {
1719
+ if (arg.type === 'Identifier') return env.get(arg.name);
1720
+ if (arg.type === 'MemberExpression') return this.evalMember(arg, env);
1721
+ if (arg.type === 'IndexExpression') return this.evalIndex(arg, env);
1722
+ throw new Error('Invalid update target');
1723
+ };
1724
+ const setValue = (v) => {
1725
+ if (arg.type === 'Identifier') env.set(arg.name, v);
1726
+ else if (arg.type === 'MemberExpression') {
1727
+ const obj = this.evaluate(arg.object, env);
1728
+ obj[arg.property] = v;
1729
+ }
1730
+ else if (arg.type === 'IndexExpression') {
1731
+ const obj = this.evaluate(arg.object, env);
1732
+ const idx = this.evaluate(arg.indexer, env);
1733
+ obj[idx] = v;
1734
+ }
1735
+ };
1736
+ const current = getCurrent();
1737
+ const newVal = (node.operator === 'PLUSPLUS') ? current + 1 : current - 1;
1738
+ if (node.prefix) { setValue(newVal); return newVal; }
1739
+ else { setValue(newVal); return current; }
1740
+ }
1741
+ }
1742
+
1743
+ module.exports = Evaluator;
1744
+
1745
+ /***/ }),
1746
+
1747
+ /***/ 211:
1748
+ /***/ ((module) => {
1749
+
1750
+ class Lexer {
1751
+ constructor(input) {
1752
+ this.input = input;
1753
+ this.pos = 0;
1754
+ this.currentChar = input[0] || null;
1755
+ }
1756
+
1757
+ advance() {
1758
+ this.pos++;
1759
+ this.currentChar = this.pos < this.input.length ? this.input[this.pos] : null;
1760
+ }
1761
+
1762
+ peek() {
1763
+ return this.pos + 1 < this.input.length ? this.input[this.pos + 1] : null;
1764
+ }
1765
+
1766
+ error(msg) {
1767
+ throw new Error(`LEXER ERROR: ${msg} at position ${this.pos}`);
1768
+ }
1769
+
1770
+ skipWhitespace() {
1771
+ while (this.currentChar && /\s/.test(this.currentChar)) this.advance();
1772
+ }
1773
+
1774
+ skipComment() {
1775
+ if (this.currentChar === '#') {
1776
+ if (this.peek() === '*') {
1777
+ this.advance(); this.advance(); // skip #*
1778
+ while (this.currentChar !== null) {
1779
+ if (this.currentChar === '*' && this.peek() === '#') {
1780
+ this.advance(); this.advance();
1781
+ return;
1782
+ }
1783
+ this.advance();
1784
+ }
1785
+ this.error("Unterminated multi-line comment (#* ... *#)");
1786
+ } else {
1787
+ while (this.currentChar && this.currentChar !== '\n') this.advance();
1788
+ }
1789
+ }
1790
+ }
1791
+
1792
+ number() {
1793
+ let result = '';
1794
+ while (this.currentChar && /[0-9]/.test(this.currentChar)) {
1795
+ result += this.currentChar;
1796
+ this.advance();
1797
+ }
1798
+
1799
+ if (this.currentChar === '.' && /[0-9]/.test(this.peek())) {
1800
+ result += '.'; this.advance();
1801
+ while (this.currentChar && /[0-9]/.test(this.currentChar)) {
1802
+ result += this.currentChar;
1803
+ this.advance();
1804
+ }
1805
+ return { type: 'NUMBER', value: parseFloat(result) };
1806
+ }
1807
+
1808
+ return { type: 'NUMBER', value: parseInt(result) };
1809
+ }
1810
+
1811
+ identifier() {
1812
+ let result = '';
1813
+ while (this.currentChar && /[A-Za-z0-9_]/.test(this.currentChar)) {
1814
+ result += this.currentChar;
1815
+ this.advance();
1816
+ }
1817
+
1818
+ const keywords = [
1819
+ 'let', 'sldeploy', 'if', 'else', 'while', 'for',
1820
+ 'break', 'continue', 'func', 'return', 'true', 'false', 'null',
1821
+ 'ask', 'define', 'import', 'from', 'as'
1822
+ ];
1823
+
1824
+ if (keywords.includes(result)) {
1825
+ return { type: result.toUpperCase(), value: result };
1826
+ }
1827
+
1828
+ return { type: 'IDENTIFIER', value: result };
1829
+ }
1830
+
1831
+
1832
+ string() {
1833
+ const quote = this.currentChar;
1834
+ this.advance();
1835
+ let result = '';
1836
+
1837
+ while (this.currentChar && this.currentChar !== quote) {
1838
+ if (this.currentChar === '\\') {
1839
+ this.advance();
1840
+ switch (this.currentChar) {
1841
+ case 'n': result += '\n'; break;
1842
+ case 't': result += '\t'; break;
1843
+ case '"': result += '"'; break;
1844
+ case "'": result += "'"; break;
1845
+ case '\\': result += '\\'; break;
1846
+ default: result += this.currentChar;
1847
+ }
1848
+ } else {
1849
+ result += this.currentChar;
1850
+ }
1851
+ this.advance();
1852
+ }
1853
+
1854
+ if (this.currentChar !== quote) {
1855
+ this.error('Unterminated string literal');
1856
+ }
1857
+
1858
+ this.advance();
1859
+ return { type: 'STRING', value: result };
1860
+ }
1861
+
1862
+ getTokens() {
1863
+ const tokens = [];
1864
+
1865
+ while (this.currentChar !== null) {
1866
+ if (/\s/.test(this.currentChar)) { this.skipWhitespace(); continue; }
1867
+ if (this.currentChar === '#') { this.skipComment(); continue; }
1868
+ if (/[0-9]/.test(this.currentChar)) { tokens.push(this.number()); continue; }
1869
+ if (/[A-Za-z_]/.test(this.currentChar)) { tokens.push(this.identifier()); continue; }
1870
+ if (this.currentChar === '"' || this.currentChar === "'") { tokens.push(this.string()); continue; }
1871
+
1872
+ const char = this.currentChar;
1873
+ const next = this.peek();
1874
+
1875
+ if (char === '=' && next === '=') { tokens.push({ type: 'EQEQ' }); this.advance(); this.advance(); continue; }
1876
+ if (char === '=' && next === '>') { tokens.push({ type: 'ARROW' }); this.advance(); this.advance(); continue; }
1877
+ if (char === '!' && next === '=') { tokens.push({ type: 'NOTEQ' }); this.advance(); this.advance(); continue; }
1878
+ if (char === '<' && next === '=') { tokens.push({ type: 'LTE' }); this.advance(); this.advance(); continue; }
1879
+ if (char === '>' && next === '=') { tokens.push({ type: 'GTE' }); this.advance(); this.advance(); continue; }
1880
+ if (char === '&' && next === '&') { tokens.push({ type: 'AND' }); this.advance(); this.advance(); continue; }
1881
+ if (char === '|' && next === '|') { tokens.push({ type: 'OR' }); this.advance(); this.advance(); continue; }
1882
+ if (char === '+' && next === '+') { tokens.push({ type: 'PLUSPLUS' }); this.advance(); this.advance(); continue; }
1883
+ if (char === '-' && next === '-') { tokens.push({ type: 'MINUSMINUS' }); this.advance(); this.advance(); continue; }
1884
+
1885
+ const map = { '+': 'PLUSEQ', '-': 'MINUSEQ', '*': 'STAREQ', '/': 'SLASHEQ', '%': 'MODEQ' };
1886
+ if (next === '=' && map[char]) { tokens.push({ type: map[char] }); this.advance(); this.advance(); continue; }
1887
+
1888
+ const singles = {
1889
+ '+': 'PLUS', '-': 'MINUS', '*': 'STAR', '/': 'SLASH', '%': 'MOD',
1890
+ '=': 'EQUAL', '<': 'LT', '>': 'GT', '!': 'NOT',
1891
+ '(': 'LPAREN', ')': 'RPAREN', '{': 'LBRACE', '}': 'RBRACE',
1892
+ ';': 'SEMICOLON', ',': 'COMMA', '[': 'LBRACKET', ']': 'RBRACKET',
1893
+ ':': 'COLON', '.': 'DOT'
1894
+ };
1895
+
1896
+ if (singles[char]) { tokens.push({ type: singles[char] }); this.advance(); continue; }
1897
+
1898
+ this.error("Unexpected character: " + char);
1899
+ }
1900
+
1901
+ tokens.push({ type: 'EOF' });
1902
+ return tokens;
1903
+ }
1904
+ }
1905
+
1906
+ module.exports = Lexer;
1907
+
1908
+ /***/ }),
1909
+
1910
+ /***/ 222:
1911
+ /***/ ((module) => {
1912
+
1913
+ class Parser {
1914
+ constructor(tokens) {
1915
+ this.tokens = tokens;
1916
+ this.pos = 0;
1917
+ this.current = this.tokens[this.pos];
1918
+ }
1919
+
1920
+ advance() {
1921
+ this.pos++;
1922
+ this.current = this.pos < this.tokens.length ? this.tokens[this.pos] : { type: 'EOF' };
1923
+ }
1924
+
1925
+ eat(type) {
1926
+ if (this.current.type === type) this.advance();
1927
+ else throw new Error(`Expected ${type}, got ${this.current.type}`);
1928
+ }
1929
+
1930
+ peekType(offset = 1) {
1931
+ return (this.tokens[this.pos + offset] || { type: 'EOF' }).type;
1932
+ }
1933
+
1934
+ parse() {
1935
+ const body = [];
1936
+ while (this.current.type !== 'EOF') {
1937
+ body.push(this.statement());
1938
+ }
1939
+ return { type: 'Program', body };
1940
+ }
1941
+
1942
+ statement() {
1943
+ switch (this.current.type) {
1944
+ case 'LET': return this.varDeclaration();
1945
+ case 'SLDEPLOY': return this.sldeployStatement();
1946
+ case 'DEFINE': return this.defineStatement();
1947
+ case 'IF': return this.ifStatement();
1948
+ case 'WHILE': return this.whileStatement();
1949
+ case 'FOR': return this.forStatement();
1950
+ case 'BREAK': return this.breakStatement();
1951
+ case 'CONTINUE': return this.continueStatement();
1952
+ case 'FUNC': return this.funcDeclaration();
1953
+ case 'RETURN': return this.returnStatement();
1954
+ case 'IMPORT': return this.importStatement();
1955
+ case 'LBRACE': return this.block();
1956
+ default:
1957
+ return this.expressionStatement();
1958
+ }
1959
+ }
1960
+
1961
+ varDeclaration() {
1962
+ this.eat('LET');
1963
+ const id = this.current.value;
1964
+ this.eat('IDENTIFIER');
1965
+ this.eat('EQUAL');
1966
+ const expr = this.expression();
1967
+ if (this.current.type === 'SEMICOLON') this.eat('SEMICOLON');
1968
+ return { type: 'VarDeclaration', id, expr };
1969
+ }
1970
+
1971
+ sldeployStatement() {
1972
+ this.eat('SLDEPLOY');
1973
+ const expr = this.expression();
1974
+ if (this.current.type === 'SEMICOLON') this.eat('SEMICOLON');
1975
+ return { type: 'SldeployStatement', expr };
1976
+ }
1977
+
1978
+ defineStatement() {
1979
+ this.eat('DEFINE');
1980
+ const id = this.current.value;
1981
+ this.eat('IDENTIFIER');
1982
+ let expr = null;
1983
+ if (this.current.type === 'EQUAL') {
1984
+ this.eat('EQUAL');
1985
+ expr = this.expression();
1986
+ }
1987
+ if (this.current.type === 'SEMICOLON') this.eat('SEMICOLON');
1988
+ return { type: 'DefineStatement', id, expr };
1989
+ }
1990
+
1991
+ ifStatement() {
1992
+ this.eat('IF');
1993
+ this.eat('LPAREN');
1994
+ const test = this.expression();
1995
+ this.eat('RPAREN');
1996
+ const consequent = this.block();
1997
+ let alternate = null;
1998
+ if (this.current.type === 'ELSE') {
1999
+ this.eat('ELSE');
2000
+ if (this.current.type === 'IF') alternate = this.ifStatement();
2001
+ else alternate = this.block();
2002
+ }
2003
+ return { type: 'IfStatement', test, consequent, alternate };
2004
+ }
2005
+
2006
+ whileStatement() {
2007
+ this.eat('WHILE');
2008
+ this.eat('LPAREN');
2009
+ const test = this.expression();
2010
+ this.eat('RPAREN');
2011
+ const body = this.block();
2012
+ return { type: 'WhileStatement', test, body };
2013
+ }
2014
+ importStatement() {
2015
+ this.eat('IMPORT');
2016
+
2017
+ let specifiers = [];
2018
+
2019
+ if (this.current.type === 'STAR') {
2020
+ this.eat('STAR');
2021
+ this.eat('AS');
2022
+ const name = this.current.value;
2023
+ this.eat('IDENTIFIER');
2024
+ specifiers.push({ type: 'NamespaceImport', local: name });
2025
+ }
2026
+ else if (this.current.type === 'LBRACE') {
2027
+ this.eat('LBRACE');
2028
+ while (this.current.type !== 'RBRACE') {
2029
+ const importedName = this.current.value;
2030
+ this.eat('IDENTIFIER');
2031
+ let localName = importedName;
2032
+ if (this.current.type === 'AS') {
2033
+ this.eat('AS');
2034
+ localName = this.current.value;
2035
+ this.eat('IDENTIFIER');
2036
+ }
2037
+ specifiers.push({ type: 'NamedImport', imported: importedName, local: localName });
2038
+ if (this.current.type === 'COMMA') this.eat('COMMA');
2039
+ }
2040
+ this.eat('RBRACE');
2041
+ }
2042
+ else if (this.current.type === 'IDENTIFIER') {
2043
+ const localName = this.current.value;
2044
+ this.eat('IDENTIFIER');
2045
+ specifiers.push({ type: 'DefaultImport', local: localName });
2046
+ } else {
2047
+ throw new Error('Unexpected token in import statement');
2048
+ }
2049
+
2050
+ this.eat('FROM');
2051
+ const pathToken = this.current;
2052
+ if (pathToken.type !== 'STRING') throw new Error('Expected string literal after from in import');
2053
+ this.eat('STRING');
2054
+
2055
+ if (this.current.type === 'SEMICOLON') this.eat('SEMICOLON');
2056
+
2057
+ return { type: 'ImportStatement', path: pathToken.value, specifiers };
2058
+ }
2059
+
2060
+
2061
+ forStatement() {
2062
+ this.eat('FOR');
2063
+ this.eat('LPAREN');
2064
+
2065
+ let init = null;
2066
+ if (this.current.type !== 'SEMICOLON') {
2067
+ init = this.current.type === 'LET' ? this.varDeclaration() : this.expressionStatement();
2068
+ } else {
2069
+ this.eat('SEMICOLON');
2070
+ }
2071
+
2072
+ let test = null;
2073
+ if (this.current.type !== 'SEMICOLON') test = this.expression();
2074
+ this.eat('SEMICOLON');
2075
+
2076
+ let update = null;
2077
+ if (this.current.type !== 'RPAREN') update = this.expression();
2078
+ this.eat('RPAREN');
2079
+
2080
+ const body = this.block();
2081
+ return { type: 'ForStatement', init, test, update, body };
2082
+ }
2083
+
2084
+ breakStatement() {
2085
+ this.eat('BREAK');
2086
+ if (this.current.type === 'SEMICOLON') this.eat('SEMICOLON');
2087
+ return { type: 'BreakStatement' };
2088
+ }
2089
+
2090
+ continueStatement() {
2091
+ this.eat('CONTINUE');
2092
+ if (this.current.type === 'SEMICOLON') this.eat('SEMICOLON');
2093
+ return { type: 'ContinueStatement' };
2094
+ }
2095
+
2096
+ funcDeclaration() {
2097
+ this.eat('FUNC');
2098
+ const name = this.current.value;
2099
+ this.eat('IDENTIFIER');
2100
+ this.eat('LPAREN');
2101
+ const params = [];
2102
+ if (this.current.type !== 'RPAREN') {
2103
+ params.push(this.current.value);
2104
+ this.eat('IDENTIFIER');
2105
+ while (this.current.type === 'COMMA') {
2106
+ this.eat('COMMA');
2107
+ params.push(this.current.value);
2108
+ this.eat('IDENTIFIER');
2109
+ }
2110
+ }
2111
+ this.eat('RPAREN');
2112
+ const body = this.block();
2113
+ return { type: 'FunctionDeclaration', name, params, body };
2114
+ }
2115
+
2116
+ returnStatement() {
2117
+ this.eat('RETURN');
2118
+ let argument = null;
2119
+ if (this.current.type !== 'SEMICOLON') argument = this.expression();
2120
+ if (this.current.type === 'SEMICOLON') this.eat('SEMICOLON');
2121
+ return { type: 'ReturnStatement', argument };
2122
+ }
2123
+
2124
+ block() {
2125
+ this.eat('LBRACE');
2126
+ const body = [];
2127
+ while (this.current.type !== 'RBRACE') {
2128
+ body.push(this.statement());
2129
+ }
2130
+ this.eat('RBRACE');
2131
+ return { type: 'BlockStatement', body };
2132
+ }
2133
+
2134
+ expressionStatement() {
2135
+ const expr = this.expression();
2136
+ if (this.current.type === 'SEMICOLON') this.eat('SEMICOLON');
2137
+ return { type: 'ExpressionStatement', expression: expr };
2138
+ }
2139
+
2140
+ expression() {
2141
+ return this.assignment();
2142
+ }
2143
+
2144
+ assignment() {
2145
+ const node = this.logicalOr();
2146
+ const compoundOps = ['PLUSEQ', 'MINUSEQ', 'STAREQ', 'SLASHEQ', 'MODEQ'];
2147
+ if (compoundOps.includes(this.current.type)) {
2148
+ const op = this.current.type;
2149
+ this.eat(op);
2150
+ const right = this.assignment();
2151
+ return { type: 'CompoundAssignment', operator: op, left: node, right };
2152
+ }
2153
+
2154
+ if (this.current.type === 'EQUAL') {
2155
+ this.eat('EQUAL');
2156
+ const right = this.assignment();
2157
+ return { type: 'AssignmentExpression', left: node, right };
2158
+ }
2159
+
2160
+ return node;
2161
+ }
2162
+
2163
+ logicalOr() {
2164
+ let node = this.logicalAnd();
2165
+ while (this.current.type === 'OR') {
2166
+ const op = this.current.type;
2167
+ this.eat(op);
2168
+ node = { type: 'LogicalExpression', operator: op, left: node, right: this.logicalAnd() };
2169
+ }
2170
+ return node;
2171
+ }
2172
+
2173
+ logicalAnd() {
2174
+ let node = this.equality();
2175
+ while (this.current.type === 'AND') {
2176
+ const op = this.current.type;
2177
+ this.eat(op);
2178
+ node = { type: 'LogicalExpression', operator: op, left: node, right: this.equality() };
2179
+ }
2180
+ return node;
2181
+ }
2182
+
2183
+ equality() {
2184
+ let node = this.comparison();
2185
+ while (['EQEQ', 'NOTEQ'].includes(this.current.type)) {
2186
+ const op = this.current.type;
2187
+ this.eat(op);
2188
+ node = { type: 'BinaryExpression', operator: op, left: node, right: this.comparison() };
2189
+ }
2190
+ return node;
2191
+ }
2192
+
2193
+ comparison() {
2194
+ let node = this.term();
2195
+ while (['LT', 'LTE', 'GT', 'GTE'].includes(this.current.type)) {
2196
+ const op = this.current.type;
2197
+ this.eat(op);
2198
+ node = { type: 'BinaryExpression', operator: op, left: node, right: this.term() };
2199
+ }
2200
+ return node;
2201
+ }
2202
+
2203
+ term() {
2204
+ let node = this.factor();
2205
+ while (['PLUS', 'MINUS'].includes(this.current.type)) {
2206
+ const op = this.current.type;
2207
+ this.eat(op);
2208
+ node = { type: 'BinaryExpression', operator: op, left: node, right: this.factor() };
2209
+ }
2210
+ return node;
2211
+ }
2212
+
2213
+ factor() {
2214
+ let node = this.unary();
2215
+ while (['STAR', 'SLASH', 'MOD'].includes(this.current.type)) {
2216
+ const op = this.current.type;
2217
+ this.eat(op);
2218
+ node = { type: 'BinaryExpression', operator: op, left: node, right: this.unary() };
2219
+ }
2220
+ return node;
2221
+ }
2222
+
2223
+ unary() {
2224
+ if (['NOT', 'MINUS', 'PLUS'].includes(this.current.type)) {
2225
+ const op = this.current.type;
2226
+ this.eat(op);
2227
+ return { type: 'UnaryExpression', operator: op, argument: this.unary() };
2228
+ }
2229
+ if (this.current.type === 'PLUSPLUS' || this.current.type === 'MINUSMINUS') {
2230
+ const op = this.current.type;
2231
+ this.eat(op);
2232
+ const argument = this.unary();
2233
+ return { type: 'UpdateExpression', operator: op, argument, prefix: true };
2234
+ }
2235
+ return this.postfix();
2236
+ }
2237
+
2238
+ postfix() {
2239
+ let node = this.primary();
2240
+ while (true) {
2241
+ if (this.current.type === 'LBRACKET') {
2242
+ this.eat('LBRACKET');
2243
+ const index = this.expression();
2244
+ this.eat('RBRACKET');
2245
+ node = { type: 'IndexExpression', object: node, indexer: index };
2246
+ continue;
2247
+ }
2248
+ if (this.current.type === 'LPAREN') {
2249
+ this.eat('LPAREN');
2250
+ const args = [];
2251
+ if (this.current.type !== 'RPAREN') {
2252
+ args.push(this.expression());
2253
+ while (this.current.type === 'COMMA') {
2254
+ this.eat('COMMA');
2255
+ args.push(this.expression());
2256
+ }
2257
+ }
2258
+ this.eat('RPAREN');
2259
+ node = { type: 'CallExpression', callee: node, arguments: args };
2260
+ continue;
2261
+ }
2262
+ if (this.current.type === 'DOT') {
2263
+ this.eat('DOT');
2264
+ if (this.current.type !== 'IDENTIFIER') throw new Error('Expected property name after dot');
2265
+ const property = this.current.value;
2266
+ this.eat('IDENTIFIER');
2267
+ node = { type: 'MemberExpression', object: node, property };
2268
+ continue;
2269
+ }
2270
+ if (this.current.type === 'PLUSPLUS' || this.current.type === 'MINUSMINUS') {
2271
+ const op = this.current.type;
2272
+ this.eat(op);
2273
+ node = { type: 'UpdateExpression', operator: op, argument: node, prefix: false };
2274
+ continue;
2275
+ }
2276
+ break;
2277
+ }
2278
+ return node;
2279
+ }
2280
+
2281
+ primary() {
2282
+ const t = this.current;
2283
+
2284
+ if (t.type === 'NUMBER') { this.eat('NUMBER'); return { type: 'Literal', value: t.value }; }
2285
+ if (t.type === 'STRING') { this.eat('STRING'); return { type: 'Literal', value: t.value }; }
2286
+ if (t.type === 'TRUE') { this.eat('TRUE'); return { type: 'Literal', value: true }; }
2287
+ if (t.type === 'FALSE') { this.eat('FALSE'); return { type: 'Literal', value: false }; }
2288
+ if (t.type === 'NULL') { this.eat('NULL'); return { type: 'Literal', value: null }; }
2289
+
2290
+ if (t.type === 'ASK') {
2291
+ this.eat('ASK');
2292
+ this.eat('LPAREN');
2293
+ const args = [];
2294
+ if (this.current.type !== 'RPAREN') {
2295
+ args.push(this.expression());
2296
+ while (this.current.type === 'COMMA') {
2297
+ this.eat('COMMA');
2298
+ args.push(this.expression());
2299
+ }
2300
+ }
2301
+ this.eat('RPAREN');
2302
+ return { type: 'CallExpression', callee: { type: 'Identifier', name: 'ask' }, arguments: args };
2303
+ }
2304
+
2305
+ if (t.type === 'IDENTIFIER') {
2306
+ const name = t.value;
2307
+ this.eat('IDENTIFIER');
2308
+ return { type: 'Identifier', name };
2309
+ }
2310
+
2311
+ if (t.type === 'LPAREN') {
2312
+ this.eat('LPAREN');
2313
+ const expr = this.expression();
2314
+ this.eat('RPAREN');
2315
+ return expr;
2316
+ }
2317
+
2318
+ if (t.type === 'LBRACKET') {
2319
+ this.eat('LBRACKET');
2320
+ const elements = [];
2321
+ if (this.current.type !== 'RBRACKET') {
2322
+ elements.push(this.expression());
2323
+ while (this.current.type === 'COMMA') {
2324
+ this.eat('COMMA');
2325
+ elements.push(this.expression());
2326
+ }
2327
+ }
2328
+ this.eat('RBRACKET');
2329
+ return { type: 'ArrayExpression', elements };
2330
+ }
2331
+
2332
+ if (t.type === 'LBRACE') {
2333
+ this.eat('LBRACE');
2334
+ const props = [];
2335
+ while (this.current.type !== 'RBRACE') {
2336
+ let key;
2337
+ if (this.current.type === 'STRING') { key = this.current.value; this.eat('STRING'); }
2338
+ else if (this.current.type === 'IDENTIFIER') { key = this.current.value; this.eat('IDENTIFIER'); }
2339
+ else throw new Error('Invalid object key');
2340
+ this.eat('COLON');
2341
+ const value = this.expression();
2342
+ props.push({ key, value });
2343
+ if (this.current.type === 'COMMA') this.eat('COMMA');
2344
+ }
2345
+ this.eat('RBRACE');
2346
+ return { type: 'ObjectExpression', props };
2347
+ }
2348
+
2349
+ throw new Error(`Unexpected token in primary: ${t.type}`);
2350
+ }
2351
+ }
2352
+
2353
+ module.exports = Parser;
2354
+
2355
+ /***/ }),
2356
+
2357
+ /***/ 317:
2358
+ /***/ ((module) => {
2359
+
2360
+ "use strict";
2361
+ module.exports = require("child_process");
2362
+
2363
+ /***/ }),
2364
+
2365
+ /***/ 982:
2366
+ /***/ ((module) => {
2367
+
2368
+ "use strict";
2369
+ module.exports = require("crypto");
2370
+
2371
+ /***/ }),
2372
+
2373
+ /***/ 896:
2374
+ /***/ ((module) => {
2375
+
2376
+ "use strict";
2377
+ module.exports = require("fs");
2378
+
2379
+ /***/ }),
2380
+
2381
+ /***/ 857:
2382
+ /***/ ((module) => {
2383
+
2384
+ "use strict";
2385
+ module.exports = require("os");
2386
+
2387
+ /***/ }),
2388
+
2389
+ /***/ 928:
2390
+ /***/ ((module) => {
2391
+
2392
+ "use strict";
2393
+ module.exports = require("path");
2394
+
2395
+ /***/ })
2396
+
2397
+ /******/ });
2398
+ /************************************************************************/
2399
+ /******/ // The module cache
2400
+ /******/ var __webpack_module_cache__ = {};
2401
+ /******/
2402
+ /******/ // The require function
2403
+ /******/ function __nccwpck_require__(moduleId) {
2404
+ /******/ // Check if module is in cache
2405
+ /******/ var cachedModule = __webpack_module_cache__[moduleId];
2406
+ /******/ if (cachedModule !== undefined) {
2407
+ /******/ return cachedModule.exports;
2408
+ /******/ }
2409
+ /******/ // Create a new module (and put it into the cache)
2410
+ /******/ var module = __webpack_module_cache__[moduleId] = {
2411
+ /******/ // no module.id needed
2412
+ /******/ // no module.loaded needed
2413
+ /******/ exports: {}
2414
+ /******/ };
2415
+ /******/
2416
+ /******/ // Execute the module function
2417
+ /******/ var threw = true;
2418
+ /******/ try {
2419
+ /******/ __webpack_modules__[moduleId](module, module.exports, __nccwpck_require__);
2420
+ /******/ threw = false;
2421
+ /******/ } finally {
2422
+ /******/ if(threw) delete __webpack_module_cache__[moduleId];
2423
+ /******/ }
2424
+ /******/
2425
+ /******/ // Return the exports of the module
2426
+ /******/ return module.exports;
2427
+ /******/ }
2428
+ /******/
2429
+ /************************************************************************/
2430
+ /******/ /* webpack/runtime/compat */
2431
+ /******/
2432
+ /******/ if (typeof __nccwpck_require__ !== 'undefined') __nccwpck_require__.ab = __dirname + "/";
2433
+ /******/
2434
+ /************************************************************************/
2435
+ var __webpack_exports__ = {};
2436
+ const fs = __nccwpck_require__(896);
2437
+ const path = __nccwpck_require__(928);
2438
+
2439
+ const Lexer = __nccwpck_require__(211);
2440
+ const Parser = __nccwpck_require__(222);
2441
+ const Evaluator = __nccwpck_require__(112);
2442
+
2443
+ const COLOR = {
2444
+ reset: '\x1b[0m',
2445
+ bold: '\x1b[1m',
2446
+ red: '\x1b[31m',
2447
+ yellow: '\x1b[33m',
2448
+ blue: '\x1b[34m',
2449
+ cyan: '\x1b[36m',
2450
+ gray: '\x1b[90m',
2451
+ green: '\x1b[32m'
2452
+ };
2453
+
2454
+ function waitAndExit(code = 1) {
2455
+ console.error(COLOR.gray + '\nPress any key to exit...' + COLOR.reset);
2456
+ process.stdin.setRawMode(true);
2457
+ process.stdin.resume();
2458
+ process.stdin.once('data', () => process.exit(code));
2459
+ }
2460
+
2461
+ function fatal(msg) {
2462
+ console.error(COLOR.red + msg + COLOR.reset);
2463
+ return waitAndExit(1);
2464
+ }
2465
+
2466
+ function printSourceContext(code, line, column) {
2467
+ const lines = code.split('\n');
2468
+ const srcLine = lines[line - 1];
2469
+ if (!srcLine) return;
2470
+
2471
+ console.error(
2472
+ COLOR.gray + `\n ${line} | ` + COLOR.reset + srcLine
2473
+ );
2474
+ console.error(
2475
+ COLOR.gray + ' | ' +
2476
+ COLOR.red + ' '.repeat(Math.max(0, column - 1)) + '^' +
2477
+ COLOR.reset
2478
+ );
2479
+ }
2480
+
2481
+ const args = process.argv.slice(2);
2482
+
2483
+ if (args.length === 0) {
2484
+ return fatal('Usage: starlight <file.sl>');
2485
+ }
2486
+
2487
+ const filePath = path.resolve(args[0]);
2488
+
2489
+ if (!fs.existsSync(filePath)) {
2490
+ return fatal(`File not found: ${filePath}`);
2491
+ }
2492
+
2493
+ let code;
2494
+ try {
2495
+ code = fs.readFileSync(filePath, 'utf-8');
2496
+ } catch (err) {
2497
+ return fatal(`Failed to read file: ${err.message}`);
2498
+ }
2499
+
2500
+ let tokens;
2501
+ try {
2502
+ const lexer = new Lexer(code);
2503
+ tokens = lexer.getTokens();
2504
+ } catch (err) {
2505
+ console.error(COLOR.red + COLOR.bold + 'Starlight Lexer Error' + COLOR.reset);
2506
+ console.error(COLOR.cyan + `File: ${filePath}` + COLOR.reset);
2507
+ console.error(COLOR.yellow + `Message: ${err.message}` + COLOR.reset);
2508
+
2509
+ if (err.line && err.column) {
2510
+ printSourceContext(code, err.line, err.column);
2511
+ }
2512
+
2513
+ return waitAndExit(1);
2514
+ }
2515
+
2516
+ let ast;
2517
+ try {
2518
+ const parser = new Parser(tokens);
2519
+ ast = parser.parse();
2520
+ } catch (err) {
2521
+ console.error(COLOR.red + COLOR.bold + 'Starlight Parser Error' + COLOR.reset);
2522
+ console.error(COLOR.cyan + `File: ${filePath}` + COLOR.reset);
2523
+ console.error(COLOR.yellow + `Message: ${err.message}` + COLOR.reset);
2524
+
2525
+ if (err.token && err.token.line && err.token.column) {
2526
+ printSourceContext(code, err.token.line, err.token.column);
2527
+ }
2528
+
2529
+ return waitAndExit(1);
2530
+ }
2531
+
2532
+ try {
2533
+ const evaluator = new Evaluator();
2534
+ evaluator.evaluate(ast);
2535
+ } catch (err) {
2536
+ console.error(COLOR.red + COLOR.bold + 'Starlight Runtime Error' + COLOR.reset);
2537
+ console.error(COLOR.cyan + `File: ${filePath}` + COLOR.reset);
2538
+ console.error(COLOR.yellow + `Message: ${err.message}` + COLOR.reset);
2539
+
2540
+ if (err.line && err.column) {
2541
+ printSourceContext(code, err.line, err.column);
2542
+ }
2543
+
2544
+ return waitAndExit(1);
2545
+ }
2546
+
2547
+ console.log(
2548
+ COLOR.green +
2549
+ '\nProgram finished successfully.' +
2550
+ COLOR.reset
2551
+ );
2552
+ waitAndExit(0);
2553
+
2554
+ module.exports = __webpack_exports__;
2555
+ /******/ })()
2556
+ ;