@vbarbarosh/node-helpers 3.66.1 → 3.68.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/README.md +2 -2
- package/dist/browser.js +603 -141
- package/package.json +3 -1
- package/src/HeartbeatServer.js +99 -0
- package/src/_finally.js +8 -0
- package/src/_finally.md +19 -0
- package/src/_perf.js +18 -0
- package/src/_perf.md +13 -0
- package/src/_restore.js +16 -0
- package/src/_restore.md +21 -0
- package/src/_try.js +11 -0
- package/src/_try.md +5 -0
- package/src/array_group.js +11 -7
- package/src/array_index.js +3 -1
- package/src/array_max.js +8 -14
- package/src/array_max.md +1 -0
- package/src/array_max.test.js +8 -0
- package/src/array_min.js +8 -14
- package/src/array_min.md +1 -0
- package/src/array_min.test.js +8 -0
- package/src/array_shuffle.md +5 -0
- package/src/array_sort.js +21 -12
- package/src/array_sort.test.js +78 -3
- package/src/array_sort_other.js +2 -2
- package/src/array_unique.js +9 -3
- package/src/array_unique.md +1 -0
- package/src/array_unique_last.js +7 -14
- package/src/array_unique_last.md +1 -0
- package/src/browser/index.js +15 -7
- package/src/countdown.js +1 -1
- package/src/fastdl.md +8 -0
- package/src/fcmp_default.js +12 -0
- package/src/fcmp_default_desc.js +12 -0
- package/src/fcmp_from_spec.js +2 -0
- package/src/fcmp_numbers.js +1 -1
- package/src/fcmp_tuples.js +15 -0
- package/src/fcmp_utf8_bin.js +13 -0
- package/src/fcmp_utf8_ci.js +7 -0
- package/src/fcmp_utf8_cs.js +7 -0
- package/src/fcmp_utf8_natural_ci.js +7 -0
- package/src/fcmp_utf8_natural_cs.js +7 -0
- package/src/fcmpx.js +120 -0
- package/src/fcmpx.md +17 -0
- package/src/fcmpx.test.js +173 -0
- package/src/filter1_from_spec.md +7 -0
- package/src/format_date_fs.js +13 -0
- package/src/format_date_human.js +13 -0
- package/src/format_hrtime.md +1 -0
- package/src/format_progress_bytes.js +6 -6
- package/src/format_progress_kilo.js +6 -6
- package/src/fs_fopen_update.md +5 -0
- package/src/fs_list.js +16 -0
- package/src/fs_list_deep.js +20 -0
- package/src/fs_ls.js +3 -0
- package/src/fs_path_extname.js +14 -0
- package/src/fs_path_extname.test.js +22 -0
- package/src/fs_size_enoent.md +3 -0
- package/src/fs_tempdir.md +6 -0
- package/src/now_atom.js +1 -1
- package/src/now_atom.md +1 -0
- package/src/now_fs.js +8 -0
- package/src/now_human.js +8 -0
- package/src/parallel.js +3 -3
- package/src/parallel.md +5 -0
- package/src/pid_exists.js +12 -0
- package/src/pid_kill_grace.js +28 -0
- package/src/ping_socket.js +32 -0
- package/src/ping_socket.md +3 -0
- package/src/plural.js +8 -2
- package/src/plural.test.js +5 -3
- package/src/sanitize_var_name.js +2 -2
- package/src/{camel_to_snake.js → str_camel_to_snake.js} +2 -2
- package/src/{camel_to_snake.test.js → str_camel_to_snake.test.js} +3 -3
- package/src/str_parse_kv.js +10 -0
- package/src/stream_chunk.md +1 -0
- package/src/stream_data_ln.md +1 -0
- package/src/stream_each.md +1 -0
- package/src/stream_filter.md +1 -0
- package/src/stream_lines.md +1 -0
- package/src/stream_map.md +1 -0
- package/src/stream_map_flatten.md +1 -0
- package/src/stream_map_parallel.md +1 -0
- package/src/stream_parse_csv.md +3 -0
- package/src/stream_progress.js +1 -1
- package/src/stream_progress.md +8 -0
- package/src/stream_skip.md +1 -0
- package/src/stream_strpbrk.md +1 -0
- package/src/stream_tap.md +1 -0
- package/src/stream_xml_analyze.md +1 -0
- package/src/stream_xml_parse.md +1 -0
- package/src/throttle.md +3 -0
- package/src/urlclean.js +1 -1
- package/src/urlclean.md +2 -0
- package/src/urlmod.md +7 -0
- package/src/user_friendly_status.md +4 -0
- package/src/wait_while.md +5 -0
- package/src/waitcb.md +12 -0
- package/src/fcmp_strings.js +0 -6
- /package/src/{stream-parse-csv.js → stream_parse_csv.js} +0 -0
package/src/parallel.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
const NotImplemented = require('./errors/NotImplemented');
|
|
2
2
|
const Promise = require('bluebird');
|
|
3
|
-
const
|
|
4
|
-
const
|
|
3
|
+
const is_fn_async = require('@vbarbarosh/type-helpers/src/is_fn_async');
|
|
4
|
+
const is_fn_gen_async = require('@vbarbarosh/type-helpers/src/is_fn_gen_async');
|
|
5
5
|
|
|
6
6
|
/**
|
|
7
7
|
* - Run until `spawn` return `null`.
|
|
@@ -12,7 +12,7 @@ const is_async_generator = require('@vbarbarosh/type-helpers/src/is_async_genera
|
|
|
12
12
|
*/
|
|
13
13
|
async function parallel({concurrency, spawn, progress})
|
|
14
14
|
{
|
|
15
|
-
if (
|
|
15
|
+
if (is_fn_async(spawn) || is_fn_gen_async(spawn)) {
|
|
16
16
|
throw new Error('[spawn] should not be async function. Instead, it should be a simple function returning either [null] or a [promise].');
|
|
17
17
|
}
|
|
18
18
|
const running = [];
|
package/src/parallel.md
ADDED
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
- Run until `spawn` return `null`.
|
|
2
|
+
- Keep no more than `concurrency` number of workers at a time.
|
|
3
|
+
|
|
4
|
+
⚠️ Warning: `spawn` should not be async function (async functions are always return `promise`).
|
|
5
|
+
Instead, it should be a simple function returning either `null` or a `promise`.
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
const Promise = require('bluebird');
|
|
2
|
+
const format_thousands = require('./format_thousands');
|
|
3
|
+
const ignore = require('./ignore');
|
|
4
|
+
const pid_exists = require('./pid_exists');
|
|
5
|
+
|
|
6
|
+
async function pid_kill_grace(pid, {grace_timeout_ms = 5000, log = ignore} = {})
|
|
7
|
+
{
|
|
8
|
+
log('Sending SIGTERM');
|
|
9
|
+
if (!process.kill(pid, 'SIGTERM')) {
|
|
10
|
+
throw new Error('SIGTERM Failed');
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
const end = Date.now() + grace_timeout_ms;
|
|
14
|
+
while (Date.now() < end) {
|
|
15
|
+
if (!pid_exists(pid)) {
|
|
16
|
+
return;
|
|
17
|
+
}
|
|
18
|
+
log(`Process is still there, waiting for 100ms, ${format_thousands(end - Date.now())}ms left`);
|
|
19
|
+
await Promise.delay(100);
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
log('Sending SIGKILL');
|
|
23
|
+
if (!process.kill(pid, 'SIGKILL')) {
|
|
24
|
+
throw new Error('SIGKILL Failed');
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
module.exports = pid_kill_grace;
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
const Promise = require('bluebird');
|
|
2
|
+
const net = require('net');
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* - Always closes the socket.
|
|
6
|
+
* - Throws on any error or timeout.
|
|
7
|
+
* - Doesn’t hang if the server sends nothing.
|
|
8
|
+
*/
|
|
9
|
+
function ping_socket(socket_path, data = 'PING', timeout_ms = 1000)
|
|
10
|
+
{
|
|
11
|
+
return new Promise(function (resolve, reject) {
|
|
12
|
+
let done = false;
|
|
13
|
+
const buf = [];
|
|
14
|
+
const socket = net.connect(socket_path);
|
|
15
|
+
socket.setTimeout(timeout_ms, () => finish(new Error('Socket Timeout')));
|
|
16
|
+
socket.on('end', () => finish(null, Buffer.concat(buf)))
|
|
17
|
+
socket.on('error', finish);
|
|
18
|
+
socket.on('connect', () => socket.end(data));
|
|
19
|
+
socket.on('data', chunk => buf.push(chunk));
|
|
20
|
+
function finish(error, out) {
|
|
21
|
+
if (done) {
|
|
22
|
+
return;
|
|
23
|
+
}
|
|
24
|
+
done = true;
|
|
25
|
+
socket.removeAllListeners();
|
|
26
|
+
socket.destroy();
|
|
27
|
+
error ? reject(error) : resolve(out);
|
|
28
|
+
}
|
|
29
|
+
});
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
module.exports = ping_socket;
|
package/src/plural.js
CHANGED
|
@@ -1,6 +1,12 @@
|
|
|
1
|
-
function plural(n,
|
|
1
|
+
function plural(n, singular, plural, zero)
|
|
2
2
|
{
|
|
3
|
-
|
|
3
|
+
if (n === 0 && typeof zero === 'string') {
|
|
4
|
+
return zero;
|
|
5
|
+
}
|
|
6
|
+
if (n % 10 === 1 && n % 100 !== 11) {
|
|
7
|
+
return singular.split('#').join(n);
|
|
8
|
+
}
|
|
9
|
+
return plural.split('#').join(n);
|
|
4
10
|
}
|
|
5
11
|
|
|
6
12
|
module.exports = plural;
|
package/src/plural.test.js
CHANGED
|
@@ -1,15 +1,17 @@
|
|
|
1
1
|
const assert = require('assert');
|
|
2
2
|
const plural = require('./plural');
|
|
3
3
|
|
|
4
|
-
const
|
|
5
|
-
['1 apple', 1, '# apple', '# apples'
|
|
4
|
+
const tests = [
|
|
5
|
+
['1 apple', 1, '# apple', '# apples'],
|
|
6
6
|
['2 apples', 2, '# apple', '# apples'],
|
|
7
7
|
['10 apples', 10, '# apple', '# apples'],
|
|
8
8
|
['21 apple', 21, '# apple', '# apples'],
|
|
9
|
+
['0 apples', 0, '# apple', '# apples'],
|
|
10
|
+
['No apples', 0, '# apple', '# apples', 'No apples'],
|
|
9
11
|
];
|
|
10
12
|
|
|
11
13
|
describe('plural', function () {
|
|
12
|
-
|
|
14
|
+
tests.forEach(function ([expected, ...args],) {
|
|
13
15
|
it(expected, function () {
|
|
14
16
|
const actual = plural(...args);
|
|
15
17
|
assert.deepStrictEqual(actual, expected);
|
package/src/sanitize_var_name.js
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
const camel_to_snake = require('./camel_to_snake');
|
|
2
1
|
const sanitize_dash_name = require('./sanitize_dash_name');
|
|
2
|
+
const str_camel_to_snake = require('./str_camel_to_snake');
|
|
3
3
|
|
|
4
4
|
function sanitize_var_name(var_name)
|
|
5
5
|
{
|
|
6
|
-
const out = sanitize_dash_name(
|
|
6
|
+
const out = sanitize_dash_name(str_camel_to_snake(var_name)).replace(/[^a-z0-9]+/g, '_');
|
|
7
7
|
if (out.length === 0) {
|
|
8
8
|
return '_';
|
|
9
9
|
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
function
|
|
1
|
+
function str_camel_to_snake(s)
|
|
2
2
|
{
|
|
3
3
|
return s
|
|
4
4
|
.replace(/([a-z0-9])([A-Z])/g, '$1_$2') // Insert underscore between lowercase/number and uppercase
|
|
@@ -6,4 +6,4 @@ function camel_to_snake(s)
|
|
|
6
6
|
.toLowerCase();
|
|
7
7
|
}
|
|
8
8
|
|
|
9
|
-
module.exports =
|
|
9
|
+
module.exports = str_camel_to_snake;
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
const assert = require('assert');
|
|
2
|
-
const
|
|
2
|
+
const str_camel_to_snake = require('./str_camel_to_snake');
|
|
3
3
|
|
|
4
4
|
const items = [
|
|
5
5
|
['UPC', 'upc'],
|
|
@@ -8,10 +8,10 @@ const items = [
|
|
|
8
8
|
['XMLHTTPRequest', 'xmlhttp_request'],
|
|
9
9
|
];
|
|
10
10
|
|
|
11
|
-
describe('
|
|
11
|
+
describe('str_camel_to_snake', function () {
|
|
12
12
|
items.forEach(function ([input, expected],) {
|
|
13
13
|
it(`${input === '' ? '☒' : input} → ${expected}`, function () {
|
|
14
|
-
assert.deepStrictEqual(
|
|
14
|
+
assert.deepStrictEqual(str_camel_to_snake(input), expected);
|
|
15
15
|
});
|
|
16
16
|
});
|
|
17
17
|
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Split a stream into chunks of objects.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Split stream on each `\n` and call `fn` for each line.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Pass each item to a simple function. This is a final step.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Pass down only those items passed user-defined criteria.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Split stream into lines.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Transform each item using a simple function.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Pass each item through a user-defined generator, passes down each yielded item.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Transform each item using a simple function in parallel.
|
package/src/stream_progress.js
CHANGED
|
@@ -7,7 +7,7 @@ const stream = require('stream');
|
|
|
7
7
|
* Monitor the progress of data through a pipe, similar to the UNIX `pv` command.
|
|
8
8
|
*
|
|
9
9
|
* Requirements:
|
|
10
|
-
* - should emit first message as fast as possible
|
|
10
|
+
* - should emit the first message as fast as possible
|
|
11
11
|
* - should always emit 100% message
|
|
12
12
|
*
|
|
13
13
|
* @similar https://www.npmjs.com/package/progress-stream
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Skip first `n` records.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Split the input stream by consecutive delimiters in `chars`.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Call `fn` on each item.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Consume XML, produce an object with analytics about provided xml stream.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Consume XML, produce objects.
|
package/src/throttle.md
ADDED
package/src/urlclean.js
CHANGED
|
@@ -2,7 +2,7 @@ const querystring = require('querystring');
|
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
* Replace unnecessary encodes symbols with chars. The returned url will be
|
|
5
|
-
* more human
|
|
5
|
+
* more human-friendly, at the same time it will still be valid url.
|
|
6
6
|
*/
|
|
7
7
|
function urlclean(url)
|
|
8
8
|
{
|
package/src/urlclean.md
ADDED
package/src/urlmod.md
ADDED
package/src/waitcb.md
ADDED
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
Wait for a Node-like function to finish (which will call `callback`
|
|
2
|
+
with 2 arguments: `error` and `value`).
|
|
3
|
+
|
|
4
|
+
```js
|
|
5
|
+
await waitcb(cb => fs.writeFile('a', 'hello\n', cb));
|
|
6
|
+
```
|
|
7
|
+
|
|
8
|
+
The same as:
|
|
9
|
+
|
|
10
|
+
```js
|
|
11
|
+
const [promise, resolve, reject] = (a => [new Promise((...v) => a = v), ...a])();
|
|
12
|
+
```
|
package/src/fcmp_strings.js
DELETED
|
File without changes
|