@jsenv/humanize 1.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.
Files changed (79) hide show
  1. package/README.md +35 -0
  2. package/dist/browser/jsenv_humanize_browser.js +1157 -0
  3. package/dist/node/jsenv_humanize_node.js +2003 -0
  4. package/package.json +49 -0
  5. package/src/.jsenv/jsenv_tests_output.txt +35 -0
  6. package/src/_tests/byte/file_size.test.js +18 -0
  7. package/src/_tests/byte/memory_usage.test.js +11 -0
  8. package/src/_tests/content_frame/content_frame.test.js +156 -0
  9. package/src/_tests/content_frame/snapshots/10_line_and_column_are_zero.txt +2 -0
  10. package/src/_tests/content_frame/snapshots/11_line_is_last.txt +3 -0
  11. package/src/_tests/content_frame/snapshots/1_basic.txt +4 -0
  12. package/src/_tests/content_frame/snapshots/2_basic_2.txt +6 -0
  13. package/src/_tests/content_frame/snapshots/3_empty_last_line.txt +7 -0
  14. package/src/_tests/content_frame/snapshots/4_no_column.txt +3 -0
  15. package/src/_tests/content_frame/snapshots/5_line_1_and_2_digits.txt +3 -0
  16. package/src/_tests/content_frame/snapshots/6_line_too_long_column_undefined.txt +3 -0
  17. package/src/_tests/content_frame/snapshots/7_line_too_long_column_near_start.txt +4 -0
  18. package/src/_tests/content_frame/snapshots/8_line_too_long_column_near_middle.txt +4 -0
  19. package/src/_tests/content_frame/snapshots/9_line_too_long_column_near_end.txt +4 -0
  20. package/src/_tests/js_value/_inspect.test.html +22 -0
  21. package/src/_tests/js_value/array.test.js +72 -0
  22. package/src/_tests/js_value/biginit.test.js +36 -0
  23. package/src/_tests/js_value/boolean.test.js +45 -0
  24. package/src/_tests/js_value/date.test.js +15 -0
  25. package/src/_tests/js_value/error.test.js +33 -0
  26. package/src/_tests/js_value/function.test.js +51 -0
  27. package/src/_tests/js_value/instance.test.js +12 -0
  28. package/src/_tests/js_value/null.test.js +6 -0
  29. package/src/_tests/js_value/number.test.js +182 -0
  30. package/src/_tests/js_value/object.test.js +173 -0
  31. package/src/_tests/js_value/regexp.test.js +14 -0
  32. package/src/_tests/js_value/string.test.js +106 -0
  33. package/src/_tests/js_value/symbol.test.js +20 -0
  34. package/src/_tests/js_value/undefined.test.js +6 -0
  35. package/src/_tests/log/log_long.test.mjs +39 -0
  36. package/src/_tests/log/log_modified.test.mjs +7 -0
  37. package/src/_tests/log/logger.test.mjs +91 -0
  38. package/src/_tests/log/spinner.duration.test_manual.mjs +25 -0
  39. package/src/_tests/log/spinner.test.mjs +33 -0
  40. package/src/_tests/log/spinner.test_manual.mjs +15 -0
  41. package/src/_tests/percentage/percentage_distribution.test.mjs +89 -0
  42. package/src/_tests/time/decimals.test.js +119 -0
  43. package/src/_tests/time/duration.test.js +20 -0
  44. package/src/_tests/time/ellapsed.test.js +10 -0
  45. package/src/byte/byte.js +44 -0
  46. package/src/content_frame/content_frame.js +157 -0
  47. package/src/js_value/array.js +58 -0
  48. package/src/js_value/bigint.js +3 -0
  49. package/src/js_value/bigint_object.js +5 -0
  50. package/src/js_value/boolean.js +1 -0
  51. package/src/js_value/boolean_object.js +12 -0
  52. package/src/js_value/constructor.js +10 -0
  53. package/src/js_value/date.js +8 -0
  54. package/src/js_value/error.js +34 -0
  55. package/src/js_value/function.js +20 -0
  56. package/src/js_value/humanize.js +140 -0
  57. package/src/js_value/null.js +1 -0
  58. package/src/js_value/number.js +101 -0
  59. package/src/js_value/number_object.js +9 -0
  60. package/src/js_value/object.js +78 -0
  61. package/src/js_value/regexp.js +1 -0
  62. package/src/js_value/string.js +141 -0
  63. package/src/js_value/string_object.js +10 -0
  64. package/src/js_value/symbol.js +24 -0
  65. package/src/js_value/undefined.js +1 -0
  66. package/src/log/LOG_LEVELS.js +9 -0
  67. package/src/log/ansi.js +37 -0
  68. package/src/log/detailed_message.js +17 -0
  69. package/src/log/dynamic_log.js +185 -0
  70. package/src/log/logger.js +85 -0
  71. package/src/log/spinner.js +72 -0
  72. package/src/log/task_log.js +46 -0
  73. package/src/log/unicode.js +52 -0
  74. package/src/main_browser.js +10 -0
  75. package/src/main_node.js +18 -0
  76. package/src/percentage/distribute_percentages.js +53 -0
  77. package/src/time/time.js +151 -0
  78. package/src/utils/decimals.js +95 -0
  79. package/src/utils/indentation.js +38 -0
