@norskvideo/moq-net 0.1.2 → 0.1.4

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.
Files changed (310) hide show
  1. package/README.md +1 -0
  2. package/announced.d.ts +111 -21
  3. package/announced.d.ts.map +1 -1
  4. package/announced.js +213 -40
  5. package/announced.js.map +1 -1
  6. package/broadcast.d.ts +80 -25
  7. package/broadcast.d.ts.map +1 -1
  8. package/broadcast.js +270 -49
  9. package/broadcast.js.map +1 -1
  10. package/connection/accept.d.ts +6 -0
  11. package/connection/accept.d.ts.map +1 -1
  12. package/connection/accept.js +42 -13
  13. package/connection/accept.js.map +1 -1
  14. package/connection/browser.d.ts +5 -0
  15. package/connection/browser.d.ts.map +1 -0
  16. package/connection/browser.js +31 -0
  17. package/connection/browser.js.map +1 -0
  18. package/connection/connect.d.ts +43 -1
  19. package/connection/connect.d.ts.map +1 -1
  20. package/connection/connect.js +118 -123
  21. package/connection/connect.js.map +1 -1
  22. package/connection/established.d.ts +43 -16
  23. package/connection/established.d.ts.map +1 -1
  24. package/connection/established.js.map +1 -1
  25. package/connection/handshake.d.ts +12 -1
  26. package/connection/handshake.d.ts.map +1 -1
  27. package/connection/handshake.js +30 -14
  28. package/connection/handshake.js.map +1 -1
  29. package/connection/index.d.ts +8 -0
  30. package/connection/index.d.ts.map +1 -1
  31. package/connection/index.js +6 -0
  32. package/connection/index.js.map +1 -1
  33. package/connection/reload.d.ts +66 -9
  34. package/connection/reload.d.ts.map +1 -1
  35. package/connection/reload.js +192 -66
  36. package/connection/reload.js.map +1 -1
  37. package/connection/stats.d.ts +92 -0
  38. package/connection/stats.d.ts.map +1 -0
  39. package/connection/stats.js +35 -0
  40. package/connection/stats.js.map +1 -0
  41. package/connection/transport.d.ts +10 -0
  42. package/connection/transport.d.ts.map +1 -0
  43. package/connection/transport.js +12 -0
  44. package/connection/transport.js.map +1 -0
  45. package/consume.d.ts +44 -0
  46. package/consume.d.ts.map +1 -0
  47. package/consume.js +60 -0
  48. package/consume.js.map +1 -0
  49. package/datagram.d.ts +23 -0
  50. package/datagram.d.ts.map +1 -0
  51. package/datagram.js +3 -0
  52. package/datagram.js.map +1 -0
  53. package/error.d.ts +76 -0
  54. package/error.d.ts.map +1 -0
  55. package/error.js +107 -0
  56. package/error.js.map +1 -0
  57. package/group.d.ts +143 -38
  58. package/group.d.ts.map +1 -1
  59. package/group.js +270 -68
  60. package/group.js.map +1 -1
  61. package/ietf/adapter.d.ts +2 -2
  62. package/ietf/adapter.d.ts.map +1 -1
  63. package/ietf/adapter.js +20 -10
  64. package/ietf/adapter.js.map +1 -1
  65. package/ietf/aliases.d.ts +73 -5
  66. package/ietf/aliases.d.ts.map +1 -1
  67. package/ietf/aliases.js +121 -14
  68. package/ietf/aliases.js.map +1 -1
  69. package/ietf/cluster.d.ts +141 -0
  70. package/ietf/cluster.d.ts.map +1 -0
  71. package/ietf/cluster.js +204 -0
  72. package/ietf/cluster.js.map +1 -0
  73. package/ietf/connection.d.ts +39 -6
  74. package/ietf/connection.d.ts.map +1 -1
  75. package/ietf/connection.js +73 -12
  76. package/ietf/connection.js.map +1 -1
  77. package/ietf/fetch.d.ts +17 -0
  78. package/ietf/fetch.d.ts.map +1 -1
  79. package/ietf/fetch.js +21 -0
  80. package/ietf/fetch.js.map +1 -1
  81. package/ietf/filter.d.ts +87 -0
  82. package/ietf/filter.d.ts.map +1 -0
  83. package/ietf/filter.js +292 -0
  84. package/ietf/filter.js.map +1 -0
  85. package/ietf/index.d.ts +2 -0
  86. package/ietf/index.d.ts.map +1 -1
  87. package/ietf/index.js +3 -0
  88. package/ietf/index.js.map +1 -1
  89. package/ietf/namespace.d.ts +6 -0
  90. package/ietf/namespace.d.ts.map +1 -1
  91. package/ietf/namespace.js +27 -2
  92. package/ietf/namespace.js.map +1 -1
  93. package/ietf/object.d.ts +54 -6
  94. package/ietf/object.d.ts.map +1 -1
  95. package/ietf/object.js +178 -25
  96. package/ietf/object.js.map +1 -1
  97. package/ietf/parameters.d.ts +35 -10
  98. package/ietf/parameters.d.ts.map +1 -1
  99. package/ietf/parameters.js +236 -45
  100. package/ietf/parameters.js.map +1 -1
  101. package/ietf/priority.d.ts +5 -0
  102. package/ietf/priority.d.ts.map +1 -0
  103. package/ietf/priority.js +10 -0
  104. package/ietf/priority.js.map +1 -0
  105. package/ietf/properties.d.ts +13 -2
  106. package/ietf/properties.d.ts.map +1 -1
  107. package/ietf/properties.js +65 -8
  108. package/ietf/properties.js.map +1 -1
  109. package/ietf/publish.d.ts.map +1 -1
  110. package/ietf/publish.js +13 -3
  111. package/ietf/publish.js.map +1 -1
  112. package/ietf/publish_namespace.d.ts +16 -2
  113. package/ietf/publish_namespace.d.ts.map +1 -1
  114. package/ietf/publish_namespace.js +25 -6
  115. package/ietf/publish_namespace.js.map +1 -1
  116. package/ietf/publisher.d.ts +40 -7
  117. package/ietf/publisher.d.ts.map +1 -1
  118. package/ietf/publisher.js +751 -134
  119. package/ietf/publisher.js.map +1 -1
  120. package/ietf/request.js +1 -1
  121. package/ietf/request.js.map +1 -1
  122. package/ietf/solicit.d.ts +41 -0
  123. package/ietf/solicit.d.ts.map +1 -0
  124. package/ietf/solicit.js +47 -0
  125. package/ietf/solicit.js.map +1 -0
  126. package/ietf/subscribe.d.ts +41 -2
  127. package/ietf/subscribe.d.ts.map +1 -1
  128. package/ietf/subscribe.js +103 -22
  129. package/ietf/subscribe.js.map +1 -1
  130. package/ietf/subscribe_namespace.d.ts +21 -7
  131. package/ietf/subscribe_namespace.d.ts.map +1 -1
  132. package/ietf/subscribe_namespace.js +31 -14
  133. package/ietf/subscribe_namespace.js.map +1 -1
  134. package/ietf/subscriber.d.ts +20 -7
  135. package/ietf/subscriber.d.ts.map +1 -1
  136. package/ietf/subscriber.js +512 -142
  137. package/ietf/subscriber.js.map +1 -1
  138. package/ietf/version.d.ts +7 -1
  139. package/ietf/version.d.ts.map +1 -1
  140. package/ietf/version.js +7 -0
  141. package/ietf/version.js.map +1 -1
  142. package/index.d.ts +10 -5
  143. package/index.d.ts.map +1 -1
  144. package/index.js +10 -5
  145. package/index.js.map +1 -1
  146. package/internal.d.ts +29 -0
  147. package/internal.d.ts.map +1 -0
  148. package/internal.js +8 -0
  149. package/internal.js.map +1 -0
  150. package/lite/announce.d.ts +62 -15
  151. package/lite/announce.d.ts.map +1 -1
  152. package/lite/announce.js +230 -94
  153. package/lite/announce.js.map +1 -1
  154. package/lite/connection.d.ts +69 -20
  155. package/lite/connection.d.ts.map +1 -1
  156. package/lite/connection.js +128 -81
  157. package/lite/connection.js.map +1 -1
  158. package/lite/datagram.d.ts +23 -0
  159. package/lite/datagram.d.ts.map +1 -0
  160. package/lite/datagram.js +57 -0
  161. package/lite/datagram.js.map +1 -0
  162. package/lite/datagram_stream.d.ts +8 -0
  163. package/lite/datagram_stream.d.ts.map +1 -0
  164. package/lite/datagram_stream.js +44 -0
  165. package/lite/datagram_stream.js.map +1 -0
  166. package/lite/fetch.d.ts.map +1 -1
  167. package/lite/fetch.js +2 -2
  168. package/lite/fetch.js.map +1 -1
  169. package/lite/index.d.ts +3 -0
  170. package/lite/index.d.ts.map +1 -1
  171. package/lite/index.js +3 -0
  172. package/lite/index.js.map +1 -1
  173. package/lite/priority.d.ts +67 -0
  174. package/lite/priority.d.ts.map +1 -0
  175. package/lite/priority.js +114 -0
  176. package/lite/priority.js.map +1 -0
  177. package/lite/probe.d.ts +18 -2
  178. package/lite/probe.d.ts.map +1 -1
  179. package/lite/probe.js +24 -22
  180. package/lite/probe.js.map +1 -1
  181. package/lite/publisher.d.ts +14 -7
  182. package/lite/publisher.d.ts.map +1 -1
  183. package/lite/publisher.js +406 -84
  184. package/lite/publisher.js.map +1 -1
  185. package/lite/setup.d.ts +83 -6
  186. package/lite/setup.d.ts.map +1 -1
  187. package/lite/setup.js +203 -31
  188. package/lite/setup.js.map +1 -1
  189. package/lite/stream.d.ts +12 -3
  190. package/lite/stream.d.ts.map +1 -1
  191. package/lite/stream.js +7 -4
  192. package/lite/stream.js.map +1 -1
  193. package/lite/subscribe.d.ts +37 -23
  194. package/lite/subscribe.d.ts.map +1 -1
  195. package/lite/subscribe.js +70 -55
  196. package/lite/subscribe.js.map +1 -1
  197. package/lite/subscriber.d.ts +29 -23
  198. package/lite/subscriber.d.ts.map +1 -1
  199. package/lite/subscriber.js +689 -112
  200. package/lite/subscriber.js.map +1 -1
  201. package/lite/track.d.ts +25 -13
  202. package/lite/track.d.ts.map +1 -1
  203. package/lite/track.js +60 -35
  204. package/lite/track.js.map +1 -1
  205. package/lite/version.d.ts +39 -4
  206. package/lite/version.d.ts.map +1 -1
  207. package/lite/version.js +139 -17
  208. package/lite/version.js.map +1 -1
  209. package/mock.d.ts +53 -3
  210. package/mock.d.ts.map +1 -1
  211. package/mock.js +110 -21
  212. package/mock.js.map +1 -1
  213. package/{lite/origin.d.ts → origin.d.ts} +25 -1
  214. package/origin.d.ts.map +1 -0
  215. package/{lite/origin.js → origin.js} +25 -1
  216. package/origin.js.map +1 -0
  217. package/package.json +6 -4
  218. package/path.d.ts +67 -0
  219. package/path.d.ts.map +1 -1
  220. package/path.js +128 -0
  221. package/path.js.map +1 -1
  222. package/stream.d.ts +94 -4
  223. package/stream.d.ts.map +1 -1
  224. package/stream.js +128 -17
  225. package/stream.js.map +1 -1
  226. package/time.d.ts +109 -86
  227. package/time.d.ts.map +1 -1
  228. package/time.js +80 -30
  229. package/time.js.map +1 -1
  230. package/track.d.ts +298 -47
  231. package/track.d.ts.map +1 -1
  232. package/track.js +721 -109
  233. package/track.js.map +1 -1
  234. package/util/timeout.d.ts +5 -0
  235. package/util/timeout.d.ts.map +1 -0
  236. package/util/timeout.js +18 -0
  237. package/util/timeout.js.map +1 -0
  238. package/util/utf8.d.ts +3 -0
  239. package/util/utf8.d.ts.map +1 -0
  240. package/util/utf8.js +7 -0
  241. package/util/utf8.js.map +1 -0
  242. package/varint.d.ts +14 -3
  243. package/varint.d.ts.map +1 -1
  244. package/varint.js +23 -12
  245. package/varint.js.map +1 -1
  246. package/zod.d.ts +5 -5
  247. package/zod.d.ts.map +1 -1
  248. package/zod.js.map +1 -1
  249. package/bandwidth.d.ts +0 -11
  250. package/bandwidth.d.ts.map +0 -1
  251. package/bandwidth.js +0 -7
  252. package/bandwidth.js.map +0 -1
  253. package/connection/cert.test.d.ts +0 -2
  254. package/connection/cert.test.d.ts.map +0 -1
  255. package/connection/cert.test.js +0 -26
  256. package/connection/cert.test.js.map +0 -1
  257. package/connection/reload.test.d.ts +0 -2
  258. package/connection/reload.test.d.ts.map +0 -1
  259. package/connection/reload.test.js +0 -39
  260. package/connection/reload.test.js.map +0 -1
  261. package/group.test.d.ts +0 -2
  262. package/group.test.d.ts.map +0 -1
  263. package/group.test.js +0 -66
  264. package/group.test.js.map +0 -1
  265. package/ietf/aliases.test.d.ts +0 -2
  266. package/ietf/aliases.test.d.ts.map +0 -1
  267. package/ietf/aliases.test.js +0 -30
  268. package/ietf/aliases.test.js.map +0 -1
  269. package/ietf/ietf.test.d.ts +0 -2
  270. package/ietf/ietf.test.d.ts.map +0 -1
  271. package/ietf/ietf.test.js +0 -873
  272. package/ietf/ietf.test.js.map +0 -1
  273. package/integration.test.d.ts +0 -2
  274. package/integration.test.d.ts.map +0 -1
  275. package/integration.test.js +0 -90
  276. package/integration.test.js.map +0 -1
  277. package/lite/origin.d.ts.map +0 -1
  278. package/lite/origin.js.map +0 -1
  279. package/lite/subscriber.test.d.ts +0 -2
  280. package/lite/subscriber.test.d.ts.map +0 -1
  281. package/lite/subscriber.test.js +0 -30
  282. package/lite/subscriber.test.js.map +0 -1
  283. package/lite/track.test.d.ts +0 -2
  284. package/lite/track.test.d.ts.map +0 -1
  285. package/lite/track.test.js +0 -53
  286. package/lite/track.test.js.map +0 -1
  287. package/path.test.d.ts +0 -2
  288. package/path.test.d.ts.map +0 -1
  289. package/path.test.js +0 -169
  290. package/path.test.js.map +0 -1
  291. package/stream.test.d.ts +0 -2
  292. package/stream.test.d.ts.map +0 -1
  293. package/stream.test.js +0 -210
  294. package/stream.test.js.map +0 -1
  295. package/track.test.d.ts +0 -2
  296. package/track.test.d.ts.map +0 -1
  297. package/track.test.js +0 -56
  298. package/track.test.js.map +0 -1
  299. package/util/error.d.ts +0 -3
  300. package/util/error.d.ts.map +0 -1
  301. package/util/error.js +0 -9
  302. package/util/error.js.map +0 -1
  303. package/util/index.d.ts +0 -2
  304. package/util/index.d.ts.map +0 -1
  305. package/util/index.js +0 -3
  306. package/util/index.js.map +0 -1
  307. package/varint.test.d.ts +0 -2
  308. package/varint.test.d.ts.map +0 -1
  309. package/varint.test.js +0 -106
  310. package/varint.test.js.map +0 -1
