@@ -371,120 +371,6 @@ export function queryDatabase(query) {
371
371
In this way, we can have a context value propagated across the async execution
372
372
flow and keep track of the value without any other efforts.
373
373
374
- ## AsyncTask
375
-
376
- <!--
377
- TODO: how do we determine a task is not going to be used anymore?
378
-
379
- Fundamentally if an object is going to be finalized, it can not be used afterward.
380
- If an async task says it is disposed, ` runInAsyncScope` throws once disposed.
381
- -->
382
-
383
- While multiplexing platform provided async resources is not a rare case,
384
- how does the async locals get properly propagated?
385
-
386
- For library owners, ` AsyncTask` s are preferred to indicate new synthetic async
387
- tasks' schedule.
388
-
389
- ` ` ` js
390
- class AsyncTask {
391
- constructor ();
392
- runInAsyncScope(callback[, thisArg, ...args]);
393
- }
394
- ` ` `
395
-
396
- ` AsyncTask .runInAsyncScope ` calls the provided function with the provided
397
- arguments in the async context of the async task. This will establish
398
- the async context, call the function, and then restore the original async
399
- context.
400
-
401
- ### Using ` AsyncTask`
402
-
403
- ` ` ` js
404
- // Callback based arbitrary asynchronous API.
405
- function connect (port , host ) {
406
- let nextId = 0 ;
407
- const requestResponseMap = new Map ();
408
-
409
- // Establish the connection, the client is linked to the current async context.
410
- const client = net .createConnection ({ host, port });
411
- client .on (' connect' , () => {
412
- console .log (' connected to server' );
413
- });
414
- client .on (' end' , () => {
415
- console .log (' disconnected from server' );
416
- });
417
-
418
- // the client is created at the async context of `connect`,
419
- // the listeners will be triggered at the async context of the
420
- // client initiating async context.
421
- client .on (' data' , (res ) => {
422
- const { id , data } = JSON .parse (res .toString (' utf8' ));
423
- const req = requestResponseMap .get (id);
424
- if (req == null ) {
425
- console .log (' unknown response with id(%s)' , id);
426
- return ;
427
- }
428
-
429
- // The req.handler callback is called under the async context of client
430
- // listeners.
431
- req .handler (data);
432
- });
433
- return {
434
- send : (data , handler ) => {
435
- const id = nextId++ ;
436
- client .write (JSON .stringify ({ id, data }));
437
- requestResponseMap .set (id, { handler });
438
- }
439
- }
440
- }
441
-
442
- // AsyncTask & Promise based connection wrapper.
443
- class DatabaseConnection {
444
- constructor (port , host ) {
445
- // Initialize connection, possibly in root async context.
446
- this .socket = connect (port, host);
447
- }
448
-
449
- async query (search ) {
450
- const task = new QueryTask (search)
451
- return new Promise ((resolve , reject ) => {
452
- this .socket .send (query, (result ) => {
453
- // This async context is triggered by `DatabaseConnection` which is
454
- // not linked to initiator of `DatabaseConnection.query`.
455
- task .runInAsyncScope (() => {
456
- // This async context linked to the initiator of
457
- // `DatabaseConnection.query`.
458
- // PromiseResolution -> QueryTask -> `DatabaseConnection.query`
459
- resolve (result)
460
- });
461
- });
462
- });
463
- }
464
- }
465
-
466
- // A simple task that extends AsyncTask.
467
- class QueryTask extends AsyncTask {
468
- constructor (search ) {
469
- // link async task to current execution async context
470
- super ();
471
- this .search = search;
472
- }
473
- }
474
- ` ` `
475
-
476
- In the example above, ` DatabaseConnection` can be established at root async
477
- context (or any other context). With ` AsyncTask` , each call to
478
- ` DatabaseConnection .query ` will schedule an async task, which will be linked
479
- to its initiator async context (may not be the one establishing
480
- ` DatabaseConnection` ). And at the resolution of socket, the contexts are
481
- propagated by the ` DatabaseConnection` , which is linked to its initiating
482
- async context, so the async context has to be re-established by
483
- ` AsyncTask .runInAsyncScope ` .
484
-
485
- In this way, we can propagate correct async context flows on multiplexing
486
- single host platform provided async resource.
487
-
488
374
# Prior Arts
489
375
490
376
## zones.js
@@ -525,14 +411,6 @@ window.onload = loadZone.wrap(e => { ... });
525
411
526
412
then at all those sites, ` Zone .current ` would be equal to ` loadZone` .
527
413
528
- Compared to this proposal, ` Zone` acts similar to the ` AsyncTask` object in
529
- this proposal. However, there are differences of the basic concept between
530
- those two definitions. The major motivation of ` AsyncTask` is to declare a
531
- logical connection between multiple asynchronously executions. With these
532
- connections, the only use case in this proposal is to propagate the values of
533
- AsyncLocal correctly. However, many features still can be built on top of the
534
- connections built by ` AsyncTask` .
535
-
536
414
## Node.js ` domain` module
537
415
538
416
Domain's global central active domain can be consumed by multiple endpoints
0 commit comments