@quilted/threads
Advanced tools
Comparing version 0.0.0-preview-20240716050509 to 0.0.0-preview-20240816031756
@@ -6,4 +6,4 @@ export { retain, release, StackFrame, isMemoryManageable, markAsTransferable, } from './memory.ts'; | ||
export { createBasicEncoder } from './encoding.ts'; | ||
export { createThreadAbortSignal, acceptThreadAbortSignal, type ThreadAbortSignal, } from './abort-signal.ts'; | ||
export { ThreadAbortSignal, type ThreadAbortSignalOptions, type ThreadAbortSignalSerialization, } from './ThreadAbortSignal.ts'; | ||
export type { Thread, ThreadTarget, ThreadEncoder, ThreadEncoderApi, ThreadEncodable, AnyFunction, } from './types.ts'; | ||
//# sourceMappingURL=index.d.ts.map |
@@ -1,2 +0,2 @@ | ||
import type { ThreadAbortSignal } from '../abort-signal.ts'; | ||
import type { ThreadAbortSignalSerialization } from '../ThreadAbortSignal.ts'; | ||
/** | ||
@@ -28,5 +28,5 @@ * A representation of a Preact signal that can be serialized between | ||
*/ | ||
signal?: AbortSignal | ThreadAbortSignal; | ||
signal?: AbortSignal | ThreadAbortSignalSerialization; | ||
}): void; | ||
} | ||
//# sourceMappingURL=types.d.ts.map |
# @quilted/threads | ||
## 0.0.0-preview-20240716050509 | ||
## 0.0.0-preview-20240816031756 | ||
### Minor Changes | ||
### Major Changes | ||
- Add support for serializing unsigned integer arrays | ||
- Changed `ThreadAbortSignal` utilities to be class-based instead of being a collection of utility functions. This change aligns the API more closely with `AbortController` in the browser, which is created with `new AbortController()`. | ||
Previously, you used `createThreadAbortSignal()` to serialize an `AbortSignal` to pass over a thread, and `acceptThreadAbortSignal()` to turn it into a “live” `AbortSignal`. With the new API, you will do the same steps, but with `ThreadAbortSignal.serialize()` and `new ThreadAbortSignal`: | ||
```ts | ||
import { | ||
createThreadAbortSignal, | ||
acceptThreadAbortSignal, | ||
} from '@quilted/threads'; | ||
const abortController = new AbortController(); | ||
const serializedAbortSignal = createThreadAbortSignal(abortController.signal); | ||
const liveAbortSignal = acceptThreadAbortSignal(serializedAbortSignal); | ||
await fetch('/', {signal: liveAbortSignal}); | ||
// Becomes: | ||
import { ThreadAbortSignal } from '@quilted/threads';\ | ||
const abortController = new AbortController(); | ||
const serializedAbortSignal = ThreadAbortSignal.serialize(abortController.signal); | ||
const liveAbortSignal = new ThreadAbortSignal(serializedAbortSignal); | ||
await fetch('/', {signal: liveAbortSignal}); | ||
``` | ||
Additionally, the new `ThreadAbortSignal` class assumes you are not doing manual memory management by default. If your target environment does not support automatic memory management of transferred functions, you will need to manually pass the `retain` and `release` functions to the new APIs: | ||
```ts | ||
import {retain, release, ThreadAbortSignal} from '@quilted/threads'; | ||
const abortController = new AbortController(); | ||
const serializedAbortSignal = ThreadAbortSignal.serialize( | ||
abortController.signal, | ||
{retain, release}, | ||
); | ||
const liveAbortSignal = new ThreadAbortSignal(serializedAbortSignal, { | ||
retain, | ||
release, | ||
}); | ||
await fetch('/', {signal: liveAbortSignal}); | ||
``` | ||
## 3.0.0 | ||
### Major Changes | ||
- [#816](https://github.com/lemonmade/quilt/pull/816) [`ecd7322`](https://github.com/lemonmade/quilt/commit/ecd7322637e54b5f34dfa310249d819e944c9171) Thanks [@lemonmade](https://github.com/lemonmade)! - Changed `ThreadAbortSignal` utilities to be class-based instead of being a collection of utility functions. This change aligns the API more closely with `AbortController` in the browser, which is created with `new AbortController()`. | ||
Previously, you used `createThreadAbortSignal()` to serialize an `AbortSignal` to pass over a thread, and `acceptThreadAbortSignal()` to turn it into a “live” `AbortSignal`. With the new API, you will do the same steps, but with `ThreadAbortSignal.serialize()` and `new ThreadAbortSignal`: | ||
```ts | ||
import { | ||
createThreadAbortSignal, | ||
acceptThreadAbortSignal, | ||
} from '@quilted/threads'; | ||
const abortController = new AbortController(); | ||
const serializedAbortSignal = createThreadAbortSignal(abortController.signal); | ||
const liveAbortSignal = acceptThreadAbortSignal(serializedAbortSignal); | ||
await fetch('/', {signal: liveAbortSignal}); | ||
// Becomes: | ||
import { ThreadAbortSignal } from '@quilted/threads';\ | ||
const abortController = new AbortController(); | ||
const serializedAbortSignal = ThreadAbortSignal.serialize(abortController.signal); | ||
const liveAbortSignal = new ThreadAbortSignal(serializedAbortSignal); | ||
await fetch('/', {signal: liveAbortSignal}); | ||
``` | ||
Additionally, the new `ThreadAbortSignal` class assumes you are not doing manual memory management by default. If your target environment does not support automatic memory management of transferred functions, you will need to manually pass the `retain` and `release` functions to the new APIs: | ||
```ts | ||
import {retain, release, ThreadAbortSignal} from '@quilted/threads'; | ||
const abortController = new AbortController(); | ||
const serializedAbortSignal = ThreadAbortSignal.serialize( | ||
abortController.signal, | ||
{retain, release}, | ||
); | ||
const liveAbortSignal = new ThreadAbortSignal(serializedAbortSignal, { | ||
retain, | ||
release, | ||
}); | ||
await fetch('/', {signal: liveAbortSignal}); | ||
``` | ||
## 2.4.0 | ||
@@ -10,0 +102,0 @@ |
@@ -5,3 +5,3 @@ { | ||
"type": "module", | ||
"version": "0.0.0-preview-20240716050509", | ||
"version": "0.0.0-preview-20240816031756", | ||
"license": "MIT", | ||
@@ -8,0 +8,0 @@ "engines": { |
@@ -240,11 +240,49 @@ # `@quilted/threads` | ||
[`AbortSignal`s](https://developer.mozilla.org/en-US/docs/Web/API/AbortSignal) allow you to communicate that an asynchronous operation should stop. Because all methods exposed through `@quilted/threads` are asynchronous, you may find many uses | ||
for `AbortSignal`s. However, it can be a bit tricky to communicate an abort signal across threads yourself. To make this easier, this library provides a pair of utilities to create a "thread-safe" `AbortSignal` on one thread, and to "accept" that signal on another thread. In the thread sending a signal, use the `createThreadAbortSignal()` function from this library, passing it an `AbortSignal`: | ||
[`AbortSignal`s](https://developer.mozilla.org/en-US/docs/Web/API/AbortSignal) allow you to communicate that an asynchronous operation should stop. Because all methods exposed through `@quilted/threads` are asynchronous, you may find many uses for `AbortSignal`s. However, it can be a bit tricky to communicate an abort signal across threads yourself. To make this easier, this library provides utilities to create a serialized `AbortSignal` on one thread, and to convert that serialized version into a “live” `AbortSignal` on another thread. In the thread sending a signal, use the `ThreadAbortSignal.serialize()` method to serialize your `AbortSignal`: | ||
```ts | ||
import {createThreadFromWebWorker, ThreadAbortSignal} from '@quilted/threads'; | ||
const worker = new Worker('worker.js'); | ||
const thread = createThreadFromWebWorker(worker); | ||
const abort = new AbortController(); | ||
await thread.calculateResult({ | ||
signal: ThreadAbortSignal.serialize(abort.signal), | ||
}); | ||
``` | ||
On the receiving thread, use `new ThreadAbortSignal()` to turn it back into a live `AbortSignal`, in the current thread’s JavaScript environment: | ||
```ts | ||
import { | ||
createThreadFromWebWorker, | ||
createThreadAbortSignal, | ||
ThreadAbortSignal, | ||
type ThreadAbortSignalSerialization, | ||
} from '@quilted/threads'; | ||
const thread = createThreadFromWebWorker(self, { | ||
expose: {calculateResult}, | ||
}); | ||
function calculateResult({ | ||
signal: threadSignal, | ||
}: { | ||
signal: ThreadAbortSignalSerialization; | ||
}) { | ||
const signal = new ThreadAbortSignal(threadSignal); | ||
return await figureOutResult({signal}); | ||
} | ||
``` | ||
If you are using `@quilted/threads`’ manual memory management approach, you must explicitly pass `retain` and `release` functions to `ThreadAbortSignal.serialize()` and `new ThreadAbortSignal()` methods: | ||
```ts | ||
import { | ||
retain, | ||
release, | ||
createThreadFromWebWorker, | ||
ThreadAbortSignal, | ||
} from '@quilted/threads'; | ||
const worker = new Worker('worker.js'); | ||
@@ -254,12 +292,14 @@ const thread = createThreadFromWebWorker(worker); | ||
const abort = new AbortController(); | ||
await thread.calculateResult({signal: createThreadSignal(abort.signal)}); | ||
``` | ||
await thread.calculateResult({ | ||
signal: ThreadAbortSignal.serialize(abort.signal, {retain, release}), | ||
}); | ||
On the receiving thread, use the `acceptThreadAbortSignal()` to turn it back into a "live" `AbortSignal`, in the current thread’s JavaScript environment: | ||
// In the worker: | ||
```ts | ||
import { | ||
retain, | ||
release, | ||
createThreadFromWebWorker, | ||
acceptThreadAbortSignal, | ||
type ThreadAbortSignal, | ||
ThreadAbortSignal, | ||
type ThreadAbortSignalSerialization, | ||
} from '@quilted/threads'; | ||
@@ -271,4 +311,8 @@ | ||
function calculateResult({signal: threadSignal}: {signal: ThreadAbortSignal}) { | ||
const signal = acceptThreadAbortSignal(threadSignal); | ||
function calculateResult({ | ||
signal: threadSignal, | ||
}: { | ||
signal: ThreadAbortSignalSerialization; | ||
}) { | ||
const signal = new ThreadAbortSignal(threadSignal, {retain, release}); | ||
return await figureOutResult({signal}); | ||
@@ -275,0 +319,0 @@ } |
@@ -31,6 +31,6 @@ export { | ||
export { | ||
createThreadAbortSignal, | ||
acceptThreadAbortSignal, | ||
type ThreadAbortSignal, | ||
} from './abort-signal.ts'; | ||
ThreadAbortSignal, | ||
type ThreadAbortSignalOptions, | ||
type ThreadAbortSignalSerialization, | ||
} from './ThreadAbortSignal.ts'; | ||
export type { | ||
@@ -37,0 +37,0 @@ Thread, |
import {signal as createSignal, type Signal} from '@preact/signals-core'; | ||
import {createThreadAbortSignal} from '../abort-signal.ts'; | ||
import {ThreadAbortSignal} from '../ThreadAbortSignal.ts'; | ||
@@ -28,3 +28,4 @@ import {type ThreadSignal} from './types.ts'; | ||
const signal = createSignal(threadSignal.initial); | ||
const threadAbortSignal = abortSignal && createThreadAbortSignal(abortSignal); | ||
const threadAbortSignal = | ||
abortSignal && ThreadAbortSignal.serialize(abortSignal); | ||
@@ -31,0 +32,0 @@ const valueDescriptor = Object.getOwnPropertyDescriptor( |
@@ -5,3 +5,3 @@ import {type Signal} from '@preact/signals-core'; | ||
import {retain, release} from '../memory.ts'; | ||
import {acceptThreadAbortSignal} from '../abort-signal.ts'; | ||
import {ThreadAbortSignal} from '../ThreadAbortSignal.ts'; | ||
@@ -54,3 +54,3 @@ import {type ThreadSignal} from './types.ts'; | ||
const abortSignal = | ||
threadAbortSignal && acceptThreadAbortSignal(threadAbortSignal); | ||
threadAbortSignal && new ThreadAbortSignal(threadAbortSignal); | ||
@@ -57,0 +57,0 @@ const finalAbortSignal = |
@@ -1,2 +0,2 @@ | ||
import type {ThreadAbortSignal} from '../abort-signal.ts'; | ||
import type {ThreadAbortSignalSerialization} from '../ThreadAbortSignal.ts'; | ||
@@ -33,5 +33,5 @@ /** | ||
*/ | ||
signal?: AbortSignal | ThreadAbortSignal; | ||
signal?: AbortSignal | ThreadAbortSignalSerialization; | ||
}, | ||
): void; | ||
} |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
262629
3952
357
124