prex-es5
Version:
Async coordination primitives and extensions on top of ES6 Promises
210 lines (161 loc) • 6.77 kB
Markdown
<!--
Copyright (c) Microsoft Corporation.
Licensed under the Apache License, Version 2.0.
See LICENSE file in the project root for details.
-->
Asynchronous coordination for JavaScript and TypeScript.
This library contains a number of coordination primitives to assist in asynchronous application development in JavaScript and TypeScript.
This includes useful additions for building complex asynchronous logic including:
* Cancellation \[[Sample](
* Coordination \[[Sample](
* Scheduling \[[Sample](
For the latest version:
```
npm install prex
```
* [API Reference](docs/index.md)
* [Cancellation](docs/cancellation.md)
* [Class: CancellationTokenSource](docs/cancellation.md
* [Class: CancellationToken](docs/cancellation.md
* [Class: CancelError](docs/cancellation.md
* [Interface: CancellationTokenRegistration](docs/cancellation.md
* [Coordination](docs/coordination.md)
* [Class: ManualResetEvent](docs/coordination.md
* [Class: AutoResetEvent](docs/coordination.md
* [Class: Semaphore](docs/coordination.md
* [Class: CountdownEvent](docs/coordination.md
* [Class: Barrier](docs/coordination.md
* [Class: ReaderWriterLock](docs/coordination.md
* [Interface: LockHandle](docs/coordination.md
* [Interface: UpgradeableLockHandle](docs/coordination.md
* [Class: Deferred](docs/coordination.md
* [Scheduling](docs/scheduling.md)
* [Class: AsyncQueue](docs/scheduling.md
* [Class: AsyncBoundedQueue](docs/scheduling.md
* [Class: AsyncStack](docs/scheduling.md
* [Function: delay(msec, value?)](docs/scheduling.md
> API Reference: [Cancellation](docs/cancellation.md)
The [CancellationTokenSource](docs/cancellation.md
[](docs/cancellation.md
create asynchronous operations that can be canceled externally. The following is an example
of a function used to download a file asynchronously that can be canceled:
```ts
import * as http from "http";
import * as fs from "fs";
import { CancellationTokenSource, CancellationToken } from "prex";
function downloadFile(from: string, to: string, token = CancellationToken.none) {
return new Promise<void>((resolve, reject) => {
const request = http.get(from);
// abort the request if canceled.
const registration = token.register(() => {
request.abort();
reject(new Error("Operation canceled."));
});
request.on("error", err => {
registration.unregister();
reject(err);
});
request.on("response", (response: http.IncomingMessage) => {
response
.pipe(fs.createWriteStream(to))
.on("error", err => {
registration.unregister();
reject(err);
})
.on("end", () => {
registration.unregister();
resolve();
});
});
});
}
async function main() {
const source = new CancellationTokenSource();
// cancel the source if the file takes more than one second to download
setTimeout(1000, () => source.cancel());
await downloadFile("http://tempuri.org/some/file", "file", source.token);
}
```
> API Reference: [Coordination](docs/coordination.md)
A [Semaphore](docs/coordination.md
section of your code when you must limit access across multiple async operations. The following
is an example of two functions which both need exclusive access to a single resource but could
possibly be preempted when suspended while awaiting an asynchronous operation:
```ts
import { Semaphore } from "prex";
const criticalResource = new Semaphore(1);
async function updateCriticalLocalResource() {
// Acquire a lock on the critical resource
await criticalResource.wait();
// Make local changes...
// await a network resources
await postUpdateToNetworkResource(changes);
// release the lock
criticalResource.release();
}
async function deleteCriticalLocalResource() {
// Acquire a lock on the critical resource
await criticalResource.wait();
// Make local changes...
// await a network resources
await postUpdateToNetworkResource(changes);
// release the lock
criticalResource.release();
}
declare function postUpdateToNetworkResource(changes): Promise<void>;
```
A [Barrier](docs/coordination.md
```ts
import { Barrier } from "prex";
const barrier = new Barrier(/*participantCount*/ 3);
async function processNpcAI() {
while (true) {
// process AI activities...
await barrier.signalAndWait();
}
}
async function processGameRules() {
while (true) {
// process game rules
await barrier.signalAndWait();
}
}
async function processGameInput() {
while (true) {
// process user input
await barrier.signalAndWait();
}
}
```
> API Reference: [Scheduling](docs/scheduling.md)
An [AsyncQueue](docs/scheduling.md
asynchronous work:
```ts
import { AsyncQueue } from "prex";
const workItems = new AsyncQueue();
function queueUserWorkItem(action: () => void) {
workItems.put(action);
}
async function processWorkItems() {
while (true) {
const action = await workItems.get();
try {
action();
}
catch (e) {
console.error(e);
}
}
}
```
Copyright (c) Microsoft Corporation.
Licensed under the Apache License, Version 2.0.
See [LICENSE](LICENSE) file in the project root for details.