@jdeighan/coffee-utils 7.0.32 → 7.0.35

Sign up to get free protection for your applications and to get access to all the features.
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@jdeighan/coffee-utils",
3
3
  "type": "module",
4
- "version": "7.0.32",
4
+ "version": "7.0.35",
5
5
  "description": "A set of utility functions for CoffeeScript",
6
6
  "main": "coffee_utils.js",
7
7
  "exports": {
@@ -5,6 +5,14 @@ export sep_eq = '='.repeat(42)
5
5
  `export const undef = undefined`
6
6
  LOG = (lArgs...) -> console.log lArgs... # synonym for console.log()
7
7
 
8
+ export doHaltOnError = false
9
+
10
+ # ---------------------------------------------------------------------------
11
+
12
+ export haltOnError = () ->
13
+
14
+ doHaltOnError = true
15
+
8
16
  # ---------------------------------------------------------------------------
9
17
  # pass - do nothing
10
18
 
@@ -15,8 +23,37 @@ export pass = () ->
15
23
 
16
24
  export error = (message) ->
17
25
 
26
+ if doHaltOnError
27
+ console.trace("ERROR: #{message}")
28
+ process.exit()
18
29
  throw new Error(message)
19
30
 
31
+ # ---------------------------------------------------------------------------
32
+
33
+ getCallers = (stackTrace, lExclude=[]) ->
34
+
35
+ iter = stackTrace.matchAll(///
36
+ at
37
+ \s+
38
+ (?:
39
+ async
40
+ \s+
41
+ )?
42
+ ([^\s(]+)
43
+ ///g)
44
+ if !iter
45
+ return ["<unknown>"]
46
+
47
+ lCallers = []
48
+ for lMatches from iter
49
+ [_, caller] = lMatches
50
+ if (caller.indexOf('file://') == 0)
51
+ break
52
+ if caller not in lExclude
53
+ lCallers.push caller
54
+
55
+ return lCallers
56
+
20
57
  # ---------------------------------------------------------------------------
21
58
  # assert - mimic nodejs's assert
22
59
  # return true so we can use it in boolean expressions
@@ -24,7 +61,24 @@ export error = (message) ->
24
61
  export assert = (cond, msg) ->
25
62
 
26
63
  if ! cond
27
- error(msg)
64
+ # try
65
+ # throw new Error()
66
+ # catch e
67
+ # stackTrace = e.stack
68
+ stackTrace = new Error().stack
69
+ lCallers = getCallers(stackTrace, ['assert'])
70
+
71
+ # console.log 'STACK'
72
+ # console.log stackTrace
73
+ console.log '--------------------'
74
+ console.log 'CALL STACK:'
75
+ for caller in lCallers
76
+ console.log " #{caller}"
77
+ console.log '--------------------'
78
+ console.log "ERROR: #{msg} (in #{lCallers[0]}())"
79
+ if doHaltOnError
80
+ process.exit()
81
+ error msg
28
82
  return true
29
83
 
30
84
  # ---------------------------------------------------------------------------
@@ -391,15 +445,16 @@ export replaceVars = (line, hVars={}, rx=/__(env\.)?([A-Za-z_]\w*)__/g) ->
391
445
 
392
446
  replacerFunc = (match, prefix, name) =>
393
447
  if prefix
394
- result = process.env[name]
395
- else if ! hVars[name]?
396
- result = 'undef'
448
+ return process.env[name]
397
449
  else
398
- result = hVars[name]
399
- if ! isString(result)
400
- result = JSON.stringify(result)
401
- return result
402
-
450
+ value = hVars[name]
451
+ if defined(value)
452
+ if isString(value)
453
+ return value
454
+ else
455
+ return JSON.stringify(value)
456
+ else
457
+ return "__#{name}__"
403
458
  return line.replace(rx, replacerFunc)
404
459
 
405
460
  # ---------------------------------------------------------------------------
@@ -1,6 +1,7 @@
1
1
  // Generated by CoffeeScript 2.6.1
2
- // coffee_utils.coffee
3
- var LOG;
2
+ // coffee_utils.coffee
3
+ var LOG, getCallers,
4
+ indexOf = [].indexOf;
4
5
 
5
6
  export var sep_dash = '-'.repeat(42);
6
7
 
@@ -12,6 +13,12 @@ LOG = function(...lArgs) {
12
13
  return console.log(...lArgs); // synonym for console.log()
13
14
  };
14
15
 
16
+ export var doHaltOnError = false;
17
+
18
+ // ---------------------------------------------------------------------------
19
+ export var haltOnError = function() {
20
+ return doHaltOnError = true;
21
+ };
15
22
 
16
23
  // ---------------------------------------------------------------------------
17
24
  // pass - do nothing
@@ -20,14 +27,58 @@ export var pass = function() {};
20
27
  // ---------------------------------------------------------------------------
21
28
  // error - throw an error
22
29
  export var error = function(message) {
30
+ if (doHaltOnError) {
31
+ console.trace(`ERROR: ${message}`);
32
+ process.exit();
33
+ }
23
34
  throw new Error(message);
24
35
  };
25
36
 
37
+ // ---------------------------------------------------------------------------
38
+ getCallers = function(stackTrace, lExclude = []) {
39
+ var _, caller, iter, lCallers, lMatches;
40
+ iter = stackTrace.matchAll(/at\s+(?:async\s+)?([^\s(]+)/g);
41
+ if (!iter) {
42
+ return ["<unknown>"];
43
+ }
44
+ lCallers = [];
45
+ for (lMatches of iter) {
46
+ [_, caller] = lMatches;
47
+ if (caller.indexOf('file://') === 0) {
48
+ break;
49
+ }
50
+ if (indexOf.call(lExclude, caller) < 0) {
51
+ lCallers.push(caller);
52
+ }
53
+ }
54
+ return lCallers;
55
+ };
56
+
26
57
  // ---------------------------------------------------------------------------
27
58
  // assert - mimic nodejs's assert
28
59
  // return true so we can use it in boolean expressions
29
60
  export var assert = function(cond, msg) {
61
+ var caller, i, lCallers, len, stackTrace;
30
62
  if (!cond) {
63
+ // try
64
+ // throw new Error()
65
+ // catch e
66
+ // stackTrace = e.stack
67
+ stackTrace = new Error().stack;
68
+ lCallers = getCallers(stackTrace, ['assert']);
69
+ // console.log 'STACK'
70
+ // console.log stackTrace
71
+ console.log('--------------------');
72
+ console.log('CALL STACK:');
73
+ for (i = 0, len = lCallers.length; i < len; i++) {
74
+ caller = lCallers[i];
75
+ console.log(` ${caller}`);
76
+ }
77
+ console.log('--------------------');
78
+ console.log(`ERROR: ${msg} (in ${lCallers[0]}())`);
79
+ if (doHaltOnError) {
80
+ process.exit();
81
+ }
31
82
  error(msg);
32
83
  }
33
84
  return true;
@@ -428,18 +479,21 @@ export var replaceVars = function(line, hVars = {}, rx = /__(env\.)?([A-Za-z_]\w
428
479
  var replacerFunc;
429
480
  assert(isHash(hVars), "replaceVars() hVars is not a hash");
430
481
  replacerFunc = (match, prefix, name) => {
431
- var result;
482
+ var value;
432
483
  if (prefix) {
433
- result = process.env[name];
434
- } else if (hVars[name] == null) {
435
- result = 'undef';
484
+ return process.env[name];
436
485
  } else {
437
- result = hVars[name];
438
- if (!isString(result)) {
439
- result = JSON.stringify(result);
486
+ value = hVars[name];
487
+ if (defined(value)) {
488
+ if (isString(value)) {
489
+ return value;
490
+ } else {
491
+ return JSON.stringify(value);
492
+ }
493
+ } else {
494
+ return `__${name}__`;
440
495
  }
441
496
  }
442
- return result;
443
497
  };
444
498
  return line.replace(rx, replacerFunc);
445
499
  };
@@ -1,7 +1,7 @@
1
1
  # indent_utils.coffee
2
2
 
3
3
  import {
4
- assert, undef, error, escapeStr,
4
+ assert, undef, error, escapeStr, defined,
5
5
  OL, isInteger, isString, isArray, isEmpty, rtrim,
6
6
  } from '@jdeighan/coffee-utils'
7
7
  import {arrayToBlock, blockToArray} from '@jdeighan/coffee-utils/block'
@@ -68,7 +68,7 @@ export indented = (input, level=1) ->
68
68
 
69
69
  export undented = (text, level=undef) ->
70
70
 
71
- if level? && (level==0)
71
+ if defined(level) && (level==0)
72
72
  return text
73
73
 
74
74
  if isString(text)
@@ -85,7 +85,7 @@ export undented = (text, level=undef) ->
85
85
  error "undented(): Not an array or string: #{OL(text)}"
86
86
 
87
87
  # --- determine what to remove from beginning of each line
88
- if level?
88
+ if defined(level)
89
89
  assert isInteger(level), "undented(): level must be an integer"
90
90
  toRemove = indentation(level)
91
91
  else
@@ -5,6 +5,7 @@ import {
5
5
  undef,
6
6
  error,
7
7
  escapeStr,
8
+ defined,
8
9
  OL,
9
10
  isInteger,
10
11
  isString,
@@ -86,7 +87,7 @@ export var indented = function(input, level = 1) {
86
87
  // - returns same type as text, i.e. either string or array
87
88
  export var undented = function(text, level = undef) {
88
89
  var i, j, lLines, lMatches, lNewLines, len, len1, line, nToRemove, toRemove;
89
- if ((level != null) && (level === 0)) {
90
+ if (defined(level) && (level === 0)) {
90
91
  return text;
91
92
  }
92
93
  if (isString(text)) {
@@ -107,7 +108,7 @@ export var undented = function(text, level = undef) {
107
108
  error(`undented(): Not an array or string: ${OL(text)}`);
108
109
  }
109
110
  // --- determine what to remove from beginning of each line
110
- if (level != null) {
111
+ if (defined(level)) {
111
112
  assert(isInteger(level), "undented(): level must be an integer");
112
113
  toRemove = indentation(level);
113
114
  } else {