@jdeighan/coffee-utils 2.1.11 → 3.0.0
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/package.json +1 -1
- package/src/UnitTester.coffee +11 -6
- package/src/UnitTester.js +13 -7
- package/src/block_utils.coffee +51 -1
- package/src/block_utils.js +66 -3
- package/src/coffee_utils.coffee +0 -48
- package/src/coffee_utils.js +6 -67
- package/src/debug_utils.coffee +54 -10
- package/src/debug_utils.js +52 -13
- package/src/indent_utils.coffee +11 -9
- package/src/indent_utils.js +14 -10
- package/src/log_utils.coffee +4 -4
- package/src/log_utils.js +7 -4
package/package.json
CHANGED
package/src/UnitTester.coffee
CHANGED
@@ -4,9 +4,10 @@ import {strict as assert} from 'assert'
|
|
4
4
|
import test from 'ava'
|
5
5
|
|
6
6
|
import {
|
7
|
-
undef,
|
7
|
+
undef, pass, error,
|
8
8
|
isString, isFunction, isInteger, isArray,
|
9
9
|
} from '@jdeighan/coffee-utils'
|
10
|
+
import {blockToArray} from '@jdeighan/coffee-utils/block'
|
10
11
|
import {log, currentLogger, setLogger} from '@jdeighan/coffee-utils/log'
|
11
12
|
import {
|
12
13
|
debug, debugging, setDebugging,
|
@@ -25,6 +26,12 @@ export class UnitTester
|
|
25
26
|
|
26
27
|
# ........................................................................
|
27
28
|
|
29
|
+
initialize: () -> # override to do any initialization
|
30
|
+
|
31
|
+
pass
|
32
|
+
|
33
|
+
# ........................................................................
|
34
|
+
|
28
35
|
justshow: (flag) ->
|
29
36
|
|
30
37
|
@justshow = flag
|
@@ -67,10 +74,7 @@ export class UnitTester
|
|
67
74
|
# ........................................................................
|
68
75
|
|
69
76
|
equal: (lineNum, input, expected) ->
|
70
|
-
|
71
|
-
@setWhichTest 'is'
|
72
|
-
else
|
73
|
-
@setWhichTest 'deepEqual'
|
77
|
+
@setWhichTest 'deepEqual'
|
74
78
|
@test lineNum, input, expected
|
75
79
|
return
|
76
80
|
|
@@ -160,7 +164,7 @@ export class UnitTester
|
|
160
164
|
# Remove empty lines
|
161
165
|
|
162
166
|
if isString(input)
|
163
|
-
lLines = for line in
|
167
|
+
lLines = for line in blockToArray(input)
|
164
168
|
line = line.trim()
|
165
169
|
line.replace(/\s+/g, ' ')
|
166
170
|
lLines = lLines.filter (line) -> line != ''
|
@@ -172,6 +176,7 @@ export class UnitTester
|
|
172
176
|
|
173
177
|
test: (lineNum, input, expected) ->
|
174
178
|
|
179
|
+
@initialize()
|
175
180
|
@lineNum = lineNum # set an object property
|
176
181
|
|
177
182
|
if (lineNum < 0) && process.env.FINALTEST
|
package/src/UnitTester.js
CHANGED
@@ -8,14 +8,18 @@ import test from 'ava';
|
|
8
8
|
|
9
9
|
import {
|
10
10
|
undef,
|
11
|
+
pass,
|
11
12
|
error,
|
12
|
-
stringToArray,
|
13
13
|
isString,
|
14
14
|
isFunction,
|
15
15
|
isInteger,
|
16
16
|
isArray
|
17
17
|
} from '@jdeighan/coffee-utils';
|
18
18
|
|
19
|
+
import {
|
20
|
+
blockToArray
|
21
|
+
} from '@jdeighan/coffee-utils/block';
|
22
|
+
|
19
23
|
import {
|
20
24
|
log,
|
21
25
|
currentLogger,
|
@@ -39,6 +43,11 @@ export var UnitTester = class UnitTester {
|
|
39
43
|
this.maxLineNum = undef;
|
40
44
|
}
|
41
45
|
|
46
|
+
// ........................................................................
|
47
|
+
initialize() { // override to do any initialization
|
48
|
+
return pass;
|
49
|
+
}
|
50
|
+
|
42
51
|
// ........................................................................
|
43
52
|
justshow(flag) {
|
44
53
|
this.justshow = flag;
|
@@ -73,11 +82,7 @@ export var UnitTester = class UnitTester {
|
|
73
82
|
|
74
83
|
// ........................................................................
|
75
84
|
equal(lineNum, input, expected) {
|
76
|
-
|
77
|
-
this.setWhichTest('is');
|
78
|
-
} else {
|
79
|
-
this.setWhichTest('deepEqual');
|
80
|
-
}
|
85
|
+
this.setWhichTest('deepEqual');
|
81
86
|
this.test(lineNum, input, expected);
|
82
87
|
}
|
83
88
|
|
@@ -161,7 +166,7 @@ export var UnitTester = class UnitTester {
|
|
161
166
|
if (isString(input)) {
|
162
167
|
lLines = (function() {
|
163
168
|
var i, len, ref, results;
|
164
|
-
ref =
|
169
|
+
ref = blockToArray(input);
|
165
170
|
results = [];
|
166
171
|
for (i = 0, len = ref.length; i < len; i++) {
|
167
172
|
line = ref[i];
|
@@ -182,6 +187,7 @@ export var UnitTester = class UnitTester {
|
|
182
187
|
// ........................................................................
|
183
188
|
test(lineNum, input, expected) {
|
184
189
|
var err, errMsg, got, whichTest;
|
190
|
+
this.initialize();
|
185
191
|
this.lineNum = lineNum; // set an object property
|
186
192
|
if ((lineNum < 0) && process.env.FINALTEST) {
|
187
193
|
error("Negative line numbers not allowed in FINALTEST");
|
package/src/block_utils.coffee
CHANGED
@@ -6,10 +6,60 @@ import {
|
|
6
6
|
import {createInterface} from 'readline'
|
7
7
|
|
8
8
|
import {
|
9
|
-
isEmpty, nonEmpty, error, isComment,
|
9
|
+
isEmpty, nonEmpty, error, isComment, rtrim,
|
10
10
|
} from '@jdeighan/coffee-utils'
|
11
11
|
import {log} from '@jdeighan/coffee-utils/log'
|
12
12
|
|
13
|
+
# ---------------------------------------------------------------------------
|
14
|
+
# blockToArray - split a block into lines
|
15
|
+
|
16
|
+
export blockToArray = (block) ->
|
17
|
+
|
18
|
+
if isEmpty(block)
|
19
|
+
return []
|
20
|
+
else
|
21
|
+
lLines = block.split(/\r?\n/)
|
22
|
+
|
23
|
+
# --- remove trailing empty lines
|
24
|
+
len = lLines.length
|
25
|
+
while (len > 0) && isEmpty(lLines[len-1])
|
26
|
+
lLines.pop()
|
27
|
+
len -= 1
|
28
|
+
return lLines
|
29
|
+
|
30
|
+
# ---------------------------------------------------------------------------
|
31
|
+
# arrayToBlock - block will have no trailing whitespace
|
32
|
+
|
33
|
+
export arrayToBlock = (lLines) ->
|
34
|
+
|
35
|
+
if lLines.length == 0
|
36
|
+
return ''
|
37
|
+
else
|
38
|
+
return rtrim(lLines.join('\n'))
|
39
|
+
|
40
|
+
# ---------------------------------------------------------------------------
|
41
|
+
# normalizeBlock - remove blank lines, trim each line
|
42
|
+
# - collapse internal whitespace to ' '
|
43
|
+
|
44
|
+
export normalizeBlock = (content) ->
|
45
|
+
|
46
|
+
if typeof content != 'string'
|
47
|
+
throw new Error("normalizeBlock(): not a string")
|
48
|
+
lLines = for line in blockToArray(content)
|
49
|
+
line = line.trim()
|
50
|
+
line.replace(/\s+/g, ' ')
|
51
|
+
lLines = lLines.filter (line) -> line != ''
|
52
|
+
return lLines.join('\n')
|
53
|
+
|
54
|
+
# ---------------------------------------------------------------------------
|
55
|
+
# truncateBlock - limit block to a certain number of lines
|
56
|
+
|
57
|
+
export truncateBlock = (str, numLines) ->
|
58
|
+
|
59
|
+
lLines = blockToArray str
|
60
|
+
lLines.length = numLines
|
61
|
+
return arrayToBlock lLines
|
62
|
+
|
13
63
|
# ---------------------------------------------------------------------------
|
14
64
|
|
15
65
|
export joinBlocks = (lBlocks...) ->
|
package/src/block_utils.js
CHANGED
@@ -14,18 +14,81 @@ import {
|
|
14
14
|
isEmpty,
|
15
15
|
nonEmpty,
|
16
16
|
error,
|
17
|
-
isComment
|
17
|
+
isComment,
|
18
|
+
rtrim
|
18
19
|
} from '@jdeighan/coffee-utils';
|
19
20
|
|
20
21
|
import {
|
21
22
|
log
|
22
23
|
} from '@jdeighan/coffee-utils/log';
|
23
24
|
|
25
|
+
// ---------------------------------------------------------------------------
|
26
|
+
// blockToArray - split a block into lines
|
27
|
+
export var blockToArray = function(block) {
|
28
|
+
var lLines, len;
|
29
|
+
if (isEmpty(block)) {
|
30
|
+
return [];
|
31
|
+
} else {
|
32
|
+
lLines = block.split(/\r?\n/);
|
33
|
+
// --- remove trailing empty lines
|
34
|
+
len = lLines.length;
|
35
|
+
while ((len > 0) && isEmpty(lLines[len - 1])) {
|
36
|
+
lLines.pop();
|
37
|
+
len -= 1;
|
38
|
+
}
|
39
|
+
return lLines;
|
40
|
+
}
|
41
|
+
};
|
42
|
+
|
43
|
+
// ---------------------------------------------------------------------------
|
44
|
+
// arrayToBlock - block will have no trailing whitespace
|
45
|
+
export var arrayToBlock = function(lLines) {
|
46
|
+
if (lLines.length === 0) {
|
47
|
+
return '';
|
48
|
+
} else {
|
49
|
+
return rtrim(lLines.join('\n'));
|
50
|
+
}
|
51
|
+
};
|
52
|
+
|
53
|
+
// ---------------------------------------------------------------------------
|
54
|
+
// normalizeBlock - remove blank lines, trim each line
|
55
|
+
// - collapse internal whitespace to ' '
|
56
|
+
export var normalizeBlock = function(content) {
|
57
|
+
var lLines, line;
|
58
|
+
if (typeof content !== 'string') {
|
59
|
+
throw new Error("normalizeBlock(): not a string");
|
60
|
+
}
|
61
|
+
lLines = (function() {
|
62
|
+
var i, len1, ref, results;
|
63
|
+
ref = blockToArray(content);
|
64
|
+
results = [];
|
65
|
+
for (i = 0, len1 = ref.length; i < len1; i++) {
|
66
|
+
line = ref[i];
|
67
|
+
line = line.trim();
|
68
|
+
results.push(line.replace(/\s+/g, ' '));
|
69
|
+
}
|
70
|
+
return results;
|
71
|
+
})();
|
72
|
+
lLines = lLines.filter(function(line) {
|
73
|
+
return line !== '';
|
74
|
+
});
|
75
|
+
return lLines.join('\n');
|
76
|
+
};
|
77
|
+
|
78
|
+
// ---------------------------------------------------------------------------
|
79
|
+
// truncateBlock - limit block to a certain number of lines
|
80
|
+
export var truncateBlock = function(str, numLines) {
|
81
|
+
var lLines;
|
82
|
+
lLines = blockToArray(str);
|
83
|
+
lLines.length = numLines;
|
84
|
+
return arrayToBlock(lLines);
|
85
|
+
};
|
86
|
+
|
24
87
|
// ---------------------------------------------------------------------------
|
25
88
|
export var joinBlocks = function(...lBlocks) {
|
26
|
-
var blk, i,
|
89
|
+
var blk, i, len1, str;
|
27
90
|
str = '';
|
28
|
-
for (i = 0,
|
91
|
+
for (i = 0, len1 = lBlocks.length; i < len1; i++) {
|
29
92
|
blk = lBlocks[i];
|
30
93
|
if (nonEmpty(blk)) {
|
31
94
|
str += "\n" + blk;
|
package/src/coffee_utils.coffee
CHANGED
@@ -233,45 +233,6 @@ export firstLine = (input) ->
|
|
233
233
|
else
|
234
234
|
return input.substring(0, pos)
|
235
235
|
|
236
|
-
# ---------------------------------------------------------------------------
|
237
|
-
# stringToArray - split a string into lines
|
238
|
-
|
239
|
-
export stringToArray = (str) ->
|
240
|
-
|
241
|
-
if isEmpty(str)
|
242
|
-
return []
|
243
|
-
else
|
244
|
-
lLines = str.split(/\r?\n/)
|
245
|
-
len = lLines.length
|
246
|
-
while (len > 0) && isEmpty(lLines[len-1])
|
247
|
-
lLines.pop()
|
248
|
-
len -= 1
|
249
|
-
return lLines
|
250
|
-
|
251
|
-
# ---------------------------------------------------------------------------
|
252
|
-
# arrayToString - every line has trailing newline
|
253
|
-
|
254
|
-
export arrayToString = (lLines) ->
|
255
|
-
|
256
|
-
if lLines.length == 0
|
257
|
-
return ''
|
258
|
-
else
|
259
|
-
return rtrim(lLines.join('\n'))
|
260
|
-
|
261
|
-
# ---------------------------------------------------------------------------
|
262
|
-
# normalize - remove blank lines, trim each line
|
263
|
-
# - collapse internal whitespace to ' '
|
264
|
-
|
265
|
-
export normalize = (content) ->
|
266
|
-
|
267
|
-
if typeof content != 'string'
|
268
|
-
throw new Error("normalize(): not a string")
|
269
|
-
lLines = for line in stringToArray(content)
|
270
|
-
line = line.trim()
|
271
|
-
line.replace(/\s+/g, ' ')
|
272
|
-
lLines = lLines.filter (line) -> line != ''
|
273
|
-
return lLines.join('\n')
|
274
|
-
|
275
236
|
# ---------------------------------------------------------------------------
|
276
237
|
|
277
238
|
export titleLine = (title, char='=', padding=2, linelen=42) ->
|
@@ -353,15 +314,6 @@ export oneline = (obj) ->
|
|
353
314
|
|
354
315
|
export OL = oneline
|
355
316
|
|
356
|
-
# ---------------------------------------------------------------------------
|
357
|
-
# truncateBlock - limit block to a certain number of lines
|
358
|
-
|
359
|
-
export truncateBlock = (str, numLines) ->
|
360
|
-
|
361
|
-
lLines = stringToArray str
|
362
|
-
lLines.length = numLines
|
363
|
-
return arrayToString lLines
|
364
|
-
|
365
317
|
# ---------------------------------------------------------------------------
|
366
318
|
|
367
319
|
export removeCR = (block) ->
|
package/src/coffee_utils.js
CHANGED
@@ -162,11 +162,11 @@ export var words = function(str) {
|
|
162
162
|
|
163
163
|
// ---------------------------------------------------------------------------
|
164
164
|
export var isArrayOfHashes = function(lItems) {
|
165
|
-
var i, item,
|
165
|
+
var i, item, len;
|
166
166
|
if (!isArray(lItems)) {
|
167
167
|
return false;
|
168
168
|
}
|
169
|
-
for (i = 0,
|
169
|
+
for (i = 0, len = lItems.length; i < len; i++) {
|
170
170
|
item = lItems[i];
|
171
171
|
if (!isHash(item)) {
|
172
172
|
return false;
|
@@ -177,11 +177,11 @@ export var isArrayOfHashes = function(lItems) {
|
|
177
177
|
|
178
178
|
// ---------------------------------------------------------------------------
|
179
179
|
export var isArrayOfStrings = function(lItems) {
|
180
|
-
var i, item,
|
180
|
+
var i, item, len;
|
181
181
|
if (!isArray(lItems)) {
|
182
182
|
return false;
|
183
183
|
}
|
184
|
-
for (i = 0,
|
184
|
+
for (i = 0, len = lItems.length; i < len; i++) {
|
185
185
|
item = lItems[i];
|
186
186
|
if (!isString(item)) {
|
187
187
|
return false;
|
@@ -242,58 +242,6 @@ export var firstLine = function(input) {
|
|
242
242
|
}
|
243
243
|
};
|
244
244
|
|
245
|
-
// ---------------------------------------------------------------------------
|
246
|
-
// stringToArray - split a string into lines
|
247
|
-
export var stringToArray = function(str) {
|
248
|
-
var lLines, len;
|
249
|
-
if (isEmpty(str)) {
|
250
|
-
return [];
|
251
|
-
} else {
|
252
|
-
lLines = str.split(/\r?\n/);
|
253
|
-
len = lLines.length;
|
254
|
-
while ((len > 0) && isEmpty(lLines[len - 1])) {
|
255
|
-
lLines.pop();
|
256
|
-
len -= 1;
|
257
|
-
}
|
258
|
-
return lLines;
|
259
|
-
}
|
260
|
-
};
|
261
|
-
|
262
|
-
// ---------------------------------------------------------------------------
|
263
|
-
// arrayToString - every line has trailing newline
|
264
|
-
export var arrayToString = function(lLines) {
|
265
|
-
if (lLines.length === 0) {
|
266
|
-
return '';
|
267
|
-
} else {
|
268
|
-
return rtrim(lLines.join('\n'));
|
269
|
-
}
|
270
|
-
};
|
271
|
-
|
272
|
-
// ---------------------------------------------------------------------------
|
273
|
-
// normalize - remove blank lines, trim each line
|
274
|
-
// - collapse internal whitespace to ' '
|
275
|
-
export var normalize = function(content) {
|
276
|
-
var lLines, line;
|
277
|
-
if (typeof content !== 'string') {
|
278
|
-
throw new Error("normalize(): not a string");
|
279
|
-
}
|
280
|
-
lLines = (function() {
|
281
|
-
var i, len1, ref, results;
|
282
|
-
ref = stringToArray(content);
|
283
|
-
results = [];
|
284
|
-
for (i = 0, len1 = ref.length; i < len1; i++) {
|
285
|
-
line = ref[i];
|
286
|
-
line = line.trim();
|
287
|
-
results.push(line.replace(/\s+/g, ' '));
|
288
|
-
}
|
289
|
-
return results;
|
290
|
-
})();
|
291
|
-
lLines = lLines.filter(function(line) {
|
292
|
-
return line !== '';
|
293
|
-
});
|
294
|
-
return lLines.join('\n');
|
295
|
-
};
|
296
|
-
|
297
245
|
// ---------------------------------------------------------------------------
|
298
246
|
export var titleLine = function(title, char = '=', padding = 2, linelen = 42) {
|
299
247
|
var nLeft, nRight, strLeft, strMiddle, strRight, titleLen;
|
@@ -352,10 +300,10 @@ export var escapeStr = function(str) {
|
|
352
300
|
croak("escapeStr(): not a string", str, 'STRING');
|
353
301
|
}
|
354
302
|
lParts = (function() {
|
355
|
-
var i,
|
303
|
+
var i, len, ref, results;
|
356
304
|
ref = str.split('');
|
357
305
|
results = [];
|
358
|
-
for (i = 0,
|
306
|
+
for (i = 0, len = ref.length; i < len; i++) {
|
359
307
|
ch = ref[i];
|
360
308
|
if (ch === '\n') {
|
361
309
|
results.push('\\n');
|
@@ -385,15 +333,6 @@ export var oneline = function(obj) {
|
|
385
333
|
|
386
334
|
export var OL = oneline;
|
387
335
|
|
388
|
-
// ---------------------------------------------------------------------------
|
389
|
-
// truncateBlock - limit block to a certain number of lines
|
390
|
-
export var truncateBlock = function(str, numLines) {
|
391
|
-
var lLines;
|
392
|
-
lLines = stringToArray(str);
|
393
|
-
lLines.length = numLines;
|
394
|
-
return arrayToString(lLines);
|
395
|
-
};
|
396
|
-
|
397
336
|
// ---------------------------------------------------------------------------
|
398
337
|
export var removeCR = function(block) {
|
399
338
|
return block.replace(/\r/g, '');
|
package/src/debug_utils.coffee
CHANGED
@@ -3,9 +3,11 @@
|
|
3
3
|
import {strict as assert} from 'assert'
|
4
4
|
import {
|
5
5
|
undef, error, croak, warn, words, isString, isFunction,
|
6
|
-
|
6
|
+
oneline, escapeStr, isNumber, isArray,
|
7
7
|
} from '@jdeighan/coffee-utils'
|
8
|
+
import {blockToArray} from '@jdeighan/coffee-utils/block'
|
8
9
|
import {log} from '@jdeighan/coffee-utils/log'
|
10
|
+
import {slurp} from '@jdeighan/coffee-utils/fs'
|
9
11
|
|
10
12
|
vbar = '│' # unicode 2502
|
11
13
|
hbar = '─' # unicode 2500
|
@@ -103,8 +105,9 @@ export resetDebugging = () ->
|
|
103
105
|
export debug = (lArgs...) ->
|
104
106
|
# --- either 1 or 2 args
|
105
107
|
|
106
|
-
|
107
|
-
|
108
|
+
# --- We always need to manipulate the stack when we encounter
|
109
|
+
# either "enter X" or "return from X", so we can't short-circuit
|
110
|
+
# when debugging is off
|
108
111
|
|
109
112
|
nArgs = lArgs.length
|
110
113
|
assert ((nArgs >= 1) && (nArgs <= 2)), "debug(); Bad # args #{nArgs}"
|
@@ -126,7 +129,7 @@ export debug = (lArgs...) ->
|
|
126
129
|
\s*
|
127
130
|
enter
|
128
131
|
\s+
|
129
|
-
([A-Za-z_][A-Za-z0-9_]*)
|
132
|
+
([A-Za-z_][A-Za-z0-9_\.]*)
|
130
133
|
///))
|
131
134
|
entering = true
|
132
135
|
curFunc = lMatches[1]
|
@@ -136,7 +139,7 @@ export debug = (lArgs...) ->
|
|
136
139
|
.*
|
137
140
|
from
|
138
141
|
\s+
|
139
|
-
([A-Za-z_][A-Za-z0-9_]*)
|
142
|
+
([A-Za-z_][A-Za-z0-9_\.]*)
|
140
143
|
///))
|
141
144
|
returning = true
|
142
145
|
curFunc = lMatches[1]
|
@@ -163,15 +166,14 @@ export debug = (lArgs...) ->
|
|
163
166
|
logItem: true,
|
164
167
|
itemPrefix: stripArrow(prefix),
|
165
168
|
}
|
169
|
+
if returning && (debugLevel > 0)
|
170
|
+
debugLevel -= 1
|
166
171
|
|
167
172
|
if returning && lDebugFuncs && funcMatch(curFunc)
|
168
173
|
setDebugging false # revert to previous setting - might still be on
|
169
174
|
|
170
|
-
if debugging
|
171
|
-
|
172
|
-
debugLevel += 1
|
173
|
-
if returning && (debugLevel > 0)
|
174
|
-
debugLevel -= 1
|
175
|
+
if debugging && entering
|
176
|
+
debugLevel += 1
|
175
177
|
return
|
176
178
|
|
177
179
|
# ---------------------------------------------------------------------------
|
@@ -195,3 +197,45 @@ export funcMatch = (curFunc) ->
|
|
195
197
|
return true
|
196
198
|
else
|
197
199
|
return false
|
200
|
+
|
201
|
+
# ---------------------------------------------------------------------------
|
202
|
+
|
203
|
+
export checkTrace = (block) ->
|
204
|
+
|
205
|
+
lStack = []
|
206
|
+
|
207
|
+
for line in blockToArray(block)
|
208
|
+
if lMatches = line.match(///
|
209
|
+
enter
|
210
|
+
\s+
|
211
|
+
([A-Za-z_][A-Za-z0-9_\.]*)
|
212
|
+
///)
|
213
|
+
funcName = lMatches[1]
|
214
|
+
lStack.push funcName
|
215
|
+
else if lMatches = line.match(///
|
216
|
+
return
|
217
|
+
.*
|
218
|
+
from
|
219
|
+
\s+
|
220
|
+
([A-Za-z_][A-Za-z0-9_\.]*)
|
221
|
+
///)
|
222
|
+
funcName = lMatches[1]
|
223
|
+
len = lStack.length
|
224
|
+
if (len == 0)
|
225
|
+
log "return from #{funcName} with empty stack"
|
226
|
+
else if (lStack[len-1] == funcName)
|
227
|
+
lStack.pop()
|
228
|
+
else if (lStack[len-2] == funcName)
|
229
|
+
log "missing return from #{lStack[len-2]}"
|
230
|
+
lStack.pop()
|
231
|
+
lStack.pop()
|
232
|
+
else
|
233
|
+
log "return from #{funcName} - not found on stack"
|
234
|
+
return
|
235
|
+
|
236
|
+
# ---------------------------------------------------------------------------
|
237
|
+
|
238
|
+
export checkTraceFile = (filepath) ->
|
239
|
+
|
240
|
+
checkTrace(slurp(filepath))
|
241
|
+
return
|
package/src/debug_utils.js
CHANGED
@@ -14,17 +14,24 @@ import {
|
|
14
14
|
words,
|
15
15
|
isString,
|
16
16
|
isFunction,
|
17
|
-
stringToArray,
|
18
17
|
oneline,
|
19
18
|
escapeStr,
|
20
19
|
isNumber,
|
21
20
|
isArray
|
22
21
|
} from '@jdeighan/coffee-utils';
|
23
22
|
|
23
|
+
import {
|
24
|
+
blockToArray
|
25
|
+
} from '@jdeighan/coffee-utils/block';
|
26
|
+
|
24
27
|
import {
|
25
28
|
log
|
26
29
|
} from '@jdeighan/coffee-utils/log';
|
27
30
|
|
31
|
+
import {
|
32
|
+
slurp
|
33
|
+
} from '@jdeighan/coffee-utils/fs';
|
34
|
+
|
28
35
|
vbar = '│'; // unicode 2502
|
29
36
|
|
30
37
|
hbar = '─'; // unicode 2500
|
@@ -115,9 +122,10 @@ export var resetDebugging = function() {
|
|
115
122
|
export var debug = function(...lArgs) {
|
116
123
|
var curFunc, entering, item, lMatches, nArgs, prefix, returning, str;
|
117
124
|
// --- either 1 or 2 args
|
118
|
-
|
119
|
-
|
120
|
-
|
125
|
+
|
126
|
+
// --- We always need to manipulate the stack when we encounter
|
127
|
+
// either "enter X" or "return from X", so we can't short-circuit
|
128
|
+
// when debugging is off
|
121
129
|
nArgs = lArgs.length;
|
122
130
|
assert((nArgs >= 1) && (nArgs <= 2), `debug(); Bad # args ${nArgs}`);
|
123
131
|
str = lArgs[0];
|
@@ -130,10 +138,10 @@ export var debug = function(...lArgs) {
|
|
130
138
|
// --- determine if we're entering or returning from a function
|
131
139
|
entering = returning = false;
|
132
140
|
curFunc = undef;
|
133
|
-
if ((lMatches = str.match(/^\s*enter\s+([A-Za-z_][A-Za-z0-9_]*)/))) {
|
141
|
+
if ((lMatches = str.match(/^\s*enter\s+([A-Za-z_][A-Za-z0-9_\.]*)/))) {
|
134
142
|
entering = true;
|
135
143
|
curFunc = lMatches[1];
|
136
|
-
} else if ((lMatches = str.match(/^\s*return.*from\s+([A-Za-z_][A-Za-z0-9_]*)/))) {
|
144
|
+
} else if ((lMatches = str.match(/^\s*return.*from\s+([A-Za-z_][A-Za-z0-9_\.]*)/))) {
|
137
145
|
returning = true;
|
138
146
|
curFunc = lMatches[1];
|
139
147
|
}
|
@@ -160,17 +168,15 @@ export var debug = function(...lArgs) {
|
|
160
168
|
itemPrefix: stripArrow(prefix)
|
161
169
|
});
|
162
170
|
}
|
171
|
+
if (returning && (debugLevel > 0)) {
|
172
|
+
debugLevel -= 1;
|
173
|
+
}
|
163
174
|
}
|
164
175
|
if (returning && lDebugFuncs && funcMatch(curFunc)) {
|
165
176
|
setDebugging(false); // revert to previous setting - might still be on
|
166
177
|
}
|
167
|
-
if (debugging) {
|
168
|
-
|
169
|
-
debugLevel += 1;
|
170
|
-
}
|
171
|
-
if (returning && (debugLevel > 0)) {
|
172
|
-
debugLevel -= 1;
|
173
|
-
}
|
178
|
+
if (debugging && entering) {
|
179
|
+
debugLevel += 1;
|
174
180
|
}
|
175
181
|
};
|
176
182
|
|
@@ -189,3 +195,36 @@ export var funcMatch = function(curFunc) {
|
|
189
195
|
return false;
|
190
196
|
}
|
191
197
|
};
|
198
|
+
|
199
|
+
// ---------------------------------------------------------------------------
|
200
|
+
export var checkTrace = function(block) {
|
201
|
+
var funcName, i, lMatches, lStack, len, len1, line, ref;
|
202
|
+
lStack = [];
|
203
|
+
ref = blockToArray(block);
|
204
|
+
for (i = 0, len1 = ref.length; i < len1; i++) {
|
205
|
+
line = ref[i];
|
206
|
+
if (lMatches = line.match(/enter\s+([A-Za-z_][A-Za-z0-9_\.]*)/)) {
|
207
|
+
funcName = lMatches[1];
|
208
|
+
lStack.push(funcName);
|
209
|
+
} else if (lMatches = line.match(/return.*from\s+([A-Za-z_][A-Za-z0-9_\.]*)/)) {
|
210
|
+
funcName = lMatches[1];
|
211
|
+
len = lStack.length;
|
212
|
+
if (len === 0) {
|
213
|
+
log(`return from ${funcName} with empty stack`);
|
214
|
+
} else if (lStack[len - 1] === funcName) {
|
215
|
+
lStack.pop();
|
216
|
+
} else if (lStack[len - 2] === funcName) {
|
217
|
+
log(`missing return from ${lStack[len - 2]}`);
|
218
|
+
lStack.pop();
|
219
|
+
lStack.pop();
|
220
|
+
} else {
|
221
|
+
log(`return from ${funcName} - not found on stack`);
|
222
|
+
}
|
223
|
+
}
|
224
|
+
}
|
225
|
+
};
|
226
|
+
|
227
|
+
// ---------------------------------------------------------------------------
|
228
|
+
export var checkTraceFile = function(filepath) {
|
229
|
+
checkTrace(slurp(filepath));
|
230
|
+
};
|
package/src/indent_utils.coffee
CHANGED
@@ -2,9 +2,10 @@
|
|
2
2
|
|
3
3
|
import {strict as assert} from 'assert'
|
4
4
|
import {
|
5
|
-
undef, error,
|
5
|
+
undef, error, escapeStr,
|
6
6
|
oneline, isInteger, isString, isArray, isEmpty, rtrim,
|
7
7
|
} from '@jdeighan/coffee-utils'
|
8
|
+
import {arrayToBlock, blockToArray} from '@jdeighan/coffee-utils/block'
|
8
9
|
|
9
10
|
# ---------------------------------------------------------------------------
|
10
11
|
# NOTE: Currently, only TAB indentation is supported
|
@@ -30,6 +31,7 @@ export indentation = (level) ->
|
|
30
31
|
|
31
32
|
# ---------------------------------------------------------------------------
|
32
33
|
# indentLevel - determine indent level of a string
|
34
|
+
# it's OK if the string is ONLY indentation
|
33
35
|
|
34
36
|
export indentLevel = (str) ->
|
35
37
|
|
@@ -51,9 +53,9 @@ export indented = (input, level=0) ->
|
|
51
53
|
"#{toAdd}#{line}"
|
52
54
|
return lLines
|
53
55
|
else
|
54
|
-
lLines = for line in
|
56
|
+
lLines = for line in blockToArray(input)
|
55
57
|
"#{toAdd}#{line}"
|
56
|
-
return
|
58
|
+
return arrayToBlock(lLines)
|
57
59
|
|
58
60
|
# ---------------------------------------------------------------------------
|
59
61
|
# undented - string with 1st line indentation removed for each line
|
@@ -67,7 +69,7 @@ export undented = (text, level=undef) ->
|
|
67
69
|
return text
|
68
70
|
|
69
71
|
if isString(text)
|
70
|
-
lLines =
|
72
|
+
lLines = blockToArray(text)
|
71
73
|
if (lLines.length == 0)
|
72
74
|
return ''
|
73
75
|
else if isArray(text)
|
@@ -97,7 +99,7 @@ export undented = (text, level=undef) ->
|
|
97
99
|
lNewLines.push(line.substr(nToRemove))
|
98
100
|
|
99
101
|
if isString(text)
|
100
|
-
return
|
102
|
+
return arrayToBlock(lNewLines)
|
101
103
|
else
|
102
104
|
return lNewLines
|
103
105
|
|
@@ -109,7 +111,7 @@ export undented = (text, level=undef) ->
|
|
109
111
|
export tabify = (str, numSpaces=undef) ->
|
110
112
|
|
111
113
|
lLines = []
|
112
|
-
for str in
|
114
|
+
for str in blockToArray(str)
|
113
115
|
lMatches = str.match(/^(\s*)(.*)$/)
|
114
116
|
[_, prefix, theRest] = lMatches
|
115
117
|
if prefix == ''
|
@@ -123,7 +125,7 @@ export tabify = (str, numSpaces=undef) ->
|
|
123
125
|
if (n % numSpaces != 0)
|
124
126
|
error "tabify(): Invalid # of leading space chars"
|
125
127
|
lLines.push '\t'.repeat(n / numSpaces) + theRest
|
126
|
-
return
|
128
|
+
return arrayToBlock(lLines)
|
127
129
|
|
128
130
|
# ---------------------------------------------------------------------------
|
129
131
|
# untabify - convert leading TABs to spaces
|
@@ -132,11 +134,11 @@ export untabify = (str, numSpaces=3) ->
|
|
132
134
|
|
133
135
|
oneIndent = ' '.repeat(numSpaces)
|
134
136
|
lLines = []
|
135
|
-
for str in
|
137
|
+
for str in blockToArray(str)
|
136
138
|
lMatches = str.match(/^(\t*)(.*)$/)
|
137
139
|
[_, prefix, theRest] = lMatches
|
138
140
|
if prefix == ''
|
139
141
|
lLines.push theRest
|
140
142
|
else
|
141
143
|
lLines.push oneIndent.repeat(prefix.length) + theRest
|
142
|
-
return
|
144
|
+
return arrayToBlock(lLines)
|
package/src/indent_utils.js
CHANGED
@@ -7,8 +7,6 @@ import {
|
|
7
7
|
import {
|
8
8
|
undef,
|
9
9
|
error,
|
10
|
-
arrayToString,
|
11
|
-
stringToArray,
|
12
10
|
escapeStr,
|
13
11
|
oneline,
|
14
12
|
isInteger,
|
@@ -18,6 +16,11 @@ import {
|
|
18
16
|
rtrim
|
19
17
|
} from '@jdeighan/coffee-utils';
|
20
18
|
|
19
|
+
import {
|
20
|
+
arrayToBlock,
|
21
|
+
blockToArray
|
22
|
+
} from '@jdeighan/coffee-utils/block';
|
23
|
+
|
21
24
|
// ---------------------------------------------------------------------------
|
22
25
|
// NOTE: Currently, only TAB indentation is supported
|
23
26
|
// ---------------------------------------------------------------------------
|
@@ -41,6 +44,7 @@ export var indentation = function(level) {
|
|
41
44
|
|
42
45
|
// ---------------------------------------------------------------------------
|
43
46
|
// indentLevel - determine indent level of a string
|
47
|
+
// it's OK if the string is ONLY indentation
|
44
48
|
export var indentLevel = function(str) {
|
45
49
|
var lMatches;
|
46
50
|
lMatches = str.match(/^\t*/);
|
@@ -70,7 +74,7 @@ export var indented = function(input, level = 0) {
|
|
70
74
|
} else {
|
71
75
|
lLines = (function() {
|
72
76
|
var i, len, ref, results;
|
73
|
-
ref =
|
77
|
+
ref = blockToArray(input);
|
74
78
|
results = [];
|
75
79
|
for (i = 0, len = ref.length; i < len; i++) {
|
76
80
|
line = ref[i];
|
@@ -78,7 +82,7 @@ export var indented = function(input, level = 0) {
|
|
78
82
|
}
|
79
83
|
return results;
|
80
84
|
})();
|
81
|
-
return
|
85
|
+
return arrayToBlock(lLines);
|
82
86
|
}
|
83
87
|
};
|
84
88
|
|
@@ -93,7 +97,7 @@ export var undented = function(text, level = undef) {
|
|
93
97
|
return text;
|
94
98
|
}
|
95
99
|
if (isString(text)) {
|
96
|
-
lLines =
|
100
|
+
lLines = blockToArray(text);
|
97
101
|
if (lLines.length === 0) {
|
98
102
|
return '';
|
99
103
|
}
|
@@ -125,7 +129,7 @@ export var undented = function(text, level = undef) {
|
|
125
129
|
}
|
126
130
|
}
|
127
131
|
if (isString(text)) {
|
128
|
-
return
|
132
|
+
return arrayToBlock(lNewLines);
|
129
133
|
} else {
|
130
134
|
return lNewLines;
|
131
135
|
}
|
@@ -138,7 +142,7 @@ export var undented = function(text, level = undef) {
|
|
138
142
|
export var tabify = function(str, numSpaces = undef) {
|
139
143
|
var _, i, lLines, lMatches, len, n, prefix, ref, theRest;
|
140
144
|
lLines = [];
|
141
|
-
ref =
|
145
|
+
ref = blockToArray(str);
|
142
146
|
for (i = 0, len = ref.length; i < len; i++) {
|
143
147
|
str = ref[i];
|
144
148
|
lMatches = str.match(/^(\s*)(.*)$/);
|
@@ -159,7 +163,7 @@ export var tabify = function(str, numSpaces = undef) {
|
|
159
163
|
lLines.push('\t'.repeat(n / numSpaces) + theRest);
|
160
164
|
}
|
161
165
|
}
|
162
|
-
return
|
166
|
+
return arrayToBlock(lLines);
|
163
167
|
};
|
164
168
|
|
165
169
|
// ---------------------------------------------------------------------------
|
@@ -168,7 +172,7 @@ export var untabify = function(str, numSpaces = 3) {
|
|
168
172
|
var _, i, lLines, lMatches, len, oneIndent, prefix, ref, theRest;
|
169
173
|
oneIndent = ' '.repeat(numSpaces);
|
170
174
|
lLines = [];
|
171
|
-
ref =
|
175
|
+
ref = blockToArray(str);
|
172
176
|
for (i = 0, len = ref.length; i < len; i++) {
|
173
177
|
str = ref[i];
|
174
178
|
lMatches = str.match(/^(\t*)(.*)$/);
|
@@ -179,5 +183,5 @@ export var untabify = function(str, numSpaces = 3) {
|
|
179
183
|
lLines.push(oneIndent.repeat(prefix.length) + theRest);
|
180
184
|
}
|
181
185
|
}
|
182
|
-
return
|
186
|
+
return arrayToBlock(lLines);
|
183
187
|
};
|
package/src/log_utils.coffee
CHANGED
@@ -4,9 +4,9 @@ import {strict as assert} from 'assert'
|
|
4
4
|
import yaml from 'js-yaml'
|
5
5
|
|
6
6
|
import {
|
7
|
-
undef, isNumber, isString, isHash, isFunction,
|
8
|
-
escapeStr, stringToArray,
|
7
|
+
undef, isNumber, isString, isHash, isFunction, escapeStr,
|
9
8
|
} from '@jdeighan/coffee-utils'
|
9
|
+
import {blockToArray} from '@jdeighan/coffee-utils/block'
|
10
10
|
import {tabify} from '@jdeighan/coffee-utils/indent'
|
11
11
|
|
12
12
|
logger = console.log # for strings
|
@@ -120,7 +120,7 @@ export log = (lArgs...) ->
|
|
120
120
|
logger "#{prefix}#{str} = '#{esc}'"
|
121
121
|
else
|
122
122
|
logger "#{prefix}#{str}:"
|
123
|
-
for line in
|
123
|
+
for line in blockToArray(item)
|
124
124
|
logger "#{itemPrefix} #{escapeStr(line)}"
|
125
125
|
else
|
126
126
|
# --- It's some type of object
|
@@ -129,7 +129,7 @@ export log = (lArgs...) ->
|
|
129
129
|
logger "#{prefix}#{str} = #{json}"
|
130
130
|
else
|
131
131
|
logger "#{prefix}#{str}:"
|
132
|
-
for str in
|
132
|
+
for str in blockToArray(stringify(item))
|
133
133
|
logger "#{itemPrefix} #{str}"
|
134
134
|
return
|
135
135
|
|
package/src/log_utils.js
CHANGED
@@ -14,10 +14,13 @@ import {
|
|
14
14
|
isString,
|
15
15
|
isHash,
|
16
16
|
isFunction,
|
17
|
-
escapeStr
|
18
|
-
stringToArray
|
17
|
+
escapeStr
|
19
18
|
} from '@jdeighan/coffee-utils';
|
20
19
|
|
20
|
+
import {
|
21
|
+
blockToArray
|
22
|
+
} from '@jdeighan/coffee-utils/block';
|
23
|
+
|
21
24
|
import {
|
22
25
|
tabify
|
23
26
|
} from '@jdeighan/coffee-utils/indent';
|
@@ -133,7 +136,7 @@ export var log = function(...lArgs) {
|
|
133
136
|
logger(`${prefix}${str} = '${esc}'`);
|
134
137
|
} else {
|
135
138
|
logger(`${prefix}${str}:`);
|
136
|
-
ref =
|
139
|
+
ref = blockToArray(item);
|
137
140
|
for (i = 0, len = ref.length; i < len; i++) {
|
138
141
|
line = ref[i];
|
139
142
|
logger(`${itemPrefix} ${escapeStr(line)}`);
|
@@ -146,7 +149,7 @@ export var log = function(...lArgs) {
|
|
146
149
|
logger(`${prefix}${str} = ${json}`);
|
147
150
|
} else {
|
148
151
|
logger(`${prefix}${str}:`);
|
149
|
-
ref1 =
|
152
|
+
ref1 = blockToArray(stringify(item));
|
150
153
|
for (j = 0, len1 = ref1.length; j < len1; j++) {
|
151
154
|
str = ref1[j];
|
152
155
|
logger(`${itemPrefix} ${str}`);
|