@zlink-systems/framework 0.29.1 → 0.30.1

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 (322) hide show
  1. package/LICENSE +150 -68
  2. package/dist/.tsbuildinfo +1 -1
  3. package/dist/contracts/Actors/ZLinkActorClient.d.ts +2 -1
  4. package/dist/contracts/Channels/Calls.d.ts +2 -1
  5. package/dist/contracts/Common/ZLinkMessageMetadata.js +11 -5
  6. package/dist/contracts/Configuration/Builders.d.ts +1 -2
  7. package/dist/contracts/Configuration/Configs.d.ts +0 -5
  8. package/dist/contracts/Configuration/RegistrationBuilders.js +6 -4
  9. package/dist/contracts/Configuration/RegistrationTypes.d.ts +1 -6
  10. package/dist/contracts/Configuration/RegistrationValidators.js +4 -4
  11. package/dist/contracts/Configuration/index.d.ts +1 -1
  12. package/dist/contracts/Handlers/Attributes.d.ts +5 -13
  13. package/dist/contracts/Handlers/Attributes.js +7 -11
  14. package/dist/contracts/Handlers/JsonContract.d.ts +2 -46
  15. package/dist/contracts/Handlers/JsonContract.js +4 -153
  16. package/dist/contracts/Spots/Contracts.d.ts +2 -1
  17. package/dist/internal.d.ts +1 -0
  18. package/dist/internal.js +3 -1
  19. package/dist/nest-integration.d.ts +1 -1
  20. package/dist/nest-integration.js +2 -1
  21. package/dist/runtime/actors/actor-client.d.ts +1 -1
  22. package/dist/runtime/actors/actor-client.js +14 -12
  23. package/dist/runtime/actors/actor-handoff.d.ts +3 -2
  24. package/dist/runtime/actors/actor-handoff.js +15 -7
  25. package/dist/runtime/actors/actor-join-relocation.d.ts +1 -0
  26. package/dist/runtime/actors/actor-local-native-join.js +9 -12
  27. package/dist/runtime/actors/actor-remote-wire.js +15 -0
  28. package/dist/runtime/actors/actor-routed-join-transport.d.ts +6 -2
  29. package/dist/runtime/actors/actor-routed-json-request.d.ts +2 -0
  30. package/dist/runtime/actors/index.d.ts +2 -1
  31. package/dist/runtime/actors/index.js +18 -6
  32. package/dist/runtime/actors/spot-actor-dispatch.js +2 -2
  33. package/dist/runtime/admission.d.ts +1 -1
  34. package/dist/runtime/admission.js +15 -5
  35. package/dist/runtime/application-jobs/application-ingress-record-owner.d.ts +9 -9
  36. package/dist/runtime/application-jobs/application-ingress-record-owner.js +45 -23
  37. package/dist/runtime/application-jobs/application-job-queue-scope.d.ts +5 -2
  38. package/dist/runtime/application-jobs/application-job-queue-scope.js +41 -21
  39. package/dist/runtime/application-jobs/contracts.d.ts +15 -2
  40. package/dist/runtime/backend/contracts/index.d.ts +27 -27
  41. package/dist/runtime/backend/mesh-completion-table.d.ts +15 -5
  42. package/dist/runtime/backend/mesh-completion-table.js +160 -50
  43. package/dist/runtime/backend/mesh-dispatch-pump.d.ts +3 -0
  44. package/dist/runtime/backend/mesh-dispatch-pump.js +53 -36
  45. package/dist/runtime/backend/node/node-backend-adapter-factory.js +6 -1
  46. package/dist/runtime/backend/node/node-backend-adapter-support.d.ts +3 -3
  47. package/dist/runtime/backend/node/node-backend-adapter-support.js +33 -31
  48. package/dist/runtime/backend/node/node-dealer-channel-client-transport.d.ts +1 -1
  49. package/dist/runtime/backend/node/node-dealer-channel-client-transport.js +5 -2
  50. package/dist/runtime/backend/node/node-mesh-backend-adapter.d.ts +1 -9
  51. package/dist/runtime/backend/node/node-mesh-backend-adapter.js +1 -1
  52. package/dist/runtime/backend/node/node-raw-binding-port.js +50 -25
  53. package/dist/runtime/backend/node/node-raw-mesh-backend.d.ts +22 -16
  54. package/dist/runtime/backend/node/node-raw-mesh-backend.js +133 -149
  55. package/dist/runtime/backend/node/node-socket-backend-adapter.js +15 -10
  56. package/dist/runtime/backend/raw-binding-port.d.ts +10 -3
  57. package/dist/runtime/backend/runtime-message.d.ts +1 -0
  58. package/dist/runtime/backend/runtime-message.js +5 -0
  59. package/dist/runtime/backend/runtime-values.d.ts +1 -0
  60. package/dist/runtime/backend/runtime-values.js +2 -1
  61. package/dist/runtime/channels/channel-clients.d.ts +1 -0
  62. package/dist/runtime/channels/channel-clients.js +58 -21
  63. package/dist/runtime/channels/channel-dispatch-pipeline.d.ts +3 -2
  64. package/dist/runtime/channels/channel-dispatch-pipeline.js +20 -11
  65. package/dist/runtime/channels/channel-dispatch-services.d.ts +1 -0
  66. package/dist/runtime/channels/channel-dispatch-services.js +45 -0
  67. package/dist/runtime/channels/channel-dispatchers.d.ts +1 -1
  68. package/dist/runtime/channels/channel-dispatchers.js +27 -26
  69. package/dist/runtime/channels/channel-envelope-inspection.d.ts +1 -2
  70. package/dist/runtime/channels/channel-envelope-inspection.js +1 -16
  71. package/dist/runtime/channels/channel-envelope.d.ts +1 -0
  72. package/dist/runtime/channels/channel-envelope.js +83 -8
  73. package/dist/runtime/channels/channel-outbound-operations.d.ts +2 -2
  74. package/dist/runtime/channels/channel-outbound-operations.js +8 -8
  75. package/dist/runtime/channels/channel-receive-loops.js +3 -3
  76. package/dist/runtime/channels/channel-runtime-lifecycle.js +2 -1
  77. package/dist/runtime/channels/channel-runtime-manager.d.ts +6 -6
  78. package/dist/runtime/channels/channel-runtime-manager.js +12 -12
  79. package/dist/runtime/channels/channel-socket-registry.d.ts +10 -3
  80. package/dist/runtime/channels/channel-socket-registry.js +59 -82
  81. package/dist/runtime/channels/channel-transports.d.ts +18 -15
  82. package/dist/runtime/channels/channel-transports.js +48 -31
  83. package/dist/runtime/channels/local-spot-route-transport.d.ts +1 -1
  84. package/dist/runtime/channels/local-spot-route-transport.js +2 -1
  85. package/dist/runtime/channels/router-socket-spot-route-transport.d.ts +2 -2
  86. package/dist/runtime/channels/router-socket-spot-route-transport.js +4 -4
  87. package/dist/runtime/channels/source-spot-router.d.ts +2 -2
  88. package/dist/runtime/channels/source-spot-router.js +4 -4
  89. package/dist/runtime/channels/spot-node-route-transport.d.ts +2 -2
  90. package/dist/runtime/channels/spot-node-route-transport.js +4 -4
  91. package/dist/runtime/channels/spot-route-bridge-transport.d.ts +2 -2
  92. package/dist/runtime/channels/spot-route-bridge-transport.js +4 -4
  93. package/dist/runtime/channels/spot-route-dispatch-strategy.d.ts +5 -4
  94. package/dist/runtime/channels/spot-route-dispatch-strategy.js +18 -18
  95. package/dist/runtime/diagnostics/message-flow.d.ts +1 -0
  96. package/dist/runtime/diagnostics/message-flow.js +3 -3
  97. package/dist/runtime/execution/serial-execution-queue.d.ts +1 -0
  98. package/dist/runtime/execution/serial-execution-queue.js +1 -0
  99. package/dist/runtime/foundation/actor-join-recovery-codec.js +2 -2
  100. package/dist/runtime/foundation/durable-service-request.d.ts +14 -0
  101. package/dist/runtime/foundation/durable-service-request.js +98 -0
  102. package/dist/runtime/foundation/operation-identity.d.ts +1 -0
  103. package/dist/runtime/foundation/operation-identity.js +5 -1
  104. package/dist/runtime/foundation/raw-service-mesh-runtime.d.ts +37 -6
  105. package/dist/runtime/foundation/raw-service-mesh-runtime.js +473 -220
  106. package/dist/runtime/foundation/service-liveness-registry.d.ts +20 -8
  107. package/dist/runtime/foundation/service-liveness-registry.js +57 -44
  108. package/dist/runtime/foundation/service-mailbox.d.ts +3 -0
  109. package/dist/runtime/foundation/service-mailbox.js +2 -1
  110. package/dist/runtime/foundation/service-relocation-object-owner.d.ts +1 -0
  111. package/dist/runtime/foundation/service-relocation-object-owner.js +1 -0
  112. package/dist/runtime/foundation/service-relocation-runtime.d.ts +2 -0
  113. package/dist/runtime/foundation/service-relocation-runtime.js +13 -1
  114. package/dist/runtime/foundation/service-runtime-contracts.d.ts +2 -0
  115. package/dist/runtime/foundation/service-stateful-runtime.d.ts +10 -9
  116. package/dist/runtime/foundation/service-stateful-runtime.js +78 -126
  117. package/dist/runtime/foundation/service-stateful-wire-codec.d.ts +5 -7
  118. package/dist/runtime/foundation/service-stateful-wire-codec.js +43 -61
  119. package/dist/runtime/foundation/service-topology-registry.d.ts +16 -4
  120. package/dist/runtime/foundation/service-topology-registry.js +69 -30
  121. package/dist/runtime/foundation/service-wire-m6a-codec.d.ts +3 -3
  122. package/dist/runtime/foundation/service-wire-m6a-codec.js +36 -38
  123. package/dist/runtime/handlers/handler-instance-scope.d.ts +8 -0
  124. package/dist/runtime/handlers/handler-instance-scope.js +54 -11
  125. package/dist/runtime/host/actor-packet-relay.js +7 -7
  126. package/dist/runtime/host/actor-runtime-options-factory.js +2 -2
  127. package/dist/runtime/host/application-job-queue.d.ts +28 -9
  128. package/dist/runtime/host/application-job-queue.js +214 -50
  129. package/dist/runtime/host/entry-actor-runtime.d.ts +1 -0
  130. package/dist/runtime/host/entry-actor-runtime.js +4 -1
  131. package/dist/runtime/host/index.d.ts +7 -1
  132. package/dist/runtime/host/index.js +154 -126
  133. package/dist/runtime/host/instance-activation-authority.d.ts +2 -1
  134. package/dist/runtime/host/instance-activation-authority.js +89 -25
  135. package/dist/runtime/host/remote-bound-session-relay.js +2 -18
  136. package/dist/runtime/host/route-mesh-runtime.js +1 -1
  137. package/dist/runtime/host/service-relocation-control.d.ts +1 -0
  138. package/dist/runtime/host/service-relocation-control.js +10 -4
  139. package/dist/runtime/host/service-relocation-host-runtime.d.ts +6 -8
  140. package/dist/runtime/host/service-relocation-host-runtime.js +215 -243
  141. package/dist/runtime/host/spot-address-transport.d.ts +1 -0
  142. package/dist/runtime/host/spot-address-transport.js +28 -14
  143. package/dist/runtime/host/spot-runtime-options-factory.js +3 -2
  144. package/dist/runtime/host/user-spot-creation-coordinator.d.ts +1 -0
  145. package/dist/runtime/host/user-spot-creation-coordinator.js +1 -0
  146. package/dist/runtime/locations/actor-location-claims.d.ts +2 -2
  147. package/dist/runtime/locations/actor-location-claims.js +34 -19
  148. package/dist/runtime/locations/domain-store-contract.d.ts +2 -2
  149. package/dist/runtime/locations/in-memory-authority-store.d.ts +4 -2
  150. package/dist/runtime/locations/in-memory-authority-store.js +80 -8
  151. package/dist/runtime/locations/in-memory-location-store.d.ts +2 -2
  152. package/dist/runtime/locations/in-memory-location-store.js +19 -3
  153. package/dist/runtime/locations/internal-location-contracts.d.ts +3 -0
  154. package/dist/runtime/locations/lifecycle.d.ts +1 -2
  155. package/dist/runtime/locations/lifecycle.js +2 -5
  156. package/dist/runtime/locations/location-store-repository.d.ts +3 -2
  157. package/dist/runtime/locations/location-store-repository.js +165 -22
  158. package/dist/runtime/locations/resolvers.d.ts +2 -1
  159. package/dist/runtime/locations/resolvers.js +10 -1
  160. package/dist/runtime/locations/runtime.d.ts +1 -1
  161. package/dist/runtime/locations/runtime.js +24 -23
  162. package/dist/runtime/messaging/framework-json-v1.d.ts +4 -6
  163. package/dist/runtime/messaging/framework-json-v1.js +38 -294
  164. package/dist/runtime/messaging/packet-name.d.ts +1 -1
  165. package/dist/runtime/messaging/packet-name.js +8 -24
  166. package/dist/runtime/messaging/request-result.d.ts +2 -0
  167. package/dist/runtime/messaging/request-result.js +54 -0
  168. package/dist/runtime/messaging/submission-result.d.ts +2 -1
  169. package/dist/runtime/messaging/submission-result.js +7 -4
  170. package/dist/runtime/protocol/service_wire_codec.generated.d.ts +15 -0
  171. package/dist/runtime/protocol/service_wire_codec.generated.js +144 -0
  172. package/dist/runtime/protocol/service_wire_pilot_codec.generated.d.ts +9 -0
  173. package/dist/runtime/protocol/service_wire_pilot_codec.generated.js +14 -1
  174. package/dist/runtime/spots/formal-remote-actor-admission-registry.d.ts +9 -2
  175. package/dist/runtime/spots/formal-remote-actor-admission-registry.js +33 -19
  176. package/dist/runtime/spots/index.d.ts +7 -3
  177. package/dist/runtime/spots/index.js +23 -16
  178. package/dist/runtime/spots/spot-activation.d.ts +3 -1
  179. package/dist/runtime/spots/spot-activation.js +21 -12
  180. package/dist/runtime/spots/spot-actor-admission-coordinator.d.ts +2 -1
  181. package/dist/runtime/spots/spot-actor-admission-coordinator.js +11 -10
  182. package/dist/runtime/spots/spot-actor-packet-dispatch.d.ts +4 -1
  183. package/dist/runtime/spots/spot-actor-packet-dispatch.js +7 -5
  184. package/dist/runtime/spots/spot-actor-packet-drain.js +2 -0
  185. package/dist/runtime/spots/spot-actor-packet-relay-dispatch.js +1 -0
  186. package/dist/runtime/spots/spot-entry-activation.js +9 -3
  187. package/dist/runtime/spots/spot-handler-registry.d.ts +3 -1
  188. package/dist/runtime/spots/spot-handler-registry.js +18 -8
  189. package/dist/runtime/spots/spot-node-autoconnect.js +4 -3
  190. package/dist/runtime/spots/spot-node-runtime-manager.d.ts +2 -1
  191. package/dist/runtime/spots/spot-node-runtime-manager.js +4 -11
  192. package/dist/runtime/spots/spot-outbound.d.ts +3 -0
  193. package/dist/runtime/spots/spot-outbound.js +24 -15
  194. package/dist/runtime/spots/spot-routed-spot-packet-dispatch.d.ts +1 -0
  195. package/dist/runtime/spots/spot-routed-spot-packet-dispatch.js +1 -1
  196. package/dist/runtime/spots/spot-routing-internal.d.ts +6 -0
  197. package/dist/runtime/spots/spot-runtime-ports.d.ts +3 -1
  198. package/dist/runtime/spots/spot-subscription-dispatch.js +0 -3
  199. package/dist/runtime/spots/spot-timer.js +1 -0
  200. package/dist/runtime/streams/stream-session-runtime.d.ts +1 -1
  201. package/dist/runtime/streams/stream-session-runtime.js +14 -28
  202. package/package.json +3 -3
  203. package/src/contracts/Actors/ZLinkActorClient.ts +2 -1
  204. package/src/contracts/Channels/Calls.ts +2 -1
  205. package/src/contracts/Common/ZLinkMessageMetadata.ts +13 -8
  206. package/src/contracts/Configuration/Builders.ts +1 -2
  207. package/src/contracts/Configuration/Configs.ts +0 -6
  208. package/src/contracts/Configuration/RegistrationBuilders.ts +8 -12
  209. package/src/contracts/Configuration/RegistrationTypes.ts +1 -6
  210. package/src/contracts/Configuration/RegistrationValidators.ts +9 -10
  211. package/src/contracts/Configuration/index.ts +1 -6
  212. package/src/contracts/Handlers/Attributes.ts +14 -21
  213. package/src/contracts/Handlers/JsonContract.ts +8 -216
  214. package/src/contracts/Spots/Contracts.ts +2 -1
  215. package/src/internal.ts +1 -0
  216. package/src/nest-integration.ts +1 -0
  217. package/src/runtime/actors/actor-client.ts +40 -16
  218. package/src/runtime/actors/actor-handoff.ts +22 -8
  219. package/src/runtime/actors/actor-join-relocation.ts +1 -0
  220. package/src/runtime/actors/actor-local-native-join.ts +17 -26
  221. package/src/runtime/actors/actor-remote-wire.ts +17 -0
  222. package/src/runtime/actors/actor-routed-join-transport.ts +14 -4
  223. package/src/runtime/actors/actor-routed-json-request.ts +10 -2
  224. package/src/runtime/actors/index.ts +19 -5
  225. package/src/runtime/actors/spot-actor-dispatch.ts +4 -2
  226. package/src/runtime/admission.ts +18 -5
  227. package/src/runtime/application-jobs/application-ingress-record-owner.ts +53 -27
  228. package/src/runtime/application-jobs/application-job-queue-scope.ts +56 -22
  229. package/src/runtime/application-jobs/contracts.ts +28 -2
  230. package/src/runtime/backend/contracts/index.ts +63 -32
  231. package/src/runtime/backend/mesh-completion-table.ts +175 -59
  232. package/src/runtime/backend/mesh-dispatch-pump.ts +59 -32
  233. package/src/runtime/backend/node/node-backend-adapter-factory.ts +12 -5
  234. package/src/runtime/backend/node/node-backend-adapter-support.ts +42 -31
  235. package/src/runtime/backend/node/node-dealer-channel-client-transport.ts +12 -2
  236. package/src/runtime/backend/node/node-mesh-backend-adapter.ts +3 -10
  237. package/src/runtime/backend/node/node-raw-binding-port.ts +73 -37
  238. package/src/runtime/backend/node/node-raw-mesh-backend.ts +209 -176
  239. package/src/runtime/backend/node/node-socket-backend-adapter.ts +32 -13
  240. package/src/runtime/backend/raw-binding-port.ts +18 -3
  241. package/src/runtime/backend/runtime-message.ts +6 -0
  242. package/src/runtime/backend/runtime-values.ts +1 -0
  243. package/src/runtime/channels/channel-clients.ts +90 -41
  244. package/src/runtime/channels/channel-dispatch-pipeline.ts +69 -34
  245. package/src/runtime/channels/channel-dispatch-services.ts +69 -1
  246. package/src/runtime/channels/channel-dispatchers.ts +29 -27
  247. package/src/runtime/channels/channel-envelope-inspection.ts +2 -16
  248. package/src/runtime/channels/channel-envelope.ts +133 -8
  249. package/src/runtime/channels/channel-outbound-operations.ts +22 -8
  250. package/src/runtime/channels/channel-receive-loops.ts +3 -3
  251. package/src/runtime/channels/channel-runtime-lifecycle.ts +7 -1
  252. package/src/runtime/channels/channel-runtime-manager.ts +29 -12
  253. package/src/runtime/channels/channel-socket-registry.ts +84 -130
  254. package/src/runtime/channels/channel-transports.ts +128 -60
  255. package/src/runtime/channels/local-spot-route-transport.ts +3 -1
  256. package/src/runtime/channels/router-socket-spot-route-transport.ts +13 -4
  257. package/src/runtime/channels/source-spot-router.ts +8 -4
  258. package/src/runtime/channels/spot-node-route-transport.ts +8 -4
  259. package/src/runtime/channels/spot-route-bridge-transport.ts +6 -4
  260. package/src/runtime/channels/spot-route-dispatch-strategy.ts +47 -18
  261. package/src/runtime/diagnostics/message-flow.ts +1 -1
  262. package/src/runtime/execution/serial-execution-queue.ts +2 -0
  263. package/src/runtime/foundation/actor-join-recovery-codec.ts +2 -2
  264. package/src/runtime/foundation/durable-service-request.ts +137 -0
  265. package/src/runtime/foundation/operation-identity.ts +5 -1
  266. package/src/runtime/foundation/raw-service-mesh-runtime.ts +642 -253
  267. package/src/runtime/foundation/service-liveness-registry.ts +68 -59
  268. package/src/runtime/foundation/service-mailbox.ts +7 -1
  269. package/src/runtime/foundation/service-relocation-object-owner.ts +2 -0
  270. package/src/runtime/foundation/service-relocation-runtime.ts +18 -1
  271. package/src/runtime/foundation/service-runtime-contracts.ts +7 -1
  272. package/src/runtime/foundation/service-stateful-runtime.ts +128 -160
  273. package/src/runtime/foundation/service-stateful-wire-codec.ts +55 -84
  274. package/src/runtime/foundation/service-topology-registry.ts +103 -42
  275. package/src/runtime/foundation/service-wire-m6a-codec.ts +57 -38
  276. package/src/runtime/handlers/handler-instance-scope.ts +67 -16
  277. package/src/runtime/host/actor-packet-relay.ts +7 -0
  278. package/src/runtime/host/actor-runtime-options-factory.ts +14 -2
  279. package/src/runtime/host/application-job-queue.ts +249 -48
  280. package/src/runtime/host/entry-actor-runtime.ts +5 -0
  281. package/src/runtime/host/index.ts +224 -160
  282. package/src/runtime/host/instance-activation-authority.ts +132 -27
  283. package/src/runtime/host/remote-bound-session-relay.ts +2 -23
  284. package/src/runtime/host/route-mesh-runtime.ts +1 -1
  285. package/src/runtime/host/service-relocation-control.ts +11 -5
  286. package/src/runtime/host/service-relocation-host-runtime.ts +317 -291
  287. package/src/runtime/host/spot-address-transport.ts +49 -24
  288. package/src/runtime/host/spot-runtime-options-factory.ts +4 -0
  289. package/src/runtime/host/user-spot-creation-coordinator.ts +8 -0
  290. package/src/runtime/locations/actor-location-claims.ts +52 -30
  291. package/src/runtime/locations/domain-store-contract.ts +6 -2
  292. package/src/runtime/locations/in-memory-authority-store.ts +113 -9
  293. package/src/runtime/locations/in-memory-location-store.ts +25 -3
  294. package/src/runtime/locations/internal-location-contracts.ts +4 -0
  295. package/src/runtime/locations/lifecycle.ts +8 -26
  296. package/src/runtime/locations/location-store-repository.ts +220 -15
  297. package/src/runtime/locations/resolvers.ts +25 -2
  298. package/src/runtime/locations/runtime.ts +28 -24
  299. package/src/runtime/messaging/framework-json-v1.ts +5 -325
  300. package/src/runtime/messaging/packet-name.ts +5 -25
  301. package/src/runtime/messaging/request-result.ts +58 -0
  302. package/src/runtime/messaging/submission-result.ts +7 -3
  303. package/src/runtime/protocol/service_wire_codec.generated.ts +131 -1
  304. package/src/runtime/protocol/service_wire_pilot_codec.generated.ts +4 -4
  305. package/src/runtime/spots/formal-remote-actor-admission-registry.ts +45 -23
  306. package/src/runtime/spots/index.ts +30 -2
  307. package/src/runtime/spots/spot-activation.ts +33 -10
  308. package/src/runtime/spots/spot-actor-admission-coordinator.ts +13 -0
  309. package/src/runtime/spots/spot-actor-packet-dispatch.ts +10 -0
  310. package/src/runtime/spots/spot-actor-packet-drain.ts +2 -0
  311. package/src/runtime/spots/spot-actor-packet-relay-dispatch.ts +1 -0
  312. package/src/runtime/spots/spot-entry-activation.ts +12 -2
  313. package/src/runtime/spots/spot-handler-registry.ts +41 -8
  314. package/src/runtime/spots/spot-node-autoconnect.ts +6 -2
  315. package/src/runtime/spots/spot-node-runtime-manager.ts +7 -12
  316. package/src/runtime/spots/spot-outbound.ts +36 -16
  317. package/src/runtime/spots/spot-routed-spot-packet-dispatch.ts +2 -1
  318. package/src/runtime/spots/spot-routing-internal.ts +14 -0
  319. package/src/runtime/spots/spot-runtime-ports.ts +3 -0
  320. package/src/runtime/spots/spot-subscription-dispatch.ts +0 -3
  321. package/src/runtime/spots/spot-timer.ts +5 -1
  322. package/src/runtime/streams/stream-session-runtime.ts +13 -30
