@torrent-tv/proxy 2.97.18 → 2.97.19

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@torrent-tv/proxy",
3
- "version": "2.97.18",
3
+ "version": "2.97.19",
4
4
  "description": "Torrent proxy client that exposes webseed-like HTTP stream endpoint.",
5
5
  "license": "GPL-3.0-or-later",
6
6
  "repository": {
@@ -99,8 +99,17 @@ export async function admitInput({ sources, reserve, readRanges }) {
99
99
  }
100
100
  }
101
101
 
102
- /** Respect stdin backpressure and release input on every completion path. */
103
- export async function writeAdmittedInput(input, stdin, { next = null } = {}) {
102
+ /**
103
+ * Respect stdin backpressure and release input on every completion path.
104
+ *
105
+ * `waiting(true)` and `waiting(false)` bracket each wait for the next input:
106
+ * the encoder has nothing to read then, and that time is not its work. Counted
107
+ * as work, a soundtrack copy fed a segment at a time read 0.43x while ffmpeg
108
+ * used 0.014 s of processor per second of film, and the start forecast charged
109
+ * the download a second time through it (Home Assistant 2026-10-12,
110
+ * torrent-tv/meta#178).
111
+ */
112
+ export async function writeAdmittedInput(input, stdin, { next = null, waiting = null } = {}) {
104
113
  if (input?.kind !== "result") throw new TypeError("Only complete input may be written to an encoder.");
105
114
  const originSeconds = input.originSeconds;
106
115
  const declarations = JSON.stringify(input.tracks.map(input => matroskaTrackIdentity(input.track)));
@@ -137,7 +146,14 @@ export async function writeAdmittedInput(input, stdin, { next = null } = {}) {
137
146
  }
138
147
  await flush();
139
148
  current.release();
140
- current = next ? await next() : null;
149
+ if (next) {
150
+ waiting?.(true);
151
+ try {
152
+ current = await next();
153
+ } finally {
154
+ waiting?.(false);
155
+ }
156
+ } else current = null;
141
157
  includeHeader = false;
142
158
  }
143
159
  stdin.end();
@@ -1206,7 +1206,7 @@ export class EncodeRuns {
1206
1206
  run.admittedInputKeys.set(nextIndex, this.#inputFailures.key(next, inputParameters));
1207
1207
  run.to = nextIndex++;
1208
1208
  return next;
1209
- } }).catch(error => {
1209
+ }, waiting: waits => { if (waits) run.inputWaitBegins(); else run.inputWaitEnds(); } }).catch(error => {
1210
1210
  this.#host.logger.warn(`encode input output=${session.outputKey} segment=${safeIndex} write failed: ${error.message}`);
1211
1211
  run.process?.stdin?.destroy();
1212
1212
  });