package/lite/index.js CHANGED
@@ -1,12 +1,15 @@
1
1
  /* @ts-self-types="./index.d.ts" */
2
2
  export * from "./announce.js";
3
3
  export * from "./connection.js";
4
+ export * from "./datagram.js";
4
5
  export * from "./fetch.js";
5
6
  export * from "./goaway.js";
6
7
  export * from "./group.js";
7
8
  export * from "./probe.js";
8
9
  export * from "./session.js";
10
+ export * from "./setup.js";
9
11
  export * from "./stream.js";
10
12
  export * from "./subscribe.js";
13
+ export * from "./track.js";
11
14
  export * from "./version.js";
12
15
  //# sourceMappingURL=index.js.map
package/lite/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/lite/index.ts"],"names":[],"mappings":"AAAA,cAAc,eAAe,CAAC;AAC9B,cAAc,iBAAiB,CAAC;AAChC,cAAc,YAAY,CAAC;AAC3B,cAAc,aAAa,CAAC;AAC5B,cAAc,YAAY,CAAC;AAC3B,cAAc,YAAY,CAAC;AAC3B,cAAc,cAAc,CAAC;AAC7B,cAAc,aAAa,CAAC;AAC5B,cAAc,gBAAgB,CAAC;AAC/B,cAAc,cAAc,CAAC","sourcesContent":["export * from \"./announce.ts\";\nexport * from \"./connection.ts\";\nexport * from \"./fetch.ts\";\nexport * from \"./goaway.ts\";\nexport * from \"./group.ts\";\nexport * from \"./probe.ts\";\nexport * from \"./session.ts\";\nexport * from \"./stream.ts\";\nexport * from \"./subscribe.ts\";\nexport * from \"./version.ts\";\n"]}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/lite/index.ts"],"names":[],"mappings":"AAAA,cAAc,eAAe,CAAC;AAC9B,cAAc,iBAAiB,CAAC;AAChC,cAAc,eAAe,CAAC;AAC9B,cAAc,YAAY,CAAC;AAC3B,cAAc,aAAa,CAAC;AAC5B,cAAc,YAAY,CAAC;AAC3B,cAAc,YAAY,CAAC;AAC3B,cAAc,cAAc,CAAC;AAC7B,cAAc,YAAY,CAAC;AAC3B,cAAc,aAAa,CAAC;AAC5B,cAAc,gBAAgB,CAAC;AAC/B,cAAc,YAAY,CAAC;AAC3B,cAAc,cAAc,CAAC","sourcesContent":["export * from \"./announce.ts\";\nexport * from \"./connection.ts\";\nexport * from \"./datagram.ts\";\nexport * from \"./fetch.ts\";\nexport * from \"./goaway.ts\";\nexport * from \"./group.ts\";\nexport * from \"./probe.ts\";\nexport * from \"./session.ts\";\nexport * from \"./setup.ts\";\nexport * from \"./stream.ts\";\nexport * from \"./subscribe.ts\";\nexport * from \"./track.ts\";\nexport * from \"./version.ts\";\n"]}
@@ -0,0 +1,67 @@
1
+ /**
2
+ * Stream prioritization for moq-lite, mirroring the Rust `lite::priority` queue.
3
+ *
4
+ * @module
5
+ */
6
+ import type { Writer } from "../stream";
7
+ import type * as track from "../track";
8
+ /**
9
+ * What to rank a group stream by.
10
+ *
11
+ * @internal
12
+ */
13
+ export interface Rank {
14
+ /** The subscriber's track priority, which outweighs everything below it. */
15
+ priority: number;
16
+ /**
17
+ * Where the group sits in the queue its own subscription wants sent, 0 being the one to
18
+ * send next. Defaults to 0, which is right for a stream that is the only one of its kind.
19
+ */
20
+ position?: number;
21
+ }
22
+ /**
23
+ * The transport send order for a group, where HIGHER values are transmitted first.
24
+ *
25
+ * A higher `priority` always wins. Below it, a group is ranked by its `position` in its own
26
+ * subscription rather than by its sequence, so two tracks at the same priority interleave:
27
+ * each one's next group ties with the other's, whatever their group numbering. Comparing
28
+ * sequences instead would let a track that had been running longer, or that numbered its
29
+ * groups from a clock, starve one that started later.
30
+ *
31
+ * @internal
32
+ */
33
+ export declare function sendOrder({ priority, position }: Rank): number;
34
+ /**
35
+ * Ranks one subscription's group streams against each other, and re-ranks them whenever the
36
+ * set changes or the subscription is updated.
37
+ *
38
+ * A group's rank is its position among the groups in flight, so which group goes first is
39
+ * decided here rather than by arithmetic on sequence numbers. Newest-first by default, since
40
+ * that is what live playback wants; an `ordered` subscription is playing through in sequence,
41
+ * so it gets the oldest group first instead.
42
+ *
43
+ * One listener covers the whole subscription. A listener per group would instead pile up on
44
+ * it, and a track that stalls with many groups open would trip the signals leak guard.
45
+ *
46
+ * @internal
47
+ */
48
+ export declare class Priority {
49
+ #private;
50
+ /** Follow `track`'s subscription until {@link close}. */
51
+ constructor(track: track.Subscriber);
52
+ /** The send order for a group at `sequence`, whether or not it has a stream yet. */
53
+ rank(sequence: number): number;
54
+ /** Rank a group's stream now, and again whenever the ranking changes, until {@link remove}. */
55
+ add(stream: Writer, sequence: number): void;
56
+ /** Stop ranking a finished group's stream, promoting whatever was queued behind it. */
57
+ remove(stream: Writer): void;
58
+ /**
59
+ * Stop taking new groups, and release the subscription listener once the last one leaves.
60
+ *
61
+ * The track can finish while several groups are still draining, and those are the ones the
62
+ * subscriber is still waiting on. They keep being promoted as the groups ahead of them
63
+ * finish, rather than being stranded at whatever position they held when the track ended.
64
+ */
65
+ close(): void;
66
+ }
67
+ //# sourceMappingURL=priority.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"priority.d.ts","sourceRoot":"","sources":["../../src/lite/priority.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAGH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,cAAc,CAAC;AAC3C,OAAO,KAAK,KAAK,KAAK,MAAM,aAAa,CAAC;AAY1C;;;;GAIG;AACH,MAAM,WAAW,IAAI;IACpB,4EAA4E;IAC5E,QAAQ,EAAE,MAAM,CAAC;IAEjB;;;OAGG;IACH,QAAQ,CAAC,EAAE,MAAM,CAAC;CAClB;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,SAAS,CAAC,EAAE,QAAQ,EAAE,QAAY,EAAE,EAAE,IAAI,GAAG,MAAM,CAElE;AAQD;;;;;;;;;;;;;GAaG;AACH,qBAAa,QAAQ;;IAMpB,yDAAyD;IACzD,YAAY,KAAK,EAAE,KAAK,CAAC,UAAU,EAGlC;IAED,oFAAoF;IACpF,IAAI,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAK7B;IAED,+FAA+F;IAC/F,GAAG,CAAC,MAAM,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,QAMnC;IAED,uFAAuF;IACvF,MAAM,CAAC,MAAM,EAAE,MAAM,QAQpB;IAED;;;;;;OAMG;IACH,KAAK,SAGJ;CAqBD"}
@@ -0,0 +1,114 @@
1
+ /* @ts-self-types="./priority.d.ts" */
2
+ /**
3
+ * Stream prioritization for moq-lite, mirroring the Rust `lite::priority` queue.
4
+ *
5
+ * @module
6
+ */
7
+ // The transport compares send orders as a single number, so the two ranks are packed into
8
+ // disjoint ranges: the track priority takes the high bits so it always dominates, and the
9
+ // position below it. Group data stays negative so protocol streams at the transport's default
10
+ // order of 0 always make progress. A u8 priority and 44-bit position fill the negative half of
11
+ // the safe integer range exactly.
12
+ const GROUP_SPAN = 2 ** 44;
13
+ /** The highest track priority the wire carries (a u8). */
14
+ const MAX_PRIORITY = 0xff;
15
+ /**
16
+ * The transport send order for a group, where HIGHER values are transmitted first.
17
+ *
18
+ * A higher `priority` always wins. Below it, a group is ranked by its `position` in its own
19
+ * subscription rather than by its sequence, so two tracks at the same priority interleave:
20
+ * each one's next group ties with the other's, whatever their group numbering. Comparing
21
+ * sequences instead would let a track that had been running longer, or that numbered its
22
+ * groups from a clock, starve one that started later.
23
+ *
24
+ * @internal
25
+ */
26
+ export function sendOrder({ priority, position = 0 }) {
27
+ return -((MAX_PRIORITY - clamp(priority, MAX_PRIORITY)) * GROUP_SPAN + clamp(position, GROUP_SPAN - 1) + 1);
28
+ }
29
+ // Both ranks are bounded: the priority by its wire type, the position by the space left below
30
+ // it. Anything outside is a caller bug rather than a value worth preserving.
31
+ function clamp(value, max) {
32
+ return Math.min(Math.max(Math.trunc(value), 0), max);
33
+ }
34
+ /**
35
+ * Ranks one subscription's group streams against each other, and re-ranks them whenever the
36
+ * set changes or the subscription is updated.
37
+ *
38
+ * A group's rank is its position among the groups in flight, so which group goes first is
39
+ * decided here rather than by arithmetic on sequence numbers. Newest-first by default, since
40
+ * that is what live playback wants; an `ordered` subscription is playing through in sequence,
41
+ * so it gets the oldest group first instead.
42
+ *
43
+ * One listener covers the whole subscription. A listener per group would instead pile up on
44
+ * it, and a track that stalls with many groups open would trip the signals leak guard.
45
+ *
46
+ * @internal
47
+ */
48
+ export class Priority {
49
+ #track;
50
+ #streams = new Map();
51
+ #dispose;
52
+ #closed = false;
53
+ /** Follow `track`'s subscription until {@link close}. */
54
+ constructor(track) {
55
+ this.#track = track;
56
+ this.#dispose = track.subscription.subscribe(() => this.#rerank());
57
+ }
58
+ /** The send order for a group at `sequence`, whether or not it has a stream yet. */
59
+ rank(sequence) {
60
+ return sendOrder({
61
+ priority: this.#track.subscription.peek()?.priority ?? 0,
62
+ position: this.#position(sequence),
63
+ });
64
+ }
65
+ /** Rank a group's stream now, and again whenever the ranking changes, until {@link remove}. */
66
+ add(stream, sequence) {
67
+ this.#streams.set(stream, sequence);
68
+ // Also covers the stream itself: opening one can block on transport capacity, so an
69
+ // update that landed while it did predates this registration.
70
+ this.#rerank();
71
+ }
72
+ /** Stop ranking a finished group's stream, promoting whatever was queued behind it. */
73
+ remove(stream) {
74
+ if (!this.#streams.delete(stream))
75
+ return;
76
+ if (this.#closed && this.#streams.size === 0) {
77
+ this.#dispose();
78
+ }
79
+ else {
80
+ this.#rerank();
81
+ }
82
+ }
83
+ /**
84
+ * Stop taking new groups, and release the subscription listener once the last one leaves.
85
+ *
86
+ * The track can finish while several groups are still draining, and those are the ones the
87
+ * subscriber is still waiting on. They keep being promoted as the groups ahead of them
88
+ * finish, rather than being stranded at whatever position they held when the track ended.
89
+ */
90
+ close() {
91
+ this.#closed = true;
92
+ if (this.#streams.size === 0)
93
+ this.#dispose();
94
+ }
95
+ // How many of this subscription's groups in flight should be sent before `sequence`.
96
+ // Sequences are unique within a subscription, so a group already registered never counts
97
+ // itself.
98
+ #position(sequence) {
99
+ const ordered = this.#track.subscription.peek()?.ordered ?? false;
100
+ let ahead = 0;
101
+ for (const other of this.#streams.values()) {
102
+ if (ordered ? other < sequence : other > sequence)
103
+ ahead++;
104
+ }
105
+ return ahead;
106
+ }
107
+ #rerank() {
108
+ const priority = this.#track.subscription.peek()?.priority ?? 0;
109
+ for (const [stream, sequence] of this.#streams) {
110
+ stream.setPriority(sendOrder({ priority, position: this.#position(sequence) }));
111
+ }
112
+ }
113
+ }
114
+ //# sourceMappingURL=priority.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"priority.js","sourceRoot":"","sources":["../../src/lite/priority.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAMH,0FAA0F;AAC1F,0FAA0F;AAC1F,8FAA8F;AAC9F,+FAA+F;AAC/F,kCAAkC;AAClC,MAAM,UAAU,GAAG,CAAC,IAAI,EAAE,CAAC;AAE3B,0DAA0D;AAC1D,MAAM,YAAY,GAAG,IAAI,CAAC;AAkB1B;;;;;;;;;;GAUG;AACH,MAAM,UAAU,SAAS,CAAC,EAAE,QAAQ,EAAE,QAAQ,GAAG,CAAC,EAAQ;IACzD,OAAO,CAAC,CAAC,CAAC,YAAY,GAAG,KAAK,CAAC,QAAQ,EAAE,YAAY,CAAC,CAAC,GAAG,UAAU,GAAG,KAAK,CAAC,QAAQ,EAAE,UAAU,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;AAC7G,CAAC;AAED,8FAA8F;AAC9F,6EAA6E;AAC7E,SAAS,KAAK,CAAC,KAAa,EAAE,GAAW;IACxC,OAAO,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC;AACtD,CAAC;AAED;;;;;;;;;;;;;GAaG;AACH,MAAM,OAAO,QAAQ;IACpB,MAAM,CAAmB;IACzB,QAAQ,GAAG,IAAI,GAAG,EAAkB,CAAC;IACrC,QAAQ,CAAU;IAClB,OAAO,GAAG,KAAK,CAAC;IAEhB,yDAAyD;IACzD,YAAY,KAAuB;QAClC,IAAI,CAAC,MAAM,GAAG,KAAK,CAAC;QACpB,IAAI,CAAC,QAAQ,GAAG,KAAK,CAAC,YAAY,CAAC,SAAS,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,CAAC;IACpE,CAAC;IAED,oFAAoF;IACpF,IAAI,CAAC,QAAgB;QACpB,OAAO,SAAS,CAAC;YAChB,QAAQ,EAAE,IAAI,CAAC,MAAM,CAAC,YAAY,CAAC,IAAI,EAAE,EAAE,QAAQ,IAAI,CAAC;YACxD,QAAQ,EAAE,IAAI,CAAC,SAAS,CAAC,QAAQ,CAAC;SAClC,CAAC,CAAC;IACJ,CAAC;IAED,+FAA+F;IAC/F,GAAG,CAAC,MAAc,EAAE,QAAgB;QACnC,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC;QAEpC,oFAAoF;QACpF,8DAA8D;QAC9D,IAAI,CAAC,OAAO,EAAE,CAAC;IAChB,CAAC;IAED,uFAAuF;IACvF,MAAM,CAAC,MAAc;QACpB,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,MAAM,CAAC,MAAM,CAAC;YAAE,OAAO;QAE1C,IAAI,IAAI,CAAC,OAAO,IAAI,IAAI,CAAC,QAAQ,CAAC,IAAI,KAAK,CAAC,EAAE,CAAC;YAC9C,IAAI,CAAC,QAAQ,EAAE,CAAC;QACjB,CAAC;aAAM,CAAC;YACP,IAAI,CAAC,OAAO,EAAE,CAAC;QAChB,CAAC;IACF,CAAC;IAED;;;;;;OAMG;IACH,KAAK;QACJ,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC;QACpB,IAAI,IAAI,CAAC,QAAQ,CAAC,IAAI,KAAK,CAAC;YAAE,IAAI,CAAC,QAAQ,EAAE,CAAC;IAC/C,CAAC;IAED,qFAAqF;IACrF,yFAAyF;IACzF,UAAU;IACV,SAAS,CAAC,QAAgB;QACzB,MAAM,OAAO,GAAG,IAAI,CAAC,MAAM,CAAC,YAAY,CAAC,IAAI,EAAE,EAAE,OAAO,IAAI,KAAK,CAAC;QAElE,IAAI,KAAK,GAAG,CAAC,CAAC;QACd,KAAK,MAAM,KAAK,IAAI,IAAI,CAAC,QAAQ,CAAC,MAAM,EAAE,EAAE,CAAC;YAC5C,IAAI,OAAO,CAAC,CAAC,CAAC,KAAK,GAAG,QAAQ,CAAC,CAAC,CAAC,KAAK,GAAG,QAAQ;gBAAE,KAAK,EAAE,CAAC;QAC5D,CAAC;QACD,OAAO,KAAK,CAAC;IACd,CAAC;IAED,OAAO;QACN,MAAM,QAAQ,GAAG,IAAI,CAAC,MAAM,CAAC,YAAY,CAAC,IAAI,EAAE,EAAE,QAAQ,IAAI,CAAC,CAAC;QAChE,KAAK,MAAM,CAAC,MAAM,EAAE,QAAQ,CAAC,IAAI,IAAI,CAAC,QAAQ,EAAE,CAAC;YAChD,MAAM,CAAC,WAAW,CAAC,SAAS,CAAC,EAAE,QAAQ,EAAE,QAAQ,EAAE,IAAI,CAAC,SAAS,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAC,CAAC;QACjF,CAAC;IACF,CAAC;CACD","sourcesContent":["/**\n * Stream prioritization for moq-lite, mirroring the Rust `lite::priority` queue.\n *\n * @module\n */\n\nimport type { Dispose } from \"@moq/signals\";\nimport type { Writer } from \"../stream.ts\";\nimport type * as track from \"../track.ts\";\n\n// The transport compares send orders as a single number, so the two ranks are packed into\n// disjoint ranges: the track priority takes the high bits so it always dominates, and the\n// position below it. Group data stays negative so protocol streams at the transport's default\n// order of 0 always make progress. A u8 priority and 44-bit position fill the negative half of\n// the safe integer range exactly.\nconst GROUP_SPAN = 2 ** 44;\n\n/** The highest track priority the wire carries (a u8). */\nconst MAX_PRIORITY = 0xff;\n\n/**\n * What to rank a group stream by.\n *\n * @internal\n */\nexport interface Rank {\n\t/** The subscriber's track priority, which outweighs everything below it. */\n\tpriority: number;\n\n\t/**\n\t * Where the group sits in the queue its own subscription wants sent, 0 being the one to\n\t * send next. Defaults to 0, which is right for a stream that is the only one of its kind.\n\t */\n\tposition?: number;\n}\n\n/**\n * The transport send order for a group, where HIGHER values are transmitted first.\n *\n * A higher `priority` always wins. Below it, a group is ranked by its `position` in its own\n * subscription rather than by its sequence, so two tracks at the same priority interleave:\n * each one's next group ties with the other's, whatever their group numbering. Comparing\n * sequences instead would let a track that had been running longer, or that numbered its\n * groups from a clock, starve one that started later.\n *\n * @internal\n */\nexport function sendOrder({ priority, position = 0 }: Rank): number {\n\treturn -((MAX_PRIORITY - clamp(priority, MAX_PRIORITY)) * GROUP_SPAN + clamp(position, GROUP_SPAN - 1) + 1);\n}\n\n// Both ranks are bounded: the priority by its wire type, the position by the space left below\n// it. Anything outside is a caller bug rather than a value worth preserving.\nfunction clamp(value: number, max: number): number {\n\treturn Math.min(Math.max(Math.trunc(value), 0), max);\n}\n\n/**\n * Ranks one subscription's group streams against each other, and re-ranks them whenever the\n * set changes or the subscription is updated.\n *\n * A group's rank is its position among the groups in flight, so which group goes first is\n * decided here rather than by arithmetic on sequence numbers. Newest-first by default, since\n * that is what live playback wants; an `ordered` subscription is playing through in sequence,\n * so it gets the oldest group first instead.\n *\n * One listener covers the whole subscription. A listener per group would instead pile up on\n * it, and a track that stalls with many groups open would trip the signals leak guard.\n *\n * @internal\n */\nexport class Priority {\n\t#track: track.Subscriber;\n\t#streams = new Map<Writer, number>();\n\t#dispose: Dispose;\n\t#closed = false;\n\n\t/** Follow `track`'s subscription until {@link close}. */\n\tconstructor(track: track.Subscriber) {\n\t\tthis.#track = track;\n\t\tthis.#dispose = track.subscription.subscribe(() => this.#rerank());\n\t}\n\n\t/** The send order for a group at `sequence`, whether or not it has a stream yet. */\n\trank(sequence: number): number {\n\t\treturn sendOrder({\n\t\t\tpriority: this.#track.subscription.peek()?.priority ?? 0,\n\t\t\tposition: this.#position(sequence),\n\t\t});\n\t}\n\n\t/** Rank a group's stream now, and again whenever the ranking changes, until {@link remove}. */\n\tadd(stream: Writer, sequence: number) {\n\t\tthis.#streams.set(stream, sequence);\n\n\t\t// Also covers the stream itself: opening one can block on transport capacity, so an\n\t\t// update that landed while it did predates this registration.\n\t\tthis.#rerank();\n\t}\n\n\t/** Stop ranking a finished group's stream, promoting whatever was queued behind it. */\n\tremove(stream: Writer) {\n\t\tif (!this.#streams.delete(stream)) return;\n\n\t\tif (this.#closed && this.#streams.size === 0) {\n\t\t\tthis.#dispose();\n\t\t} else {\n\t\t\tthis.#rerank();\n\t\t}\n\t}\n\n\t/**\n\t * Stop taking new groups, and release the subscription listener once the last one leaves.\n\t *\n\t * The track can finish while several groups are still draining, and those are the ones the\n\t * subscriber is still waiting on. They keep being promoted as the groups ahead of them\n\t * finish, rather than being stranded at whatever position they held when the track ended.\n\t */\n\tclose() {\n\t\tthis.#closed = true;\n\t\tif (this.#streams.size === 0) this.#dispose();\n\t}\n\n\t// How many of this subscription's groups in flight should be sent before `sequence`.\n\t// Sequences are unique within a subscription, so a group already registered never counts\n\t// itself.\n\t#position(sequence: number): number {\n\t\tconst ordered = this.#track.subscription.peek()?.ordered ?? false;\n\n\t\tlet ahead = 0;\n\t\tfor (const other of this.#streams.values()) {\n\t\t\tif (ordered ? other < sequence : other > sequence) ahead++;\n\t\t}\n\t\treturn ahead;\n\t}\n\n\t#rerank() {\n\t\tconst priority = this.#track.subscription.peek()?.priority ?? 0;\n\t\tfor (const [stream, sequence] of this.#streams) {\n\t\t\tstream.setPriority(sendOrder({ priority, position: this.#position(sequence) }));\n\t\t}\n\t}\n}\n"]}
package/lite/probe.d.ts CHANGED
@@ -1,10 +1,26 @@
1
1
  import type { Reader, Writer } from "../stream";
2
2
  import { Version } from "./version";
3
+ /** The metrics a PROBE message carries. Each is independently optional. */
4
+ export interface ProbeInit {
5
+ /** Estimated send bitrate in bits per second. Omit if unknown. */
6
+ bitrate?: number;
7
+ /** Smoothed round-trip time in milliseconds. Omit if unknown. */
8
+ rtt?: number;
9
+ }
10
+ /**
11
+ * A PROBE message: the publisher's current view of the connection.
12
+ *
13
+ * Both metrics are independently optional and travel as 0 for unknown, so a
14
+ * transport exposing only one still has something to report. A measured 0 is
15
+ * rounded up to 1, since the wire cannot tell it from unknown.
16
+ */
3
17
  export declare class Probe {
4
18
  #private;
5
- bitrate: number;
19
+ /** Estimated send bitrate in bits per second, or undefined if unknown. */
20
+ bitrate?: number;
21
+ /** Smoothed round-trip time in milliseconds, or undefined if unknown. */
6
22
  rtt?: number;
7
- constructor(bitrate: number, rtt?: number);
23
+ constructor({ bitrate, rtt }?: ProbeInit);
8
24
  encode(w: Writer, version: Version): Promise<void>;
9
25
  static decode(r: Reader, version: Version): Promise<Probe>;
10
26
  static decodeMaybe(r: Reader, version: Version): Promise<Probe | undefined>;
@@ -1 +1 @@
1
- {"version":3,"file":"probe.d.ts","sourceRoot":"","sources":["../../src/lite/probe.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,cAAc,CAAC;AAEnD,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AAYvC,qBAAa,KAAK;;IACjB,OAAO,EAAE,MAAM,CAAC;IAChB,GAAG,CAAC,EAAE,MAAM,CAAC;IAEb,YAAY,OAAO,EAAE,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,EAGxC;IA+BK,MAAM,CAAC,CAAC,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAGvD;IAED,OAAa,MAAM,CAAC,CAAC,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,GAAG,OAAO,CAAC,KAAK,CAAC,CAG/D;IAED,OAAa,WAAW,CAAC,CAAC,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,GAAG,OAAO,CAAC,KAAK,GAAG,SAAS,CAAC,CAGhF;CACD"}
1
+ {"version":3,"file":"probe.d.ts","sourceRoot":"","sources":["../../src/lite/probe.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,cAAc,CAAC;AAEnD,OAAO,EAAe,OAAO,EAAE,MAAM,cAAc,CAAC;AAYpD,2EAA2E;AAC3E,MAAM,WAAW,SAAS;IACzB,kEAAkE;IAClE,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,iEAAiE;IACjE,GAAG,CAAC,EAAE,MAAM,CAAC;CACb;AAED;;;;;;GAMG;AACH,qBAAa,KAAK;;IACjB,0EAA0E;IAC1E,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,yEAAyE;IACzE,GAAG,CAAC,EAAE,MAAM,CAAC;IAIb,YAAY,EAAE,OAAO,EAAE,GAAG,EAAE,GAAE,SAAc,EAG3C;IAsBK,MAAM,CAAC,CAAC,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAGvD;IAED,OAAa,MAAM,CAAC,CAAC,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,GAAG,OAAO,CAAC,KAAK,CAAC,CAG/D;IAED,OAAa,WAAW,CAAC,CAAC,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,GAAG,OAAO,CAAC,KAAK,GAAG,SAAS,CAAC,CAGhF;CACD"}
package/lite/probe.js CHANGED
@@ -1,6 +1,6 @@
1
1
  /* @ts-self-types="./probe.d.ts" */
2
2
  import * as Message from "./message.js";
3
- import { Version } from "./version.js";
3
+ import { hasProbeRtt, Version } from "./version.js";
4
4
  function guardProbe(version) {
5
5
  switch (version) {
6
6
  case Version.DRAFT_01:
@@ -10,39 +10,41 @@ function guardProbe(version) {
10
10
  break;
11
11
  }
12
12
  }
13
+ /**
14
+ * A PROBE message: the publisher's current view of the connection.
15
+ *
16
+ * Both metrics are independently optional and travel as 0 for unknown, so a
17
+ * transport exposing only one still has something to report. A measured 0 is
18
+ * rounded up to 1, since the wire cannot tell it from unknown.
19
+ */
13
20
  export class Probe {
21
+ /** Estimated send bitrate in bits per second, or undefined if unknown. */
14
22
  bitrate;
23
+ /** Smoothed round-trip time in milliseconds, or undefined if unknown. */
15
24
  rtt;
16
- constructor(bitrate, rtt) {
25
+ // Named rather than positional: the two fields share a type, so positional
26
+ // arguments could be swapped without a type error.
27
+ constructor({ bitrate, rtt } = {}) {
17
28
  this.bitrate = bitrate;
18
29
  this.rtt = rtt;
19
30
  }
20
31
  async #encode(w, version) {
21
- await w.u53(this.bitrate);
22
- switch (version) {
23
- case Version.DRAFT_03:
24
- break;
25
- default: {
26
- // 0 means unknown; round Some(0) up to 1.
27
- const wire = this.rtt !== undefined ? Math.max(this.rtt, 1) : 0;
28
- await w.u53(wire);
29
- break;
30
- }
32
+ // 0 means unknown; round a measured 0 up to 1.
33
+ await w.u53(this.bitrate !== undefined ? Math.max(this.bitrate, 1) : 0);
34
+ if (hasProbeRtt(version)) {
35
+ await w.u53(this.rtt !== undefined ? Math.max(this.rtt, 1) : 0);
31
36
  }
32
37
  }
33
38
  static async #decode(r, version) {
34
- const bitrate = await r.u53();
39
+ // 0 means unknown, the same as the RTT below.
40
+ const bitrateWire = await r.u53();
41
+ const bitrate = bitrateWire === 0 ? undefined : bitrateWire;
35
42
  let rtt;
36
- switch (version) {
37
- case Version.DRAFT_03:
38
- break;
39
- default: {
40
- const wire = await r.u53();
41
- rtt = wire === 0 ? undefined : wire;
42
- break;
43
- }
43
+ if (hasProbeRtt(version)) {
44
+ const wire = await r.u53();
45
+ rtt = wire === 0 ? undefined : wire;
44
46
  }
45
- return new Probe(bitrate, rtt);
47
+ return new Probe({ bitrate, rtt });
46
48
  }
47
49
  async encode(w, version) {
48
50
  guardProbe(version);
package/lite/probe.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"probe.js","sourceRoot":"","sources":["../../src/lite/probe.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,OAAO,MAAM,cAAc,CAAC;AACxC,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AAEvC,SAAS,UAAU,CAAC,OAAgB;IACnC,QAAQ,OAAO,EAAE,CAAC;QACjB,KAAK,OAAO,CAAC,QAAQ,CAAC;QACtB,KAAK,OAAO,CAAC,QAAQ;YACpB,MAAM,IAAI,KAAK,CAAC,sCAAsC,CAAC,CAAC;QACzD;YACC,MAAM;IACR,CAAC;AACF,CAAC;AAED,MAAM,OAAO,KAAK;IACjB,OAAO,CAAS;IAChB,GAAG,CAAU;IAEb,YAAY,OAAe,EAAE,GAAY;QACxC,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC;QACvB,IAAI,CAAC,GAAG,GAAG,GAAG,CAAC;IAChB,CAAC;IAED,KAAK,CAAC,OAAO,CAAC,CAAS,EAAE,OAAgB;QACxC,MAAM,CAAC,CAAC,GAAG,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QAC1B,QAAQ,OAAO,EAAE,CAAC;YACjB,KAAK,OAAO,CAAC,QAAQ;gBACpB,MAAM;YACP,SAAS,CAAC;gBACT,0CAA0C;gBAC1C,MAAM,IAAI,GAAG,IAAI,CAAC,GAAG,KAAK,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,GAAG,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;gBAChE,MAAM,CAAC,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;gBAClB,MAAM;YACP,CAAC;QACF,CAAC;IACF,CAAC;IAED,MAAM,CAAC,KAAK,CAAC,OAAO,CAAC,CAAS,EAAE,OAAgB;QAC/C,MAAM,OAAO,GAAG,MAAM,CAAC,CAAC,GAAG,EAAE,CAAC;QAC9B,IAAI,GAAuB,CAAC;QAC5B,QAAQ,OAAO,EAAE,CAAC;YACjB,KAAK,OAAO,CAAC,QAAQ;gBACpB,MAAM;YACP,SAAS,CAAC;gBACT,MAAM,IAAI,GAAG,MAAM,CAAC,CAAC,GAAG,EAAE,CAAC;gBAC3B,GAAG,GAAG,IAAI,KAAK,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC;gBACpC,MAAM;YACP,CAAC;QACF,CAAC;QACD,OAAO,IAAI,KAAK,CAAC,OAAO,EAAE,GAAG,CAAC,CAAC;IAChC,CAAC;IAED,KAAK,CAAC,MAAM,CAAC,CAAS,EAAE,OAAgB;QACvC,UAAU,CAAC,OAAO,CAAC,CAAC;QACpB,OAAO,OAAO,CAAC,MAAM,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC,CAAC;IAC3D,CAAC;IAED,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,CAAS,EAAE,OAAgB;QAC9C,UAAU,CAAC,OAAO,CAAC,CAAC;QACpB,OAAO,OAAO,CAAC,MAAM,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC,CAAC;IAC5D,CAAC;IAED,MAAM,CAAC,KAAK,CAAC,WAAW,CAAC,CAAS,EAAE,OAAgB;QACnD,UAAU,CAAC,OAAO,CAAC,CAAC;QACpB,OAAO,OAAO,CAAC,WAAW,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC,CAAC;IACjE,CAAC;CACD","sourcesContent":["import type { Reader, Writer } from \"../stream.ts\";\nimport * as Message from \"./message.ts\";\nimport { Version } from \"./version.ts\";\n\nfunction guardProbe(version: Version) {\n\tswitch (version) {\n\t\tcase Version.DRAFT_01:\n\t\tcase Version.DRAFT_02:\n\t\t\tthrow new Error(\"probe not supported for this version\");\n\t\tdefault:\n\t\t\tbreak;\n\t}\n}\n\nexport class Probe {\n\tbitrate: number;\n\trtt?: number;\n\n\tconstructor(bitrate: number, rtt?: number) {\n\t\tthis.bitrate = bitrate;\n\t\tthis.rtt = rtt;\n\t}\n\n\tasync #encode(w: Writer, version: Version) {\n\t\tawait w.u53(this.bitrate);\n\t\tswitch (version) {\n\t\t\tcase Version.DRAFT_03:\n\t\t\t\tbreak;\n\t\t\tdefault: {\n\t\t\t\t// 0 means unknown; round Some(0) up to 1.\n\t\t\t\tconst wire = this.rtt !== undefined ? Math.max(this.rtt, 1) : 0;\n\t\t\t\tawait w.u53(wire);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\tstatic async #decode(r: Reader, version: Version): Promise<Probe> {\n\t\tconst bitrate = await r.u53();\n\t\tlet rtt: number | undefined;\n\t\tswitch (version) {\n\t\t\tcase Version.DRAFT_03:\n\t\t\t\tbreak;\n\t\t\tdefault: {\n\t\t\t\tconst wire = await r.u53();\n\t\t\t\trtt = wire === 0 ? undefined : wire;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\treturn new Probe(bitrate, rtt);\n\t}\n\n\tasync encode(w: Writer, version: Version): Promise<void> {\n\t\tguardProbe(version);\n\t\treturn Message.encode(w, (w) => this.#encode(w, version));\n\t}\n\n\tstatic async decode(r: Reader, version: Version): Promise<Probe> {\n\t\tguardProbe(version);\n\t\treturn Message.decode(r, (r) => Probe.#decode(r, version));\n\t}\n\n\tstatic async decodeMaybe(r: Reader, version: Version): Promise<Probe | undefined> {\n\t\tguardProbe(version);\n\t\treturn Message.decodeMaybe(r, (r) => Probe.#decode(r, version));\n\t}\n}\n"]}
1
+ {"version":3,"file":"probe.js","sourceRoot":"","sources":["../../src/lite/probe.ts"],"names":[],"mappings":"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","sourcesContent":["import type { Reader, Writer } from \"../stream.ts\";\nimport * as Message from \"./message.ts\";\nimport { hasProbeRtt, Version } from \"./version.ts\";\n\nfunction guardProbe(version: Version) {\n\tswitch (version) {\n\t\tcase Version.DRAFT_01:\n\t\tcase Version.DRAFT_02:\n\t\t\tthrow new Error(\"probe not supported for this version\");\n\t\tdefault:\n\t\t\tbreak;\n\t}\n}\n\n/** The metrics a PROBE message carries. Each is independently optional. */\nexport interface ProbeInit {\n\t/** Estimated send bitrate in bits per second. Omit if unknown. */\n\tbitrate?: number;\n\t/** Smoothed round-trip time in milliseconds. Omit if unknown. */\n\trtt?: number;\n}\n\n/**\n * A PROBE message: the publisher's current view of the connection.\n *\n * Both metrics are independently optional and travel as 0 for unknown, so a\n * transport exposing only one still has something to report. A measured 0 is\n * rounded up to 1, since the wire cannot tell it from unknown.\n */\nexport class Probe {\n\t/** Estimated send bitrate in bits per second, or undefined if unknown. */\n\tbitrate?: number;\n\t/** Smoothed round-trip time in milliseconds, or undefined if unknown. */\n\trtt?: number;\n\n\t// Named rather than positional: the two fields share a type, so positional\n\t// arguments could be swapped without a type error.\n\tconstructor({ bitrate, rtt }: ProbeInit = {}) {\n\t\tthis.bitrate = bitrate;\n\t\tthis.rtt = rtt;\n\t}\n\n\tasync #encode(w: Writer, version: Version) {\n\t\t// 0 means unknown; round a measured 0 up to 1.\n\t\tawait w.u53(this.bitrate !== undefined ? Math.max(this.bitrate, 1) : 0);\n\t\tif (hasProbeRtt(version)) {\n\t\t\tawait w.u53(this.rtt !== undefined ? Math.max(this.rtt, 1) : 0);\n\t\t}\n\t}\n\n\tstatic async #decode(r: Reader, version: Version): Promise<Probe> {\n\t\t// 0 means unknown, the same as the RTT below.\n\t\tconst bitrateWire = await r.u53();\n\t\tconst bitrate = bitrateWire === 0 ? undefined : bitrateWire;\n\t\tlet rtt: number | undefined;\n\t\tif (hasProbeRtt(version)) {\n\t\t\tconst wire = await r.u53();\n\t\t\trtt = wire === 0 ? undefined : wire;\n\t\t}\n\t\treturn new Probe({ bitrate, rtt });\n\t}\n\n\tasync encode(w: Writer, version: Version): Promise<void> {\n\t\tguardProbe(version);\n\t\treturn Message.encode(w, (w) => this.#encode(w, version));\n\t}\n\n\tstatic async decode(r: Reader, version: Version): Promise<Probe> {\n\t\tguardProbe(version);\n\t\treturn Message.decode(r, (r) => Probe.#decode(r, version));\n\t}\n\n\tstatic async decodeMaybe(r: Reader, version: Version): Promise<Probe | undefined> {\n\t\tguardProbe(version);\n\t\treturn Message.decodeMaybe(r, (r) => Probe.#decode(r, version));\n\t}\n}\n"]}
@@ -1,10 +1,11 @@
1
- import type { Broadcast } from "../broadcast";
1
+ import type * as broadcast from "../broadcast";
2
+ import type { Origin } from "../origin";
2
3
  import * as Path from "../path";
3
4
  import { type Stream } from "../stream";
4
- import { type AnnounceInterest } from "./announce";
5
- import type { Origin } from "./origin";
5
+ import { type AnnounceRequest } from "./announce";
6
+ import type { Fetch } from "./fetch";
6
7
  import { type Subscribe } from "./subscribe";
7
- import type { Track as TrackMessage } from "./track";
8
+ import { type Track as TrackMessage } from "./track";
8
9
  import { Version } from "./version";
9
10
  /**
10
11
  * Handles publishing broadcasts and managing their lifecycle.
@@ -28,7 +29,7 @@ export declare class Publisher {
28
29
  * Publishes a broadcast with any associated tracks.
29
30
  * @param name - The broadcast to publish
30
31
  */
31
- publish(path: Path.Valid, broadcast: Broadcast): void;
32
+ publish(path: Path.Valid, broadcast: broadcast.Producer): void;
32
33
  /**
33
34
  * Handles an announce interest message.
34
35
  * @param msg - The announce interest message
@@ -36,7 +37,7 @@ export declare class Publisher {
36
37
  *
37
38
  * @internal
38
39
  */
39
- runAnnounce(msg: AnnounceInterest, stream: Stream): Promise<void>;
40
+ runAnnounce(msg: AnnounceRequest, stream: Stream): Promise<void>;
40
41
  /**
41
42
  * Handles a subscribe message.
42
43
  * @param msg - The subscribe message
@@ -46,7 +47,13 @@ export declare class Publisher {
46
47
  */
47
48
  runSubscribe(msg: Subscribe, stream: Stream): Promise<void>;
48
49
  /**
49
- * Serves a Track stream (moq-lite-05+): replies with the track's immutable TRACK_INFO.
50
+ * Handles a FETCH stream by serving one group as bare frame records (lite-05+).
51
+ *
52
+ * @internal
53
+ */
54
+ runFetch(msg: Fetch, stream: Stream): Promise<void>;
55
+ /**
56
+ * Answers a TRACK stream (0x6) with a single TRACK_INFO, then FINs.
50
57
  *
51
58
  * @internal
52
59
  */
@@ -1 +1 @@
1
- {"version":3,"file":"publisher.d.ts","sourceRoot":"","sources":["../../src/lite/publisher.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,iBAAiB,CAAC;AAEjD,OAAO,KAAK,IAAI,MAAM,YAAY,CAAC;AACnC,OAAO,EAAE,KAAK,MAAM,EAAU,MAAM,cAAc,CAAC;AAGnD,OAAO,EAA0B,KAAK,gBAAgB,EAAE,MAAM,eAAe,CAAC;AAE9E,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AAE1C,OAAO,EAA2B,KAAK,SAAS,EAA8C,MAAM,gBAAgB,CAAC;AACrH,OAAO,KAAK,EAAE,KAAK,IAAI,YAAY,EAAE,MAAM,YAAY,CAAC;AAExD,OAAO,EAAkB,OAAO,EAAE,MAAM,cAAc,CAAC;AAMvD;;;;GAIG;AACH,qBAAa,SAAS;;IAErB,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAC;IAM1B,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IAQxB;;;;;;;OAOG;IACH,YAAY,IAAI,EAAE,YAAY,EAAE,OAAO,EAAE,OAAO,EAAE,MAAM,EAAE,MAAM,EAI/D;IAED;;;OAGG;IACH,OAAO,CAAC,IAAI,EAAE,IAAI,CAAC,KAAK,EAAE,SAAS,EAAE,SAAS,QAY7C;IAED;;;;;;OAMG;IACG,WAAW,CAAC,GAAG,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM,iBA0EtD;IAED;;;;;;OAMG;IACG,YAAY,CAAC,GAAG,EAAE,SAAS,EAAE,MAAM,EAAE,MAAM,iBA6ChD;IAED;;;;OAIG;IACG,YAAY,CAAC,GAAG,EAAE,YAAY,EAAE,MAAM,EAAE,MAAM,iBAUnD;IAmGD;;;;;OAKG;IACG,QAAQ,CAAC,MAAM,EAAE,MAAM,iBAmD5B;IAED,KAAK,SAOJ;CACD"}
1
+ {"version":3,"file":"publisher.d.ts","sourceRoot":"","sources":["../../src/lite/publisher.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,KAAK,SAAS,MAAM,iBAAiB,CAAC;AAGlD,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,cAAc,CAAC;AAC3C,OAAO,KAAK,IAAI,MAAM,YAAY,CAAC;AACnC,OAAO,EAAE,KAAK,MAAM,EAAU,MAAM,cAAc,CAAC;AAGnD,OAAO,EAA4B,KAAK,eAAe,EAA2B,MAAM,eAAe,CAAC;AAGxG,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AAIxC,OAAO,EAEN,KAAK,SAAS,EAKd,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAiC,KAAK,KAAK,IAAI,YAAY,EAAE,MAAM,YAAY,CAAC;AACvF,OAAO,EAA2D,OAAO,EAAE,MAAM,cAAc,CAAC;AA4ChG;;;;GAIG;AACH,qBAAa,SAAS;;IAErB,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAC;IAM1B,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IAoBxB;;;;;;;OAOG;IACH,YAAY,IAAI,EAAE,YAAY,EAAE,OAAO,EAAE,OAAO,EAAE,MAAM,EAAE,MAAM,EAU/D;IAED;;;OAGG;IACH,OAAO,CAAC,IAAI,EAAE,IAAI,CAAC,KAAK,EAAE,SAAS,EAAE,SAAS,CAAC,QAAQ,QActD;IAED;;;;;;OAMG;IACG,WAAW,CAAC,GAAG,EAAE,eAAe,EAAE,MAAM,EAAE,MAAM,iBA2GrD;IAED;;;;;;OAMG;IACG,YAAY,CAAC,GAAG,EAAE,SAAS,EAAE,MAAM,EAAE,MAAM,iBA6FhD;IAED;;;;OAIG;IACG,QAAQ,CAAC,GAAG,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,iBAkCxC;IAsFD;;;;OAIG;IACG,YAAY,CAAC,GAAG,EAAE,YAAY,EAAE,MAAM,EAAE,MAAM,iBAUnD;IAgKD;;;;;OAKG;IACG,QAAQ,CAAC,MAAM,EAAE,MAAM,iBAiF5B;IAED,KAAK,SAWJ;CACD"}