@@ -6,7 +6,7 @@ import type {
6
6
  ZLinkBackendReceived,
7
7
  ZLinkBackendTopicMessage
8
8
  } from '../runtime-values';
9
- import type { CoreHwmBudgetSnapshot } from '@zlink-systems/zlink';
9
+ import type { CoreHwmBudgetSnapshot, ReceiveFlowState } from '@zlink-systems/zlink';
10
10
  import { type ZLinkBackendRecvFlags, type ZLinkBackendSendFlags } from '../runtime-values';
11
11
  export * from '../runtime-values';
12
12
  type MessageLike = ZLinkBackendMessageLike;
@@ -27,6 +27,7 @@ import type {
27
27
  import type { RoutingId } from '../../../contracts';
28
28
  import type { ZLinkCoreHwmOptions } from '../../../contracts/Configuration';
29
29
  import type { ZLinkSubmitResult } from '../../messaging/submission-result';
30
+ import type { ZLinkMeshCompletionHandler } from '../mesh-completion-table';
30
31
  import type { Message } from '../../../contracts/Common/Message';
31
32
  import type {
32
33
  ServiceSpotMessageFollowSeal,
@@ -38,6 +39,7 @@ import type {
38
39
  ServiceActorCreateRecord,
39
40
  ServiceDirectSpotRouteFence,
40
41
  ServiceInstanceRouteFence,
42
+ ServiceInstanceColdActivationTarget,
41
43
  ServiceUserSpotCloseRecord,
42
44
  ServiceUserSpotCreateRecord
43
45
  } from '../../foundation/service-stateful-wire-codec';
@@ -60,6 +62,7 @@ export type ZLinkBackendObjectPlacement =
60
62
  | { readonly kind: 'unavailable' };
61
63
 
62
64
  export interface ZLinkBackendMeshNode {
65
+ readonly routingId?: RoutingId;
63
66
  completeClosedInstance?(spotId: string, objectGeneration: bigint): void;
64
67
  setDispatchErrorReporter?(
65
68
  reporter: import('../../channels/dispatch-error-reporter').ZLinkDispatchErrorReporter,
@@ -112,30 +115,19 @@ export interface ZLinkBackendMeshNode {
112
115
  selectObjectPlacement(stableType: string): ZLinkBackendObjectPlacement;
113
116
  instanceSpotPlacementTypes?(): readonly string[];
114
117
  sendToMissingInstanceSpot(
115
- target: {
116
- readonly targetNodeRid: string;
117
- readonly targetNodeGeneration: bigint;
118
- readonly targetSpotId: string;
119
- readonly stableType: string;
120
- readonly descriptorVersion: string;
121
- },
118
+ target: ServiceInstanceColdActivationTarget,
122
119
  parts: ZLinkBackendMessageLike | readonly ZLinkBackendMessageLike[],
123
120
  deadlineUnixMs: bigint,
124
121
  sourceSpotId?: string,
125
122
  metadata?: ReadonlyMap<string, string>
126
123
  ): Promise<SubmitResult>;
127
124
  requestToMissingInstanceSpot(
128
- target: {
129
- readonly targetNodeRid: string;
130
- readonly targetNodeGeneration: bigint;
131
- readonly targetSpotId: string;
132
- readonly stableType: string;
133
- readonly descriptorVersion: string;
134
- },
125
+ target: ServiceInstanceColdActivationTarget,
135
126
  parts: ZLinkBackendMessageLike | readonly ZLinkBackendMessageLike[],
136
127
  deadlineUnixMs: bigint,
137
128
  sourceSpotId?: string,
138
- metadata?: ReadonlyMap<string, string>
129
+ metadata?: ReadonlyMap<string, string>,
130
+ onAdmitted?: () => void
139
131
  ): MeshOperationId;
140
132
  sendToInstanceSpot(
141
133
  route: ServiceInstanceRouteFence,
@@ -150,7 +142,8 @@ export interface ZLinkBackendMeshNode {
150
142
  timeoutMs?: number,
151
143
  sourceSpotId?: string,
152
144
  metadata?: ReadonlyMap<string, string>,
153
- instanceIntent?: boolean
145
+ instanceIntent?: boolean,
146
+ onAdmitted?: () => void
154
147
  ): MeshOperationId;
155
148
  registerUserSpotOperationHandler(handler: ServiceUserSpotOperationHandler): void;
156
149
  requestUserSpotCreate(
@@ -192,12 +185,16 @@ export interface ZLinkBackendMeshNode {
192
185
  readonly lifecycleGeneration: bigint;
193
186
  }): void;
194
187
  isObjectClientNodeDirectTarget?(targetRid: unknown): boolean;
188
+ observePeerRoute?(
189
+ targetRid: unknown
190
+ ): import('../../foundation/durable-service-request').PeerRouteObservation;
191
+ hasPeerRouteOrConnectionIntent?(targetRid: unknown, endpoint: string): boolean;
195
192
  isPeerRouteReady?(targetRid: unknown, lifecycleGeneration?: bigint): boolean;
196
193
  sendToNode(
197
194
  targetRid: unknown,
198
195
  parts: MessageLike | readonly MessageLike[],
199
196
  options?: { flags?: number }
200
- ): Promise<SubmitResult>;
197
+ ): SubmitResult | Promise<SubmitResult>;
201
198
  /**
202
199
  * Sends service-wire infrastructure frames directly to a peer. Relocation
203
200
  * Prepare may add NODE-INTERNAL sideband frames after its canonical frame.
@@ -218,12 +215,21 @@ export interface ZLinkBackendMeshNode {
218
215
  requestInfrastructureControlFrames?(
219
216
  targetRid: unknown,
220
217
  frames: readonly Uint8Array[],
221
- options?: { readonly timeoutMs?: number }
218
+ options?: {
219
+ readonly timeoutMs?: number;
220
+ readonly signal?: AbortSignal;
221
+ readonly onSubmitted?: (signal: AbortSignal) => Promise<void>;
222
+ }
222
223
  ): Promise<readonly Uint8Array[]>;
223
224
  requestToNode(
224
225
  targetRid: unknown,
225
226
  parts: MessageLike | readonly MessageLike[],
226
- options?: { flags?: number; timeoutMs?: number; applicationMetadata?: Buffer }
227
+ options?: {
228
+ flags?: number;
229
+ timeoutMs?: number;
230
+ applicationMetadata?: Buffer;
231
+ onAdmitted?: () => void;
232
+ }
227
233
  ): MeshOperationId;
228
234
  sendToChannel(
229
235
  channelName: string,
@@ -233,7 +239,12 @@ export interface ZLinkBackendMeshNode {
233
239
  requestToChannel(
234
240
  channelName: string,
235
241
  parts: MessageLike | readonly MessageLike[],
236
- options?: { flags?: number; timeoutMs?: number; applicationMetadata?: Buffer }
242
+ options?: {
243
+ flags?: number;
244
+ timeoutMs?: number;
245
+ applicationMetadata?: Buffer;
246
+ onAdmitted?: () => void;
247
+ }
237
248
  ): MeshOperationId;
238
249
  status(): MeshNodeStatus;
239
250
  peers(): MeshPeerEntry[];
@@ -359,7 +370,12 @@ export interface ZLinkBackendMeshNode {
359
370
  requestToActor(
360
371
  actor: ZLinkBackendActorRef,
361
372
  parts: MessageLike | readonly MessageLike[],
362
- options?: { flags?: number; timeoutMs?: number; applicationMetadata?: Buffer }
373
+ options?: {
374
+ flags?: number;
375
+ timeoutMs?: number;
376
+ applicationMetadata?: Buffer;
377
+ onAdmitted?: () => void;
378
+ }
363
379
  ): MeshOperationId;
364
380
  actorSendToActor(
365
381
  source: ZLinkBackendActorRef,
@@ -371,7 +387,12 @@ export interface ZLinkBackendMeshNode {
371
387
  source: ZLinkBackendActorRef,
372
388
  target: ZLinkBackendActorRef,
373
389
  parts: MessageLike | readonly MessageLike[],
374
- options?: { flags?: number; timeoutMs?: number; applicationMetadata?: Buffer }
390
+ options?: {
391
+ flags?: number;
392
+ timeoutMs?: number;
393
+ applicationMetadata?: Buffer;
394
+ onAdmitted?: () => void;
395
+ }
375
396
  ): MeshOperationId;
376
397
  sendActorBoundSession(
377
398
  actor: ZLinkBackendActorRef,
@@ -390,6 +411,7 @@ export interface ZLinkBackendMeshNode {
390
411
  timeoutMs?: number
391
412
  ): MeshOperationId;
392
413
  setReadyHandler(handler: (readyDomains: number) => number): void;
414
+ setCompletionHandler(handler: ZLinkMeshCompletionHandler): void;
393
415
  createReadyBatch(capacity: number): ReadyBatch;
394
416
  createReceiveBatch(messageCapacity: number, partCapacity: number): ReceiveBatch;
395
417
  drainReady(
@@ -476,7 +498,6 @@ export interface ZLinkBackendSocket extends ZLinkBackendObject {
476
498
  readonly lastEndpoint?: string;
477
499
  bind(endpoint: string): void;
478
500
  setChannelName(channelName: string): void;
479
- setReceiveFlowState?(state: 0 | 1): void;
480
501
  dispose(): Promise<void>;
481
502
  }
482
503
 
@@ -486,7 +507,7 @@ export interface ZLinkBackendConnectableSocket extends ZLinkBackendSocket {
486
507
  }
487
508
 
488
509
  export interface ZLinkBackendDealerSocket extends ZLinkBackendConnectableSocket {
489
- setReceiveFlowState(state: 0 | 1): void;
510
+ receiveAdmission?: import('../../foundation/service-liveness-registry').ServiceLivenessConnection;
490
511
  setRoutingId(routingId: RoutingId): void;
491
512
  peerWeight: number;
492
513
  sendHighWaterMark: number;
@@ -494,7 +515,11 @@ export interface ZLinkBackendDealerSocket extends ZLinkBackendConnectableSocket
494
515
  receiveTimeoutMs: number;
495
516
  maxMessageSize: number;
496
517
  send(message: Message | readonly Message[]): Promise<void>;
497
- request(message: Message | readonly Message[], timeoutMs?: number): Promise<readonly Message[]>;
518
+ request(
519
+ message: Message | readonly Message[],
520
+ timeoutMs?: number,
521
+ onAdmitted?: () => void
522
+ ): Promise<readonly Message[]>;
498
523
  recv(flags?: ZLinkBackendRecvFlags): Received | undefined;
499
524
  }
500
525
 
@@ -511,11 +536,11 @@ export interface ZLinkBackendSendOperation {
511
536
  export interface ZLinkBackendRequestOperation {
512
537
  message(message: MessageLike): ZLinkBackendRequestOperation;
513
538
  timeout(timeoutMs: number): ZLinkBackendRequestOperation;
514
- submit(): Promise<readonly Message[]>;
539
+ submit(onAdmitted?: () => void): Promise<readonly Message[]>;
515
540
  }
516
541
 
517
542
  export interface ZLinkBackendRouterSocket extends ZLinkBackendConnectableSocket {
518
- setReceiveFlowState(state: 0 | 1): void;
543
+ setReceiveFlowState(state: ReceiveFlowState): void;
519
544
  /** Enables the native probe handshake for manually configured routes. */
520
545
  setProbe(enabled: boolean): void;
521
546
  peerWeight: number;
@@ -529,7 +554,8 @@ export interface ZLinkBackendRouterSocket extends ZLinkBackendConnectableSocket
529
554
  request(
530
555
  routingId: RoutingId,
531
556
  message: Message | readonly Message[],
532
- timeoutMs?: number
557
+ timeoutMs?: number,
558
+ onAdmitted?: () => void
533
559
  ): Promise<readonly Message[]>;
534
560
  sendToSpot(
535
561
  targetNodeRid: RoutingId,
@@ -541,7 +567,8 @@ export interface ZLinkBackendRouterSocket extends ZLinkBackendConnectableSocket
541
567
  targetNodeRid: RoutingId,
542
568
  targetSpotId: RoutingId,
543
569
  parts: readonly Message[],
544
- timeoutMs?: number
570
+ timeoutMs?: number,
571
+ onAdmitted?: () => void
545
572
  ): Promise<readonly Message[]>;
546
573
  disconnectPeer(routingId: RoutingId): void;
547
574
  reply(routingId: RoutingId, replyToken: unknown): ZLinkBackendReplyOperation;
@@ -549,6 +576,7 @@ export interface ZLinkBackendRouterSocket extends ZLinkBackendConnectableSocket
549
576
  }
550
577
 
551
578
  export interface ZLinkBackendPublisherSocket extends ZLinkBackendSocket {
579
+ lingerMs: number;
552
580
  sendTimeoutMs: number;
553
581
  sendHighWaterMark: number;
554
582
  noDrop: boolean;
@@ -697,7 +725,8 @@ export interface ZLinkBackendSpot extends ZLinkBackendObject {
697
725
  requestToChannel(
698
726
  channelName: string,
699
727
  payload: Message | readonly Message[],
700
- timeoutMs?: number
728
+ timeoutMs?: number,
729
+ onAdmitted?: () => void
701
730
  ): Promise<readonly Message[]>;
702
731
  sendToChannel(channelName: string, payload: Message | readonly Message[]): Promise<void>;
703
732
  publish(
@@ -714,7 +743,8 @@ export interface ZLinkBackendSpot extends ZLinkBackendObject {
714
743
  targetRid: RoutingId,
715
744
  spotId: RoutingId,
716
745
  payload: Message | readonly Message[],
717
- timeoutMs?: number
746
+ timeoutMs?: number,
747
+ onAdmitted?: () => void
718
748
  ): Promise<readonly Message[]>;
719
749
  dispose(): Promise<void>;
720
750
  }
@@ -739,6 +769,7 @@ export interface ZLinkMeshBackendAdapter {
739
769
  readonly trustProfile?: string;
740
770
  readonly applicationJobQueue: import('../../application-jobs/contracts').ApplicationJobQueuePort;
741
771
  readonly applicationJobReceiveFlowFailureSink?: (error: unknown) => void;
772
+ readonly infrastructureTaskRunner?: import('../../spots/spot-actor-join-dispatch').ZLinkDetachedTaskRunner;
742
773
  readonly peerAdmissionSealed?: () => boolean;
743
774
  }
744
775
  ): ZLinkBackendMeshNode;
@@ -5,7 +5,7 @@ import type {
5
5
  ReceiveKindData,
6
6
  ReceiveRecord
7
7
  } from '../foundation/service-runtime-contracts';
8
- import { operationIdentityKey } from '../foundation/operation-identity';
8
+ import { operationIdentityKey, validateOperationIdentity } from '../foundation/operation-identity';
9
9
 
10
10
  export interface ZLinkMeshCompletionDiagnostic {
11
11
  readonly kind: 'unknownOrLate';
@@ -21,25 +21,128 @@ export interface ZLinkMeshCompletion {
21
21
  readonly parts: Message[];
22
22
  }
23
23
 
24
- interface PendingCompletion {
25
- readonly resolve: (completion: ZLinkMeshCompletion) => void;
26
- readonly reject: (error: unknown) => void;
27
- readonly removeAbort?: () => void;
24
+ const COMPLETION_SLOT_BLOCK_SIZE = 64;
25
+ const COMPLETION_HASH_BUCKETS_PER_SLOT = 2;
26
+ const COMPLETION_HASH_WORD_SCALE = 0x1_0000;
27
+ const COMPLETION_HASH_MULTIPLIER = 0x9e37_79b1;
28
+ const COMPLETION_ABORT_OPTIONS = Object.freeze({ once: true });
29
+
30
+ class CompletionSlot {
31
+ generation = 0;
32
+ next = -1;
33
+ high?: bigint;
34
+ low?: bigint;
35
+ hashNext = -1;
36
+ resolve?: (completion: ZLinkMeshCompletion) => void;
37
+ reject?: (error: unknown) => void;
38
+ signal?: AbortSignal;
39
+
40
+ constructor(readonly abort: () => void) {}
28
41
  }
29
42
 
43
+ export type ZLinkMeshCompletionTerminal = Pick<ReceiveRecord, 'operationId' | 'terminalResult'>;
44
+ export type ZLinkMeshCompletionHandler = (
45
+ terminal: ZLinkMeshCompletionTerminal,
46
+ materialize: () => ReceiveRecord
47
+ ) => void;
48
+
30
49
  export class ZLinkMeshCompletionTable {
31
- private readonly pending = new Map<string, PendingCompletion>();
50
+ private buckets = new Int32Array(0);
51
+ private readonly slots: CompletionSlot[] = [];
52
+ private free = -1;
53
+ private activeCount = 0;
32
54
  private disposed = false;
33
55
 
34
- constructor(
35
- private readonly onDiagnostic?: (diagnostic: ZLinkMeshCompletionDiagnostic) => void
36
- ) {}
56
+ constructor(private readonly onDiagnostic?: (diagnostic: ZLinkMeshCompletionDiagnostic) => void) {
57
+ this.prepareSlots();
58
+ }
59
+
60
+ private prepareSlots(): void {
61
+ const start = this.slots.length;
62
+ for (let index = start; index < start + COMPLETION_SLOT_BLOCK_SIZE; index++) {
63
+ const slot = new CompletionSlot(() => {
64
+ const reject = slot.reject;
65
+ const signal = slot.signal;
66
+ if (reject === undefined) return;
67
+ this.releaseSlot(index);
68
+ reject(signal?.reason ?? new DOMException('The operation was aborted.', 'AbortError'));
69
+ });
70
+ slot.next = this.free;
71
+ this.slots.push(slot);
72
+ this.free = index;
73
+ }
74
+ const minimumBuckets = this.slots.length * COMPLETION_HASH_BUCKETS_PER_SLOT;
75
+ this.buckets = new Int32Array(2 ** Math.ceil(Math.log2(minimumBuckets))).fill(-1);
76
+ for (let index = 0; index < this.slots.length; index++) {
77
+ const slot = this.slots[index]!;
78
+ if (slot.high === undefined) continue;
79
+ this.indexSlot(index);
80
+ }
81
+ }
82
+
83
+ private bucket(high: bigint, low: bigint): number {
84
+ const highWord = Number(high);
85
+ const lowWord = Number(low);
86
+ // Bucket selection may collide; the stored 128-bit identity is compared exactly.
87
+ const hash =
88
+ Math.imul(
89
+ highWord ^ Math.trunc(highWord / COMPLETION_HASH_WORD_SCALE),
90
+ COMPLETION_HASH_MULTIPLIER
91
+ ) ^
92
+ lowWord ^
93
+ Math.trunc(lowWord / COMPLETION_HASH_WORD_SCALE);
94
+ return hash & (this.buckets.length - 1);
95
+ }
96
+
97
+ private indexSlot(index: number): void {
98
+ const slot = this.slots[index]!;
99
+ const bucket = this.bucket(slot.high!, slot.low!);
100
+ slot.hashNext = this.buckets[bucket]!;
101
+ this.buckets[bucket] = index;
102
+ }
103
+
104
+ private findSlot(operationId: MeshOperationId): number {
105
+ validateOperationIdentity(operationId);
106
+ for (
107
+ let index = this.buckets[this.bucket(operationId.high, operationId.low)]!;
108
+ index !== -1;
109
+ index = this.slots[index]!.hashNext
110
+ ) {
111
+ const slot = this.slots[index]!;
112
+ if (slot.high === operationId.high && slot.low === operationId.low) return index;
113
+ }
114
+ return -1;
115
+ }
116
+
117
+ private releaseSlot(index: number): void {
118
+ const slot = this.slots[index]!;
119
+ if (slot.high !== undefined) {
120
+ const bucket = this.bucket(slot.high, slot.low!);
121
+ let previous = -1;
122
+ let current = this.buckets[bucket]!;
123
+ while (current !== index) {
124
+ previous = current;
125
+ current = this.slots[current]!.hashNext;
126
+ }
127
+ if (previous === -1) this.buckets[bucket] = slot.hashNext;
128
+ else this.slots[previous]!.hashNext = slot.hashNext;
129
+ }
130
+ slot.signal?.removeEventListener('abort', slot.abort);
131
+ slot.high = undefined;
132
+ slot.low = undefined;
133
+ slot.hashNext = -1;
134
+ slot.signal = undefined;
135
+ slot.resolve = undefined;
136
+ slot.reject = undefined;
137
+ slot.next = this.free;
138
+ this.free = index;
139
+ this.activeCount--;
140
+ }
37
141
 
38
142
  /**
39
- * Submits and registers without yielding control to the event loop. Mesh
40
- * completion dispatch is asynchronous, so a completion cannot overtake the
41
- * registration. The table therefore does not need to retain responses that
42
- * arrived before their waiter.
143
+ * Reserves the dispatcher slot before transport submission. The backend
144
+ * observes native terminals through Promises, so identity binding finishes
145
+ * before the terminal callback can run, without an infrastructure pump.
43
146
  */
44
147
  submit(operation: () => MeshOperationId, signal?: AbortSignal): Promise<ZLinkMeshCompletion> {
45
148
  if (this.isDisposed()) {
@@ -50,32 +153,33 @@ export class ZLinkMeshCompletionTable {
50
153
  signal.reason ?? new DOMException('The operation was aborted.', 'AbortError')
51
154
  );
52
155
  }
53
- const operationId = operation();
54
- // The backend submission callback can synchronously re-enter `dispose()`.
55
- // TypeScript's control-flow analysis cannot observe mutation through it.
56
- if (this.disposed) {
57
- return Promise.reject(new Error('Mesh completion table is disposed.'));
58
- }
59
- const key = operationIdentityKey(operationId);
60
- if (this.pending.has(key)) {
61
- return Promise.reject(new Error(`Mesh operation '${key}' is already pending.`));
62
- }
63
156
  return new Promise((resolve, reject) => {
64
- const abort = () => {
65
- this.pending.delete(key);
66
- reject(signal?.reason ?? new DOMException('The operation was aborted.', 'AbortError'));
67
- };
68
- if (signal?.aborted === true) {
69
- abort();
70
- return;
157
+ if (this.free === -1) this.prepareSlots();
158
+ const index = this.free;
159
+ const slot = this.slots[index]!;
160
+ this.free = slot.next;
161
+ const generation = ++slot.generation;
162
+ slot.resolve = resolve;
163
+ slot.reject = reject;
164
+ slot.signal = signal;
165
+ this.activeCount++;
166
+ try {
167
+ signal?.addEventListener('abort', slot.abort, COMPLETION_ABORT_OPTIONS);
168
+ const operationId = operation();
169
+ // A reentrant abort may release and reuse this slot during submission.
170
+ if (slot.generation !== generation || slot.resolve !== resolve) return;
171
+ if (this.findSlot(operationId) !== -1) {
172
+ throw new Error(
173
+ `Mesh operation '${operationIdentityKey(operationId)}' is already pending.`
174
+ );
175
+ }
176
+ slot.high = operationId.high;
177
+ slot.low = operationId.low;
178
+ this.indexSlot(index);
179
+ } catch (error) {
180
+ if (slot.generation === generation && slot.resolve === resolve) this.releaseSlot(index);
181
+ reject(error);
71
182
  }
72
- signal?.addEventListener('abort', abort, { once: true });
73
- this.pending.set(key, {
74
- resolve,
75
- reject,
76
- removeAbort:
77
- signal === undefined ? undefined : () => signal.removeEventListener('abort', abort)
78
- });
79
183
  });
80
184
  }
81
185
 
@@ -83,10 +187,11 @@ export class ZLinkMeshCompletionTable {
83
187
  return this.disposed;
84
188
  }
85
189
 
86
- complete(record: ReceiveRecord): void {
87
- const key = operationIdentityKey(record.operationId);
88
- const pending = this.pending.get(key);
89
- if (pending === undefined) {
190
+ complete(record: ReceiveRecord): void;
191
+ complete(record: ZLinkMeshCompletionTerminal, materialize: () => ReceiveRecord): void;
192
+ complete(record: ZLinkMeshCompletionTerminal, materialize?: () => ReceiveRecord): void {
193
+ const index = this.findSlot(record.operationId);
194
+ if (index === -1) {
90
195
  this.onDiagnostic?.({
91
196
  kind: 'unknownOrLate',
92
197
  operationId: Object.freeze({ ...record.operationId }),
@@ -94,12 +199,16 @@ export class ZLinkMeshCompletionTable {
94
199
  });
95
200
  return;
96
201
  }
97
- this.pending.delete(key);
98
- pending.removeAbort?.();
202
+ const slot = this.slots[index]!;
203
+ const resolve = slot.resolve!;
204
+ const reject = slot.reject!;
205
+ this.releaseSlot(index);
99
206
  try {
100
- pending.resolve(retainCompletion(record));
207
+ resolve(
208
+ retainCompletion(materialize === undefined ? (record as ReceiveRecord) : materialize())
209
+ );
101
210
  } catch (error) {
102
- pending.reject(error);
211
+ reject(error);
103
212
  }
104
213
  }
105
214
 
@@ -108,36 +217,43 @@ export class ZLinkMeshCompletionTable {
108
217
  return;
109
218
  }
110
219
  this.disposed = true;
111
- const pending = [...this.pending.values()];
112
- this.pending.clear();
113
- for (const entry of pending) {
114
- entry.removeAbort?.();
115
- }
116
- for (const entry of pending) {
117
- entry.reject(reason);
220
+ for (let index = 0; index < this.slots.length; index++) {
221
+ const reject = this.slots[index]!.reject;
222
+ if (reject === undefined) continue;
223
+ this.releaseSlot(index);
224
+ reject(reason);
118
225
  }
119
226
  }
120
227
 
121
228
  get pendingCount(): number {
122
- return this.pending.size;
229
+ return this.activeCount;
123
230
  }
124
231
  }
125
232
 
126
233
  function retainCompletion(record: ReceiveRecord): ZLinkMeshCompletion {
234
+ const parts = retainCompletionParts(record.parts);
235
+ // The retention pass verifies every part is already a managed runtime message.
236
+ if (parts === record.parts) return record as unknown as ZLinkMeshCompletion;
127
237
  return {
128
238
  terminalResult: record.terminalResult,
129
239
  failureErrno: record.failureErrno,
130
240
  operationKind: record.operationKind,
131
241
  kindData: record.kindData,
132
- parts: record.parts.map(retainCompletionPart)
242
+ parts
133
243
  };
134
244
  }
135
245
 
136
- function retainCompletionPart(part: ZLinkMessage): Message {
137
- // A runtime message already owns a managed Buffer and close() is a no-op.
138
- // Binding-native messages can expose native storage through data(), which
139
- // becomes invalid when their owner closes; materialize that one boundary copy.
140
- return part instanceof Message ? part : Message.fromOwned(Buffer.from(part.data()));
246
+ function retainCompletionParts(parts: readonly ZLinkMessage[]): Message[] {
247
+ // Reuse managed messages and wrap binding payloads in the runtime representation.
248
+ let retained: Message[] | undefined;
249
+ for (let index = 0; index < parts.length; index++) {
250
+ const part = parts[index]!;
251
+ if (!(part instanceof Message)) {
252
+ retained ??= parts.slice() as Message[];
253
+ retained[index] = Message.fromOwned(Message.retainPayload(part));
254
+ }
255
+ }
256
+ return retained ?? (parts as Message[]);
141
257
  }
142
258
 
143
259
  export function closeMeshCompletion(completion: ZLinkMeshCompletion): void {