@thi.ng/fibers 1.0.2 → 1.0.4
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/CHANGELOG.md +1 -1
- package/README.md +6 -0
- package/csp.js +2 -4
- package/fiber.js +13 -26
- package/ops.js +11 -22
- package/package.json +19 -15
package/CHANGELOG.md
CHANGED
package/README.md
CHANGED
|
@@ -23,6 +23,7 @@
|
|
|
23
23
|
- [Channels](#channels)
|
|
24
24
|
- [CSP ping/pong example](#csp-pingpong-example)
|
|
25
25
|
- [Status](#status)
|
|
26
|
+
- [Related packages](#related-packages)
|
|
26
27
|
- [Installation](#installation)
|
|
27
28
|
- [Dependencies](#dependencies)
|
|
28
29
|
- [Usage examples](#usage-examples)
|
|
@@ -371,6 +372,11 @@ if (res !== undefined) {
|
|
|
371
372
|
|
|
372
373
|
[Search or submit any issues for this package](https://github.com/thi-ng/umbrella/issues?q=%5Bfibers%5D+in%3Atitle)
|
|
373
374
|
|
|
375
|
+
## Related packages
|
|
376
|
+
|
|
377
|
+
- [@thi.ng/csp](https://github.com/thi-ng/umbrella/tree/develop/packages/csp) - Primitives & operators for Communicating Sequential Processes based on async/await and async iterables
|
|
378
|
+
- [@thi.ng/transducers-async](https://github.com/thi-ng/umbrella/tree/develop/packages/transducers-async) - Async versions of various highly composable transducers, reducers and iterators
|
|
379
|
+
|
|
374
380
|
## Installation
|
|
375
381
|
|
|
376
382
|
```bash
|
package/csp.js
CHANGED
|
@@ -84,13 +84,11 @@ class Channel {
|
|
|
84
84
|
close(wait = true) {
|
|
85
85
|
const chan = this;
|
|
86
86
|
return fiber(function* (ctx) {
|
|
87
|
-
if (chan.state >= STATE_CLOSING)
|
|
88
|
-
return;
|
|
87
|
+
if (chan.state >= STATE_CLOSING) return;
|
|
89
88
|
if (wait) {
|
|
90
89
|
ctx.logger?.debug("waiting to close...");
|
|
91
90
|
chan.state = STATE_CLOSING;
|
|
92
|
-
while (chan.buffer.readable())
|
|
93
|
-
yield;
|
|
91
|
+
while (chan.buffer.readable()) yield;
|
|
94
92
|
}
|
|
95
93
|
chan.state = STATE_CLOSED;
|
|
96
94
|
chan.buffer.clear();
|
package/fiber.js
CHANGED
|
@@ -5,8 +5,7 @@ var __decorateClass = (decorators, target, key, kind) => {
|
|
|
5
5
|
for (var i = decorators.length - 1, decorator; i >= 0; i--)
|
|
6
6
|
if (decorator = decorators[i])
|
|
7
7
|
result = (kind ? decorator(target, key, result) : decorator(result)) || result;
|
|
8
|
-
if (kind && result)
|
|
9
|
-
__defProp(target, key, result);
|
|
8
|
+
if (kind && result) __defProp(target, key, result);
|
|
10
9
|
return result;
|
|
11
10
|
};
|
|
12
11
|
import { INotifyMixin } from "@thi.ng/api/mixins/inotify";
|
|
@@ -64,8 +63,7 @@ let Fiber = class {
|
|
|
64
63
|
} else {
|
|
65
64
|
this.idgen = DEFAULT_ID_GEN;
|
|
66
65
|
}
|
|
67
|
-
if (this.idgen)
|
|
68
|
-
this.id = this.idgen.next();
|
|
66
|
+
if (this.idgen) this.id = this.idgen.next();
|
|
69
67
|
this.gen = isFunction(gen) ? gen(this) : gen;
|
|
70
68
|
}
|
|
71
69
|
/**
|
|
@@ -73,8 +71,7 @@ let Fiber = class {
|
|
|
73
71
|
* Then return this fiber's value.
|
|
74
72
|
*/
|
|
75
73
|
*[Symbol.iterator]() {
|
|
76
|
-
while (this.state <= STATE_ACTIVE && this.next() <= STATE_ACTIVE)
|
|
77
|
-
yield;
|
|
74
|
+
while (this.state <= STATE_ACTIVE && this.next() <= STATE_ACTIVE) yield;
|
|
78
75
|
return this.value;
|
|
79
76
|
}
|
|
80
77
|
/**
|
|
@@ -178,8 +175,7 @@ let Fiber = class {
|
|
|
178
175
|
* @param opts
|
|
179
176
|
*/
|
|
180
177
|
fork(body, opts) {
|
|
181
|
-
if (!this.isActive())
|
|
182
|
-
illegalState(`fiber (id: ${this.id}) not active`);
|
|
178
|
+
if (!this.isActive()) illegalState(`fiber (id: ${this.id}) not active`);
|
|
183
179
|
let $fiber;
|
|
184
180
|
if (body instanceof Fiber) {
|
|
185
181
|
if (body.parent)
|
|
@@ -218,8 +214,7 @@ let Fiber = class {
|
|
|
218
214
|
*/
|
|
219
215
|
*join() {
|
|
220
216
|
this.logger?.debug("waiting for children...");
|
|
221
|
-
while (this.children.length)
|
|
222
|
-
yield;
|
|
217
|
+
while (this.children.length) yield;
|
|
223
218
|
}
|
|
224
219
|
/**
|
|
225
220
|
* Processes a single iteration of this fiber and any of its children. Does
|
|
@@ -246,16 +241,14 @@ let Fiber = class {
|
|
|
246
241
|
if (child.state > STATE_ACTIVE || child.next() > STATE_ACTIVE) {
|
|
247
242
|
children.splice(i, 1);
|
|
248
243
|
n--;
|
|
249
|
-
} else
|
|
250
|
-
i++;
|
|
244
|
+
} else i++;
|
|
251
245
|
}
|
|
252
246
|
} else if (this.autoTerminate) {
|
|
253
247
|
this.cancel();
|
|
254
248
|
break;
|
|
255
249
|
}
|
|
256
250
|
const res = this.gen ? this.gen.next(this) : NO_RESULT;
|
|
257
|
-
if (res.done)
|
|
258
|
-
this.done(res.value);
|
|
251
|
+
if (res.done) this.done(res.value);
|
|
259
252
|
} catch (e) {
|
|
260
253
|
this.catch(e);
|
|
261
254
|
}
|
|
@@ -283,11 +276,9 @@ let Fiber = class {
|
|
|
283
276
|
* Function is a no-op if the fiber is not active anymore.
|
|
284
277
|
*/
|
|
285
278
|
cancel() {
|
|
286
|
-
if (!this.isActive())
|
|
287
|
-
return;
|
|
279
|
+
if (!this.isActive()) return;
|
|
288
280
|
this.logger?.debug("cancel", this.id);
|
|
289
|
-
for (let child of this.children)
|
|
290
|
-
child.cancel();
|
|
281
|
+
for (let child of this.children) child.cancel();
|
|
291
282
|
this.deinit();
|
|
292
283
|
this.state = STATE_CANCELED;
|
|
293
284
|
this.idgen?.free(this.id);
|
|
@@ -304,12 +295,10 @@ let Fiber = class {
|
|
|
304
295
|
* @param value
|
|
305
296
|
*/
|
|
306
297
|
done(value) {
|
|
307
|
-
if (!this.isActive())
|
|
308
|
-
return;
|
|
298
|
+
if (!this.isActive()) return;
|
|
309
299
|
this.logger?.debug("done", this.id, value);
|
|
310
300
|
this.value = value;
|
|
311
|
-
for (let child of this.children)
|
|
312
|
-
child.done();
|
|
301
|
+
for (let child of this.children) child.done();
|
|
313
302
|
this.deinit();
|
|
314
303
|
this.state = STATE_DONE;
|
|
315
304
|
this.idgen?.free(this.id);
|
|
@@ -328,11 +317,9 @@ let Fiber = class {
|
|
|
328
317
|
* @param err
|
|
329
318
|
*/
|
|
330
319
|
catch(err) {
|
|
331
|
-
if (this.state >= STATE_ERROR || this.user?.catch?.(this, err))
|
|
332
|
-
return;
|
|
320
|
+
if (this.state >= STATE_ERROR || this.user?.catch?.(this, err)) return;
|
|
333
321
|
this.logger ? this.logger.severe(`error ${this.id}:`, err) : console.warn(`error ${this.id}:`, err);
|
|
334
|
-
for (let child of this.children)
|
|
335
|
-
child.cancel();
|
|
322
|
+
for (let child of this.children) child.cancel();
|
|
336
323
|
this.state = STATE_ERROR;
|
|
337
324
|
this.error = err;
|
|
338
325
|
this.deinit();
|
package/ops.js
CHANGED
|
@@ -10,23 +10,18 @@ import { Fiber, fiber } from "./fiber.js";
|
|
|
10
10
|
const wait = (delay) => delay !== void 0 ? untilPromise(
|
|
11
11
|
new Promise((resolve) => setTimeout(resolve, delay))
|
|
12
12
|
) : fiber(function* () {
|
|
13
|
-
while (true)
|
|
14
|
-
yield;
|
|
13
|
+
while (true) yield;
|
|
15
14
|
});
|
|
16
15
|
function* waitFrames(delay) {
|
|
17
|
-
while (delay-- > 0)
|
|
18
|
-
yield;
|
|
16
|
+
while (delay-- > 0) yield;
|
|
19
17
|
}
|
|
20
18
|
const sequence = (fibers, opts) => fiber(function* (ctx) {
|
|
21
19
|
for (let fiber2 of fibers) {
|
|
22
20
|
const $fiber = ctx.fork(fiber2);
|
|
23
|
-
while ($fiber.isActive())
|
|
24
|
-
|
|
25
|
-
if ($fiber.state === STATE_ERROR)
|
|
26
|
-
throw $fiber.error;
|
|
21
|
+
while ($fiber.isActive()) yield;
|
|
22
|
+
if ($fiber.state === STATE_ERROR) throw $fiber.error;
|
|
27
23
|
ctx.value = $fiber.value;
|
|
28
|
-
if ($fiber.state > STATE_DONE || ctx.state > STATE_ACTIVE)
|
|
29
|
-
break;
|
|
24
|
+
if ($fiber.state > STATE_DONE || ctx.state > STATE_ACTIVE) break;
|
|
30
25
|
}
|
|
31
26
|
return ctx.value;
|
|
32
27
|
}, opts);
|
|
@@ -34,8 +29,7 @@ const first = (fibers, opts) => fiber(function* (ctx) {
|
|
|
34
29
|
const $fibers = [...fibers].map((f) => ctx.fork(f));
|
|
35
30
|
while (true) {
|
|
36
31
|
for (let f of $fibers) {
|
|
37
|
-
if (!f.isActive())
|
|
38
|
-
return f;
|
|
32
|
+
if (!f.isActive()) return f;
|
|
39
33
|
}
|
|
40
34
|
yield;
|
|
41
35
|
}
|
|
@@ -74,12 +68,10 @@ const timeSliceIterable = (src, consume, maxTime, opts) => fiber(function* () {
|
|
|
74
68
|
}
|
|
75
69
|
}, opts);
|
|
76
70
|
function* until(pred) {
|
|
77
|
-
while (!pred())
|
|
78
|
-
yield;
|
|
71
|
+
while (!pred()) yield;
|
|
79
72
|
}
|
|
80
73
|
function* untilState(state, pred) {
|
|
81
|
-
while (!pred(state))
|
|
82
|
-
yield;
|
|
74
|
+
while (!pred(state)) yield;
|
|
83
75
|
}
|
|
84
76
|
const untilPromise = (promise, opts) => fiber(function* (ctx) {
|
|
85
77
|
let error;
|
|
@@ -88,8 +80,7 @@ const untilPromise = (promise, opts) => fiber(function* (ctx) {
|
|
|
88
80
|
(e) => error = e
|
|
89
81
|
);
|
|
90
82
|
while (true) {
|
|
91
|
-
if (error)
|
|
92
|
-
throw error;
|
|
83
|
+
if (error) throw error;
|
|
93
84
|
yield;
|
|
94
85
|
}
|
|
95
86
|
}, opts);
|
|
@@ -114,8 +105,7 @@ class Shuffle extends Fiber {
|
|
|
114
105
|
this.forkAll(...fibers);
|
|
115
106
|
}
|
|
116
107
|
next() {
|
|
117
|
-
if (!this.isActive())
|
|
118
|
-
return this.state;
|
|
108
|
+
if (!this.isActive()) return this.state;
|
|
119
109
|
$shuffle(this.children, this.children.length, this.rnd);
|
|
120
110
|
return super.next();
|
|
121
111
|
}
|
|
@@ -129,8 +119,7 @@ const asPromise = (task, opts) => new Promise((resolve, reject) => {
|
|
|
129
119
|
ctx.state < STATE_ERROR && resolve(ctx.deref());
|
|
130
120
|
},
|
|
131
121
|
catch: (ctx, e) => {
|
|
132
|
-
if (opts?.catch && opts.catch(ctx, e))
|
|
133
|
-
return true;
|
|
122
|
+
if (opts?.catch && opts.catch(ctx, e)) return true;
|
|
134
123
|
reject(e);
|
|
135
124
|
return false;
|
|
136
125
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@thi.ng/fibers",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.4",
|
|
4
4
|
"description": "Process hierarchies & operators for cooperative multitasking",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"module": "./index.js",
|
|
@@ -36,21 +36,21 @@
|
|
|
36
36
|
"tool:tangle": "../../node_modules/.bin/tangle src/**/*.ts"
|
|
37
37
|
},
|
|
38
38
|
"dependencies": {
|
|
39
|
-
"@thi.ng/api": "^8.11.
|
|
40
|
-
"@thi.ng/arrays": "^2.9.
|
|
41
|
-
"@thi.ng/bench": "^3.5.
|
|
42
|
-
"@thi.ng/buffers": "^0.1.
|
|
43
|
-
"@thi.ng/checks": "^3.6.
|
|
44
|
-
"@thi.ng/errors": "^2.5.
|
|
45
|
-
"@thi.ng/idgen": "^2.2.
|
|
46
|
-
"@thi.ng/logger": "^3.0.
|
|
47
|
-
"@thi.ng/random": "^3.
|
|
39
|
+
"@thi.ng/api": "^8.11.2",
|
|
40
|
+
"@thi.ng/arrays": "^2.9.6",
|
|
41
|
+
"@thi.ng/bench": "^3.5.6",
|
|
42
|
+
"@thi.ng/buffers": "^0.1.3",
|
|
43
|
+
"@thi.ng/checks": "^3.6.4",
|
|
44
|
+
"@thi.ng/errors": "^2.5.7",
|
|
45
|
+
"@thi.ng/idgen": "^2.2.41",
|
|
46
|
+
"@thi.ng/logger": "^3.0.12",
|
|
47
|
+
"@thi.ng/random": "^3.8.0"
|
|
48
48
|
},
|
|
49
49
|
"devDependencies": {
|
|
50
|
-
"@microsoft/api-extractor": "^7.43.
|
|
51
|
-
"esbuild": "^0.
|
|
52
|
-
"typedoc": "^0.25.
|
|
53
|
-
"typescript": "^5.4.
|
|
50
|
+
"@microsoft/api-extractor": "^7.43.2",
|
|
51
|
+
"esbuild": "^0.21.1",
|
|
52
|
+
"typedoc": "^0.25.13",
|
|
53
|
+
"typescript": "^5.4.5"
|
|
54
54
|
},
|
|
55
55
|
"keywords": [
|
|
56
56
|
"blocking",
|
|
@@ -106,8 +106,12 @@
|
|
|
106
106
|
}
|
|
107
107
|
},
|
|
108
108
|
"thi.ng": {
|
|
109
|
+
"related": [
|
|
110
|
+
"csp",
|
|
111
|
+
"transducers-async"
|
|
112
|
+
],
|
|
109
113
|
"status": "alpha",
|
|
110
114
|
"year": 2023
|
|
111
115
|
},
|
|
112
|
-
"gitHead": "
|
|
116
|
+
"gitHead": "df34b4a9e650cc7323575356de207d78933bdcf3\n"
|
|
113
117
|
}
|