first commit

This commit is contained in:
2026-05-29 08:20:56 +01:00
commit 949299f58d
6368 changed files with 527176 additions and 0 deletions

View File

@@ -0,0 +1,58 @@
# TransportScheduler
The `TransportScheduler` class drives the lookahead loop that polls the transport and fires scheduled callbacks. It bridges the `Transport` and the wall clock, ensuring that musical events are delivered with sample-accurate timing even when the underlying poll timer is coarse.
<!-- begin:auto-docs -->
_(no submodules)_
<!-- end:auto-docs -->
## Purpose
In real-time audio systems, callbacks must fire at precise musical times. A naive approach would poll the transport on every sample, which is prohibitively expensive. Instead, `TransportScheduler` polls at a coarse interval (~100 Hz) and asks the transport to process the entire time window in one go. The transport then uses `TickSource.forEachTickBetween` to visit every musical tick in the window and invoke callbacks at their exact audio times.
## Features
- Poll-driven lookahead using `@suaveplan/timing`'s `createScheduler`
- `start()` / `stop()` lifecycle
- `AbortSignal` support for mid-run cancellation
- OpenTelemetry `transport.tick` span per poll
- Throws `AUDIO_TRANSPORT_SCHEDULER_NOT_STARTED` for invalid operations
## Usage: Basic
```ts
import { Transport, TransportScheduler } from "@suaveplan/audio-transport";
const tr = new Transport();
const scheduler = new TransportScheduler(tr, () => Date.now() / 1000);
tr.start();
scheduler.start();
```
## Usage: Advanced
```ts
const ac = new AbortController();
scheduler.start({ signal: ac.signal });
// Later:
ac.abort();
```
## API Reference
### Constructor
`new TransportScheduler(transport, clock, options?)`
### Methods
- `start(options?)` — begin polling; accepts `AbortSignal`
- `stop()` — halt polling
### Properties
- `running` — boolean
## Implementation Notes
The scheduler uses real timers via `createScheduler`. Each poll creates an OpenTelemetry span named `transport.tick`. Calling `stop()` before `start()` throws `AUDIO_TRANSPORT_SCHEDULER_NOT_STARTED`. The scheduler does not emit FSM events directly; those are emitted synchronously by the `Transport` when `start`, `stop`, or `pause` are called. The `_tick` and `_scheduleNextPoll` methods contain defensive guards for the case where `stop()` races with a scheduled callback.