@camstack/types 1.2.187 → 1.2.188

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.
@@ -102,6 +102,7 @@ function buildVideoArgs(video, outputArgs) {
102
102
  ];
103
103
  if (video.preset !== void 0) args.push("-preset", video.preset);
104
104
  if (video.tune !== void 0) args.push("-tune", video.tune);
105
+ if (video.singleSlicePerFrame === true && video.encoder === "libx264") args.push("-x264-params", "sliced-threads=0");
105
106
  if (video.profile !== void 0) args.push("-profile:v", video.profile);
106
107
  if (video.level !== void 0) args.push("-level", video.level);
107
108
  if (video.pixelFormat !== void 0) args.push("-pix_fmt", video.pixelFormat);
@@ -376,6 +377,7 @@ function invocationFromEncodeProfile(input) {
376
377
  scale,
377
378
  ...v.preset !== void 0 ? { preset: v.preset } : {},
378
379
  ...v.tune !== void 0 ? { tune: v.tune } : {},
380
+ ...v.singleSlicePerFrame !== void 0 ? { singleSlicePerFrame: v.singleSlicePerFrame } : {},
379
381
  ...v.profile !== void 0 ? { profile: v.profile } : {},
380
382
  ...v.level !== void 0 ? { level: v.level } : {},
381
383
  ...input.pixelFormat !== void 0 ? { pixelFormat: input.pixelFormat } : {},
@@ -102,6 +102,7 @@ function buildVideoArgs(video, outputArgs) {
102
102
  ];
103
103
  if (video.preset !== void 0) args.push("-preset", video.preset);
104
104
  if (video.tune !== void 0) args.push("-tune", video.tune);
105
+ if (video.singleSlicePerFrame === true && video.encoder === "libx264") args.push("-x264-params", "sliced-threads=0");
105
106
  if (video.profile !== void 0) args.push("-profile:v", video.profile);
106
107
  if (video.level !== void 0) args.push("-level", video.level);
107
108
  if (video.pixelFormat !== void 0) args.push("-pix_fmt", video.pixelFormat);
@@ -376,6 +377,7 @@ function invocationFromEncodeProfile(input) {
376
377
  scale,
377
378
  ...v.preset !== void 0 ? { preset: v.preset } : {},
378
379
  ...v.tune !== void 0 ? { tune: v.tune } : {},
380
+ ...v.singleSlicePerFrame !== void 0 ? { singleSlicePerFrame: v.singleSlicePerFrame } : {},
379
381
  ...v.profile !== void 0 ? { profile: v.profile } : {},
380
382
  ...v.level !== void 0 ? { level: v.level } : {},
381
383
  ...input.pixelFormat !== void 0 ? { pixelFormat: input.pixelFormat } : {},
@@ -407,6 +407,7 @@ export declare const EgressEncodeSchema: z.ZodObject<{
407
407
  film: "film";
408
408
  animation: "animation";
409
409
  }>>;
410
+ singleSlicePerFrame: z.ZodOptional<z.ZodBoolean>;
410
411
  }, z.core.$strip>;
411
412
  audio: z.ZodUnion<readonly [z.ZodLiteral<"passthrough">, z.ZodObject<{
412
413
  codec: z.ZodEnum<{
@@ -478,6 +479,7 @@ export declare const EgressTranscodeRequestSchema: z.ZodObject<{
478
479
  film: "film";
479
480
  animation: "animation";
480
481
  }>>;
482
+ singleSlicePerFrame: z.ZodOptional<z.ZodBoolean>;
481
483
  }, z.core.$strip>;
482
484
  audio: z.ZodUnion<readonly [z.ZodLiteral<"passthrough">, z.ZodObject<{
483
485
  codec: z.ZodEnum<{
@@ -602,6 +604,7 @@ export declare const streamBrokerCapability: {
602
604
  film: "film";
603
605
  animation: "animation";
604
606
  }>>;
607
+ singleSlicePerFrame: z.ZodOptional<z.ZodBoolean>;
605
608
  }, z.core.$strip>;
606
609
  audio: z.ZodUnion<readonly [z.ZodLiteral<"passthrough">, z.ZodObject<{
607
610
  codec: z.ZodEnum<{
@@ -1141,6 +1144,7 @@ export declare const streamBrokerCapability: {
1141
1144
  film: "film";
1142
1145
  animation: "animation";
1143
1146
  }>>;
1147
+ singleSlicePerFrame: z.ZodOptional<z.ZodBoolean>;
1144
1148
  }, z.core.$strip>;
1145
1149
  audio: z.ZodUnion<readonly [z.ZodLiteral<"passthrough">, z.ZodObject<{
1146
1150
  codec: z.ZodEnum<{
@@ -42,6 +42,7 @@ export declare const VideoEncodeSchema: z.ZodObject<{
42
42
  film: "film";
43
43
  animation: "animation";
44
44
  }>>;
45
+ singleSlicePerFrame: z.ZodOptional<z.ZodBoolean>;
45
46
  }, z.core.$strip>;
46
47
  export type VideoEncode = z.infer<typeof VideoEncodeSchema>;
47
48
  export declare const AudioEncodeSchema: z.ZodUnion<readonly [z.ZodLiteral<"passthrough">, z.ZodObject<{
@@ -89,6 +90,7 @@ export declare const EncodeProfileSchema: z.ZodObject<{
89
90
  film: "film";
90
91
  animation: "animation";
91
92
  }>>;
93
+ singleSlicePerFrame: z.ZodOptional<z.ZodBoolean>;
92
94
  }, z.core.$strip>;
93
95
  audio: z.ZodUnion<readonly [z.ZodLiteral<"passthrough">, z.ZodObject<{
94
96
  codec: z.ZodEnum<{
@@ -90,6 +90,8 @@ export interface FfmpegVideoEncodePlan {
90
90
  readonly scale?: FfmpegScalePlan | null;
91
91
  readonly preset?: string;
92
92
  readonly tune?: string;
93
+ /** One slice per access unit — see `VideoEncodeSchema.singleSlicePerFrame`. */
94
+ readonly singleSlicePerFrame?: boolean;
93
95
  /** `-profile:v` — baseline / main / high. */
94
96
  readonly profile?: string;
95
97
  /**
package/dist/index.js CHANGED
@@ -1,7 +1,7 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
2
  const require_sleep = require("./sleep-DXsYD0RX.js");
3
3
  const require_event_category = require("./event-category-yW4s1MGD.js");
4
- const require_canonical_hash = require("./canonical-hash-DNV8S5ET.js");
4
+ const require_canonical_hash = require("./canonical-hash-9lydiEzx.js");
5
5
  const require_enums = require("./enums.js");
6
6
  const require_err_msg = require("./err-msg-COpsHMw2.js");
7
7
  let zod = require("zod");
@@ -321,7 +321,23 @@ var VideoEncodeSchema = zod.z.object({
321
321
  "zerolatency",
322
322
  "film",
323
323
  "animation"
324
- ]).optional()
324
+ ]).optional(),
325
+ /**
326
+ * ONE slice per access unit.
327
+ *
328
+ * `-tune zerolatency` turns on x264's sliced threads, and a frame then leaves
329
+ * the encoder as five NAL slices that share one RTP timestamp and carry one
330
+ * marker bit. A libwebrtc depacketiser sees five frame-starts and one
331
+ * frame-end per frame: the first pictures render and the video then freezes
332
+ * for good while the audio, on its own plane, plays on. Measured on this hub
333
+ * 2026-09-13 against the Echo, and reduced to one slice by this flag alone.
334
+ *
335
+ * A NAMED field and not a raw flag, because {@link EgressEncodeSchema} omits
336
+ * `outputArgs` on purpose: an opaque array is part of the sharing key, so two
337
+ * consumers meaning the same thing spelled differently would stop sharing one
338
+ * child. Absent means "whatever the encoder does" — today's behaviour.
339
+ */
340
+ singleSlicePerFrame: zod.z.boolean().optional()
325
341
  });
326
342
  var AudioEncodeSchema = zod.z.union([zod.z.literal("passthrough"), zod.z.object({
327
343
  codec: zod.z.enum([
@@ -443,31 +459,10 @@ var WEBRTC_EGRESS_PROFILE = {
443
459
  var ALEXA_EGRESS_PROFILE = {
444
460
  ...BASE_LIVE_EGRESS_PROFILE,
445
461
  audio: { codec: "opus" },
446
- /**
447
- * ONE slice per access unit.
448
- *
449
- * `-tune zerolatency` turns on x264's sliced threads, and every access unit
450
- * came out of this encode as FIVE slices — measured on the hub 2026-09-13 on
451
- * the exact argv this path spawns, and reduced to one by this single flag.
452
- *
453
- * Five slices share one RTP timestamp and carry one marker bit, so a
454
- * libwebrtc depacketiser sees five frame-starts and one frame-end per frame.
455
- * The Echo renders the first pictures and then freezes for good, while the
456
- * audio — a separate plane — plays on. It is the only structural property
457
- * that survived the elimination: the same freeze reproduced at 2304×1296
458
- * HEVC with 217 KB keyframes AND at 640×360 H.264 with 67 KB keyframes and a
459
- * fifth of the bitrate, so source, resolution, bitrate, keyframe burst,
460
- * hardware decode, parameter sets, drift and bitstream conformance are all
461
- * out — each ruled out by a measurement, not by elimination.
462
- *
463
- * The tune STAYS: it also drops the lookahead and the B-frames, which a live
464
- * path wants. Only the slicing is unwanted, and this is the flag that says so.
465
- *
466
- * Scoped to Alexa deliberately. HomeKit and the browser transcode inherit
467
- * {@link BASE_LIVE_EGRESS_PROFILE}; whether they want the same shape is a
468
- * question for their own evidence, and the browser has not been measured.
469
- */
470
- outputArgs: ["-x264-params", "sliced-threads=0"]
462
+ video: {
463
+ ...BASE_LIVE_EGRESS_PROFILE.video,
464
+ singleSlicePerFrame: true
465
+ }
471
466
  };
472
467
  /** VBV window for a consumer whose budget is enforced per second (HomeKit). */
473
468
  var RATE_CONTROL_TIGHT = {
@@ -610,7 +605,8 @@ function canonicalVideo(video) {
610
605
  gopFrames: video.gopFrames ?? -1,
611
606
  bf: video.bf ?? -1,
612
607
  preset: video.preset ?? UNSET,
613
- tune: video.tune ?? UNSET
608
+ tune: video.tune ?? UNSET,
609
+ singleSlicePerFrame: video.singleSlicePerFrame === void 0 ? UNSET : String(video.singleSlicePerFrame)
614
610
  };
615
611
  }
616
612
  function canonicalAudio(audio) {
package/dist/index.mjs CHANGED
@@ -1,6 +1,6 @@
1
1
  import { $ as CameraStreamSchema, A as DEVICE_STATUS_METHOD, At as collectHydratedFieldValues, B as toNodeId, C as ChargingStatus, Ct as createDurableState, D as adminUiCapability, Dt as WELL_KNOWN_TABS, E as DeviceType, Et as isEvent, F as resolveCapMount, Ft as expandAudioChunkToF32le, G as scopeKey, H as ReadinessTimeoutError, I as systemMethod, It as isAudioChunkFormat, J as BrokerStatusSchema, K as AudioChunkFormatSchema, L as CAP_NODE_PIN_CONTEXT_KEY, M as expandCapMethods, Mt as resolveHydratedFieldValue, N as isDeviceConfigCap, Nt as AUDIO_CHUNK_FORMATS, O as DEFAULT_RUNTIME_STATE_DURABILITY, Ot as WELL_KNOWN_TAB_MAP, P as method, Pt as audioChunkBytesPerSample, Q as CamStreamResolutionSchema, R as nodePin, S as DEVICE_CHILDREN_BATCH_MAX, St as normalizeAddonInitResult, T as DeviceRole, Tt as emitReadiness, U as emitDownForOwnedCaps, V as ReadinessRegistry, W as readinessKey, X as CamProfileSchema, Y as CAM_PROFILE_ORDER, Z as CamStreamKindSchema, _ as createMirrorSource, _t as selectAssignedProfileSlots, a as asJsonObject, at as ProfileRtspEntrySchema, b as deviceOpsCapability, bt as DisposerChain, c as parseJsonArray, ct as StreamSourceEntrySchema, d as BOOT_RECOVERY_BACKOFF_MS, dt as SubscribeAudioChunksResultSchema, et as DecodedAudioChunkSchema, f as DEVICE_SCOPED_CAPS, ft as SubscribeFramesInputSchema, g as createLazyTrpcSource, gt as parseProfileBrokerId, h as createEventBusSliceSource, ht as makeSourceBrokerId, i as asJsonArray, it as FrameHandleSchema, j as event, jt as hydrateSchema, k as DEVICE_SETTINGS_CONTRIBUTION_METHODS, kt as collectHydratedFieldEntries, l as parseJsonObject, lt as StreamSourceSchema, m as createDeviceProxy, mt as makeProfileBrokerId, n as sleepCancellable, nt as EncodedPacketSchema, o as asNumber, ot as ProfileSlotSchema, p as isDeviceScopedCap, pt as SubscribeFramesResultSchema, q as BrokerStatsSchema, r as asBoolean, rt as FrameHandleFormatSchema, s as asString, st as ProfileSlotStatusSchema, t as sleep, tt as DecodedFrameSchema, u as parseJsonUnknown, ut as SubscribeAudioChunksInputSchema, v as createSliceHandle, vt as DATAPLANE_SECRET_HEADER, w as DeviceFeature, wt as createEvent, x as viewerUiCapability, xt as BaseAddon, y as RawStateResultSchema, yt as SHARE_VIEW_KINDS, z as readNodePin } from "./sleep-DBKu2-U5.mjs";
2
2
  import { t as EventCategory } from "./event-category-ZyX6jcse.mjs";
3
- import { a as buildAudioArgs, c as buildVideoArgs, d as logBannerArgs, f as pickVideoEncoder, i as audioPlanFromEncodeProfile, l as invocationFromEncodeProfile, n as Fmp4BoxSplitter, o as buildFfmpegArgs, r as AUDIO_PRESETS, s as buildInputArgs, t as canonicalHash, u as isSoftwareDecode } from "./canonical-hash-rO1sRmEK.mjs";
3
+ import { a as buildAudioArgs, c as buildVideoArgs, d as logBannerArgs, f as pickVideoEncoder, i as audioPlanFromEncodeProfile, l as invocationFromEncodeProfile, n as Fmp4BoxSplitter, o as buildFfmpegArgs, r as AUDIO_PRESETS, s as buildInputArgs, t as canonicalHash, u as isSoftwareDecode } from "./canonical-hash-Ch5bSjFG.mjs";
4
4
  import { EventSourceType } from "./enums.mjs";
5
5
  import { t as errMsg } from "./err-msg-IQTHeDzc.mjs";
6
6
  import { z } from "zod";
@@ -320,7 +320,23 @@ var VideoEncodeSchema = z.object({
320
320
  "zerolatency",
321
321
  "film",
322
322
  "animation"
323
- ]).optional()
323
+ ]).optional(),
324
+ /**
325
+ * ONE slice per access unit.
326
+ *
327
+ * `-tune zerolatency` turns on x264's sliced threads, and a frame then leaves
328
+ * the encoder as five NAL slices that share one RTP timestamp and carry one
329
+ * marker bit. A libwebrtc depacketiser sees five frame-starts and one
330
+ * frame-end per frame: the first pictures render and the video then freezes
331
+ * for good while the audio, on its own plane, plays on. Measured on this hub
332
+ * 2026-09-13 against the Echo, and reduced to one slice by this flag alone.
333
+ *
334
+ * A NAMED field and not a raw flag, because {@link EgressEncodeSchema} omits
335
+ * `outputArgs` on purpose: an opaque array is part of the sharing key, so two
336
+ * consumers meaning the same thing spelled differently would stop sharing one
337
+ * child. Absent means "whatever the encoder does" — today's behaviour.
338
+ */
339
+ singleSlicePerFrame: z.boolean().optional()
324
340
  });
325
341
  var AudioEncodeSchema = z.union([z.literal("passthrough"), z.object({
326
342
  codec: z.enum([
@@ -442,31 +458,10 @@ var WEBRTC_EGRESS_PROFILE = {
442
458
  var ALEXA_EGRESS_PROFILE = {
443
459
  ...BASE_LIVE_EGRESS_PROFILE,
444
460
  audio: { codec: "opus" },
445
- /**
446
- * ONE slice per access unit.
447
- *
448
- * `-tune zerolatency` turns on x264's sliced threads, and every access unit
449
- * came out of this encode as FIVE slices — measured on the hub 2026-09-13 on
450
- * the exact argv this path spawns, and reduced to one by this single flag.
451
- *
452
- * Five slices share one RTP timestamp and carry one marker bit, so a
453
- * libwebrtc depacketiser sees five frame-starts and one frame-end per frame.
454
- * The Echo renders the first pictures and then freezes for good, while the
455
- * audio — a separate plane — plays on. It is the only structural property
456
- * that survived the elimination: the same freeze reproduced at 2304×1296
457
- * HEVC with 217 KB keyframes AND at 640×360 H.264 with 67 KB keyframes and a
458
- * fifth of the bitrate, so source, resolution, bitrate, keyframe burst,
459
- * hardware decode, parameter sets, drift and bitstream conformance are all
460
- * out — each ruled out by a measurement, not by elimination.
461
- *
462
- * The tune STAYS: it also drops the lookahead and the B-frames, which a live
463
- * path wants. Only the slicing is unwanted, and this is the flag that says so.
464
- *
465
- * Scoped to Alexa deliberately. HomeKit and the browser transcode inherit
466
- * {@link BASE_LIVE_EGRESS_PROFILE}; whether they want the same shape is a
467
- * question for their own evidence, and the browser has not been measured.
468
- */
469
- outputArgs: ["-x264-params", "sliced-threads=0"]
461
+ video: {
462
+ ...BASE_LIVE_EGRESS_PROFILE.video,
463
+ singleSlicePerFrame: true
464
+ }
470
465
  };
471
466
  /** VBV window for a consumer whose budget is enforced per second (HomeKit). */
472
467
  var RATE_CONTROL_TIGHT = {
@@ -609,7 +604,8 @@ function canonicalVideo(video) {
609
604
  gopFrames: video.gopFrames ?? -1,
610
605
  bf: video.bf ?? -1,
611
606
  preset: video.preset ?? UNSET,
612
- tune: video.tune ?? UNSET
607
+ tune: video.tune ?? UNSET,
608
+ singleSlicePerFrame: video.singleSlicePerFrame === void 0 ? UNSET : String(video.singleSlicePerFrame)
613
609
  };
614
610
  }
615
611
  function canonicalAudio(audio) {
package/dist/node.js CHANGED
@@ -21,7 +21,7 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
21
21
  enumerable: true
22
22
  }) : target, mod));
23
23
  //#endregion
24
- const require_canonical_hash = require("./canonical-hash-DNV8S5ET.js");
24
+ const require_canonical_hash = require("./canonical-hash-9lydiEzx.js");
25
25
  const require_err_msg = require("./err-msg-COpsHMw2.js");
26
26
  let node_crypto = require("node:crypto");
27
27
  let node_fs = require("node:fs");
package/dist/node.mjs CHANGED
@@ -1,4 +1,4 @@
1
- import { n as Fmp4BoxSplitter, o as buildFfmpegArgs, t as canonicalHash, u as isSoftwareDecode } from "./canonical-hash-rO1sRmEK.mjs";
1
+ import { n as Fmp4BoxSplitter, o as buildFfmpegArgs, t as canonicalHash, u as isSoftwareDecode } from "./canonical-hash-Ch5bSjFG.mjs";
2
2
  import { t as errMsg } from "./err-msg-IQTHeDzc.mjs";
3
3
  import { createHash, createHmac, randomUUID, timingSafeEqual } from "node:crypto";
4
4
  import * as fs from "node:fs";
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@camstack/types",
3
- "version": "1.2.187",
3
+ "version": "1.2.188",
4
4
  "description": "Shared types, interfaces, and model catalogs for the CamStack detection ecosystem",
5
5
  "keywords": [
6
6
  "camstack",