@@ -0,0 +1,182 @@
1
+ // https://github.com/sindresorhus/eslint-plugin-unicorn/blob/main/test/numeric-separators-style.mjs
2
+
3
+ import { assert } from "@jsenv/assert";
4
+ import { humanize } from "@jsenv/humanize";
5
+
6
+ {
7
+ const actual = humanize(0);
8
+ const expected = "0";
9
+ assert({ actual, expected });
10
+ }
11
+
12
+ {
13
+ const actual = humanize(1);
14
+ const expected = "1";
15
+ assert({ actual, expected });
16
+ }
17
+
18
+ {
19
+ const actual = humanize(-0);
20
+ const expected = "-0";
21
+ assert({ actual, expected });
22
+ }
23
+
24
+ {
25
+ const actual = humanize(NaN);
26
+ const expected = "NaN";
27
+ assert({ actual, expected });
28
+ }
29
+
30
+ {
31
+ const actual = humanize(Infinity);
32
+ const expected = "Infinity";
33
+ assert({ actual, expected });
34
+ }
35
+
36
+ {
37
+ const actual = humanize(-Infinity);
38
+ const expected = "-Infinity";
39
+ assert({ actual, expected });
40
+ }
41
+
42
+ {
43
+ // eslint-disable-next-line no-new-wrappers
44
+ const actual = humanize(new Number(0));
45
+ const expected = "Number(0)";
46
+ assert({ actual, expected });
47
+ }
48
+
49
+ {
50
+ // eslint-disable-next-line no-new-wrappers
51
+ const actual = humanize(new Number(0), { parenthesis: true });
52
+ const expected = "(Number(0))";
53
+ assert({ actual, expected });
54
+ }
55
+
56
+ {
57
+ // eslint-disable-next-line no-new-wrappers
58
+ const actual = humanize(new Number(0), { useNew: true });
59
+ const expected = "new Number(0)";
60
+ assert({ actual, expected });
61
+ }
62
+
63
+ {
64
+ // eslint-disable-next-line no-new-wrappers
65
+ const actual = humanize(new Number(0), { parenthesis: true, useNew: true });
66
+ const expected = "new (Number(0))";
67
+ assert({ actual, expected });
68
+ }
69
+
70
+ // numeric separator - numbers
71
+ {
72
+ const actual = humanize(1235);
73
+ const expected = "1235";
74
+ assert({ actual, expected });
75
+ }
76
+
77
+ {
78
+ const actual = humanize(67000);
79
+ const expected = "67_000";
80
+ assert({ actual, expected });
81
+ }
82
+
83
+ {
84
+ const actual = humanize(149600000);
85
+ const expected = "149_600_000";
86
+ assert({ actual, expected });
87
+ }
88
+
89
+ {
90
+ const actual = humanize(1_464_301);
91
+ const expected = "1_464_301";
92
+ assert({ actual, expected });
93
+ }
94
+
95
+ // decimal
96
+ {
97
+ const actual = humanize(1234.56);
98
+ const expected = "1234.56";
99
+ assert({ actual, expected });
100
+ }
101
+
102
+ {
103
+ const actual = humanize(12345.67);
104
+ const expected = "12_345.67";
105
+ assert({ actual, expected });
106
+ }
107
+
108
+ {
109
+ const actual = humanize(-0.120123);
110
+ const expected = "-0.120123";
111
+ assert({ actual, expected });
112
+ }
113
+
114
+ // negative
115
+ {
116
+ const actual = humanize(-1000001);
117
+ const expected = "-1_000_001";
118
+ assert({ actual, expected });
119
+ }
120
+
121
+ // exponential
122
+ {
123
+ const actual = humanize(-1.23456e105);
124
+ const expected = "-1.23456e+105";
125
+ assert({ actual, expected });
126
+ }
127
+
128
+ {
129
+ const actual = humanize(-1200000e5);
130
+ const expected = "-120_000_000_000";
131
+ assert({ actual, expected });
132
+ }
133
+
134
+ {
135
+ // prettier-ignore
136
+ const actual = humanize(3.65432E12)
137
+ const expected = "3_654_320_000_000";
138
+ assert({ actual, expected });
139
+ }
140
+
141
+ // numeric separator - binary
142
+ {
143
+ const actual = humanize(0b10101010101010);
144
+ const expected = "10_922";
145
+ assert({ actual, expected });
146
+ }
147
+
148
+ {
149
+ // prettier-ignore
150
+ const actual = humanize(0B10101010101010)
151
+ const expected = "10_922";
152
+ assert({ actual, expected });
153
+ }
154
+
155
+ // numeric separator - hexadecimal
156
+ {
157
+ const actual = humanize(0xfabf00d);
158
+ const expected = "262_926_349";
159
+ assert({ actual, expected });
160
+ }
161
+
162
+ {
163
+ // prettier-ignore
164
+ const actual = humanize(0xABCDEF)
165
+ // prettier-ignore
166
+ const expected = "11_259_375"
167
+ assert({ actual, expected });
168
+ }
169
+
170
+ // numeric separator - octal
171
+ {
172
+ const actual = humanize(0o010101010101);
173
+ const expected = "1_090_785_345";
174
+ assert({ actual, expected });
175
+ }
176
+
177
+ {
178
+ // prettier-ignore
179
+ const actual = humanize(0O010101010101)
180
+ const expected = "1_090_785_345";
181
+ assert({ actual, expected });
182
+ }
@@ -0,0 +1,173 @@
1
+ import { assert } from "@jsenv/assert";
2
+ import { humanize } from "@jsenv/humanize";
3
+
4
+ {
5
+ const actual = humanize({});
6
+ const expected = "{}";
7
+ assert({ actual, expected });
8
+ }
9
+
10
+ {
11
+ // eslint-disable-next-line no-new-object
12
+ const actual = humanize(new Object({}));
13
+ const expected = "{}";
14
+ assert({ actual, expected });
15
+ }
16
+
17
+ {
18
+ const actual = humanize({}, { objectConstructor: true });
19
+ const expected = "Object({})";
20
+ assert({ actual, expected });
21
+ }
22
+
23
+ {
24
+ const actual = humanize(
25
+ { foo: true },
26
+ { objectConstructor: true, useNew: true },
27
+ );
28
+ const expected = `new Object({
29
+ "foo": true
30
+ })`;
31
+ assert({
32
+ actual,
33
+ expected,
34
+ });
35
+ }
36
+
37
+ {
38
+ const actual = humanize({ 0: "foo" });
39
+ const expected = `{
40
+ 0: "foo"
41
+ }`;
42
+ assert({ actual, expected });
43
+ }
44
+
45
+ {
46
+ const actual = humanize({ Infinity: "foo" });
47
+ const expected = `{
48
+ "Infinity": "foo"
49
+ }`;
50
+ assert({ actual, expected });
51
+ }
52
+
53
+ {
54
+ const actual = humanize({ name: "dam" }, { quote: "'" });
55
+ const expected = `{
56
+ 'name': 'dam'
57
+ }`;
58
+ assert({ actual, expected });
59
+ }
60
+
61
+ {
62
+ const actual = humanize(
63
+ { foo: true, nested: { bar: true } },
64
+ { parenthesis: true },
65
+ );
66
+ const expected = `({
67
+ "foo": true,
68
+ "nested": ({
69
+ "bar": true
70
+ })
71
+ })`;
72
+ assert({ actual, expected });
73
+ }
74
+
75
+ {
76
+ const foo = { foo: true, bar: false };
77
+
78
+ const actual = humanize(foo);
79
+ const expected = `{
80
+ "foo": true,
81
+ "bar": false
82
+ }`;
83
+ assert({ actual, expected });
84
+ }
85
+
86
+ {
87
+ const actual = humanize(
88
+ Object.create({
89
+ foo: true,
90
+ }),
91
+ );
92
+ const expected = "{}";
93
+ assert({ actual, expected });
94
+ }
95
+
96
+ {
97
+ const nested = { foo: { name: "dam" } };
98
+ const actual = humanize(nested);
99
+ const expected = `{
100
+ "foo": {
101
+ "name": "dam"
102
+ }
103
+ }`;
104
+ assert({ actual, expected });
105
+ }
106
+
107
+ {
108
+ const circularObject = {
109
+ foo: true,
110
+ };
111
+ circularObject.self = circularObject;
112
+ const actual = humanize(circularObject);
113
+ const expected = `{
114
+ "foo": true,
115
+ "self": Symbol.for('circular')
116
+ }`;
117
+ assert({ actual, expected });
118
+ }
119
+
120
+ {
121
+ const nestedCircularObject = {
122
+ foo: true,
123
+ };
124
+ nestedCircularObject.nested = {
125
+ bar: true,
126
+ parent: nestedCircularObject,
127
+ };
128
+ const actual = humanize(nestedCircularObject);
129
+ const expected = `{
130
+ "foo": true,
131
+ "nested": {
132
+ "bar": true,
133
+ "parent": Symbol.for('circular')
134
+ }
135
+ }`;
136
+ assert({ actual, expected });
137
+ }
138
+
139
+ {
140
+ const actual = humanize(Object.create(null));
141
+ const expected = "{}";
142
+ assert({ actual, expected });
143
+ }
144
+
145
+ {
146
+ const object = Object.create(null);
147
+ object[Symbol.toStringTag] = "stuff";
148
+ const actual = humanize(object);
149
+ const expected = `{
150
+ [Symbol("Symbol.toStringTag")]: "stuff"
151
+ }`;
152
+ assert({ actual, expected });
153
+ }
154
+
155
+ {
156
+ const object = Object.create(null);
157
+ object[Symbol.toStringTag] = "stuff";
158
+ object.foo = true;
159
+ const actual = humanize(object);
160
+ const expected = `{
161
+ "foo": true,
162
+ [Symbol("Symbol.toStringTag")]: "stuff"
163
+ }`;
164
+ assert({ actual, expected });
165
+ }
166
+
167
+ {
168
+ const actual = humanize({ [Symbol()]: true });
169
+ const expected = `{
170
+ [Symbol()]: true
171
+ }`;
172
+ assert({ actual, expected });
173
+ }
@@ -0,0 +1,14 @@
1
+ import { assert } from "@jsenv/assert";
2
+ import { humanize } from "@jsenv/humanize";
3
+
4
+ {
5
+ const actual = humanize(/ok/g);
6
+ const expected = "/ok/g";
7
+ assert({ actual, expected });
8
+ }
9
+
10
+ {
11
+ const actual = humanize(new RegExp("foo", "g"));
12
+ const expected = "/foo/g";
13
+ assert({ actual, expected });
14
+ }
@@ -0,0 +1,106 @@
1
+ import { assert } from "@jsenv/assert";
2
+ import { humanize } from "@jsenv/humanize";
3
+
4
+ {
5
+ const actual = humanize(String.fromCharCode(127));
6
+ const expected = `"\\x7F"`;
7
+ assert({ actual, expected });
8
+ }
9
+
10
+ {
11
+ const actual = humanize("");
12
+ const expected = `""`;
13
+ assert({ actual, expected });
14
+ }
15
+
16
+ {
17
+ const actual = humanize("dam");
18
+ const expected = `"dam"`;
19
+ assert({ actual, expected });
20
+ }
21
+
22
+ {
23
+ const actual = humanize("don't");
24
+ const expected = `"don't"`;
25
+ assert({ actual, expected });
26
+ }
27
+
28
+ {
29
+ const actual = humanize("don't", { quote: "'" });
30
+ const expected = `'don\\\'t'`;
31
+ assert({ actual, expected });
32
+ }
33
+
34
+ {
35
+ const actual = humanize(`his name is "dam"`);
36
+ const expected = `'his name is "dam"'`;
37
+ assert({ actual, expected });
38
+ }
39
+
40
+ {
41
+ const actual = humanize(`his name is "dam"`, { quote: "'" });
42
+ const expected = `'his name is "dam"'`;
43
+ assert({ actual, expected });
44
+ }
45
+
46
+ {
47
+ const actual = humanize("a\nb");
48
+ const expected = `"a\\nb"`;
49
+ assert({ actual, expected });
50
+ }
51
+
52
+ {
53
+ const actual = humanize("a\rb");
54
+ const expected = `"a\\rb"`;
55
+ assert({ actual, expected });
56
+ }
57
+
58
+ {
59
+ const actual = humanize("a\u2028b");
60
+ const expected = `"a\\u2028b"`;
61
+ assert({ actual, expected });
62
+ }
63
+
64
+ {
65
+ const actual = humanize("a\u2029b");
66
+ const expected = `"a\\u2029b"`;
67
+ assert({ actual, expected });
68
+ }
69
+
70
+ {
71
+ // eslint-disable-next-line no-new-wrappers
72
+ const actual = humanize(new String(""));
73
+ const expected = `String("")`;
74
+ assert({
75
+ actual,
76
+ expected,
77
+ });
78
+ }
79
+
80
+ {
81
+ // eslint-disable-next-line no-new-wrappers
82
+ const actual = humanize(new String("dam"));
83
+ const expected = `String("dam")`;
84
+ assert({
85
+ actual,
86
+ expected,
87
+ });
88
+ }
89
+
90
+ {
91
+ const actual = humanize("dam", { quote: "'" });
92
+ const expected = `'dam'`;
93
+ assert({ actual, expected });
94
+ }
95
+
96
+ {
97
+ const actual = humanize(`\`"'`);
98
+ const expected = `"\`\\\"'"`;
99
+ assert({ actual, expected });
100
+ }
101
+
102
+ {
103
+ const actual = humanize(`""''`);
104
+ const expected = `\`""''\``;
105
+ assert({ actual, expected });
106
+ }
@@ -0,0 +1,20 @@
1
+ import { assert } from "@jsenv/assert";
2
+ import { humanize } from "@jsenv/humanize";
3
+
4
+ {
5
+ const actual = humanize(Symbol());
6
+ const expected = "Symbol()";
7
+ assert({ actual, expected });
8
+ }
9
+
10
+ {
11
+ const actual = humanize(Symbol("foo"));
12
+ const expected = `Symbol("foo")`;
13
+ assert({ actual, expected });
14
+ }
15
+
16
+ {
17
+ const actual = humanize(Symbol(42));
18
+ const expected = `Symbol("42")`;
19
+ assert({ actual, expected });
20
+ }
@@ -0,0 +1,6 @@
1
+ import { assert } from "@jsenv/assert";
2
+ import { humanize } from "@jsenv/humanize";
3
+
4
+ const actual = humanize(undefined);
5
+ const expected = "undefined";
6
+ assert({ actual, expected });
@@ -0,0 +1,39 @@
1
+ // must be verfied by human eyes
2
+ // depending on terminal height
3
+ // either the whole log can be rewritten (updated)
4
+ // or it will be kept and second log appended at the bottom
5
+
6
+ import { createDynamicLog } from "@jsenv/humanize";
7
+
8
+ const log = createDynamicLog();
9
+ log.update(`
10
+ 1
11
+ 2
12
+ 3
13
+ 4
14
+ 5
15
+ 6
16
+ 7
17
+ 8
18
+ 9
19
+ 10
20
+ 11
21
+ 12
22
+ 13
23
+ 14
24
+ 15
25
+ 16
26
+ 17
27
+ 18`);
28
+ log.update(`
29
+ a
30
+ b
31
+ c
32
+ d
33
+ e
34
+ f
35
+ g`);
36
+ log.update(`
37
+ alpha
38
+ beta
39
+ gamma`);
@@ -0,0 +1,7 @@
1
+ import { createDynamicLog } from "@jsenv/humanize";
2
+
3
+ const dynamicLog = createDynamicLog();
4
+ dynamicLog.update("hello");
5
+ console.log("hey");
6
+ dynamicLog.update("world");
7
+ dynamicLog.update("!");
@@ -0,0 +1,91 @@
1
+ import { assert } from "@jsenv/assert";
2
+
3
+ import { createLogger } from "@jsenv/humanize";
4
+
5
+ try {
6
+ createLogger({ logLevel: "foo" });
7
+ throw new Error("should throw");
8
+ } catch (actual) {
9
+ const expected = new Error(`unexpected logLevel.
10
+ --- logLevel ---
11
+ foo
12
+ --- allowed log levels ---
13
+ off
14
+ error
15
+ warn
16
+ info
17
+ debug`);
18
+ assert({ actual, expected });
19
+ }
20
+
21
+ {
22
+ const logger = createLogger();
23
+ const actual = logger.levels;
24
+ const expected = {
25
+ debug: false,
26
+ info: true,
27
+ warn: true,
28
+ error: true,
29
+ };
30
+ assert({ actual, expected });
31
+ }
32
+
33
+ {
34
+ const logger = createLogger({ logLevel: "off" });
35
+ const actual = logger.levels;
36
+ const expected = {
37
+ debug: false,
38
+ info: false,
39
+ warn: false,
40
+ error: false,
41
+ };
42
+ assert({ actual, expected });
43
+ }
44
+
45
+ {
46
+ const logger = createLogger({ logLevel: "debug" });
47
+ const actual = logger.levels;
48
+ const expected = {
49
+ debug: true,
50
+ info: true,
51
+ warn: true,
52
+ error: true,
53
+ };
54
+ assert({ actual, expected });
55
+ }
56
+
57
+ {
58
+ const logger = createLogger({ logLevel: "info" });
59
+ const actual = logger.levels;
60
+ const expected = {
61
+ debug: false,
62
+ info: true,
63
+ warn: true,
64
+ error: true,
65
+ };
66
+ assert({ actual, expected });
67
+ }
68
+
69
+ {
70
+ const logger = createLogger({ logLevel: "warn" });
71
+ const actual = logger.levels;
72
+ const expected = {
73
+ debug: false,
74
+ info: false,
75
+ warn: true,
76
+ error: true,
77
+ };
78
+ assert({ actual, expected });
79
+ }
80
+
81
+ {
82
+ const logger = createLogger({ logLevel: "error" });
83
+ const actual = logger.levels;
84
+ const expected = {
85
+ debug: false,
86
+ info: false,
87
+ warn: false,
88
+ error: true,
89
+ };
90
+ assert({ actual, expected });
91
+ }
@@ -0,0 +1,25 @@
1
+ import { createDynamicLog, startSpinner } from "@jsenv/humanize";
2
+
3
+ const dynamicLog = createDynamicLog();
4
+ const startMs = Date.now();
5
+ let msDuration = 0;
6
+ let text = "Doing something";
7
+ const spinner = startSpinner({
8
+ dynamicLog,
9
+ render: () => text,
10
+ effect: () => {
11
+ const intervalId = setInterval(() => {
12
+ msDuration = Date.now() - startMs;
13
+ text = `Doing something ${msDuration} ms`;
14
+ }, 100);
15
+ return () => {
16
+ clearInterval(intervalId);
17
+ };
18
+ },
19
+ });
20
+ await new Promise((resolve) => setTimeout(resolve, 2500));
21
+
22
+ spinner.stop("Done");
23
+ console.log(`Done in ${msDuration} ms`);
24
+
25
+ await new Promise((resolve) => setTimeout(resolve, 500));
@@ -0,0 +1,33 @@
1
+ // import { assert } from "@jsenv/assert"
2
+
3
+ // import { startSpinner } from "@jsenv/humanize"
4
+ // import { spyStreamOutput } from "@jsenv/humanize/src/internal/spy_stream_output.js"
5
+
6
+ // let getOutput = spyStreamOutput(process.stdout)
7
+ // startSpinner({
8
+ // frames: ["a", "b"],
9
+ // text: "loading",
10
+ // fps: 1,
11
+ // })
12
+
13
+ // {
14
+ // const actual = getOutput()
15
+ // const expected = `a loading\n`
16
+ // assert({ actual, expected })
17
+ // }
18
+ // getOutput = spyStreamOutput(process.stdout)
19
+ // await new Promise((resolve) => setTimeout(resolve, 1500))
20
+
21
+ // {
22
+ // const actual = getOutput()
23
+ // const expected = `b loading\n`
24
+ // assert({ actual, expected })
25
+ // }
26
+ // getOutput = spyStreamOutput(process.stdout)
27
+ // await new Promise((resolve) => setTimeout(resolve, 1500))
28
+
29
+ // {
30
+ // const actual = getOutput()
31
+ // const expected = `a loading\n`
32
+ // assert({ actual, expected })
33
+ // }
@@ -0,0 +1,15 @@
1
+ import { createDynamicLog, startSpinner } from "@jsenv/humanize";
2
+
3
+ const dynamicLog = createDynamicLog();
4
+ const spinner = startSpinner({
5
+ dynamicLog,
6
+ render: () => "Loading and I would say even more",
7
+ stopOnWriteFromOutside: true,
8
+ });
9
+
10
+ await new Promise((resolve) => setTimeout(resolve, 2500));
11
+
12
+ dynamicLog.update("Hey");
13
+ spinner.stop();
14
+
15
+ await new Promise((resolve) => setTimeout(resolve, 500));