@zlink-systems/framework 0.27.0 → 0.28.0

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 (121) hide show
  1. package/dist/.tsbuildinfo +1 -1
  2. package/dist/contracts/Actors/ZLinkActorClient.d.ts +1 -1
  3. package/dist/contracts/Channels/Calls.d.ts +1 -1
  4. package/dist/contracts/Configuration/Builders.d.ts +0 -1
  5. package/dist/contracts/Configuration/Configs.d.ts +0 -1
  6. package/dist/contracts/Configuration/RegistrationTypes.d.ts +0 -5
  7. package/dist/contracts/Configuration/RegistrationValidators.js +0 -2
  8. package/dist/contracts/Spots/Contracts.d.ts +1 -1
  9. package/dist/contracts/Streams/BoundSessionContracts.d.ts +1 -1
  10. package/dist/contracts/Streams/IZLinkSession.d.ts +2 -3
  11. package/dist/contracts/Streams/IZLinkSessionActor.d.ts +2 -2
  12. package/dist/runtime/actors/actor-client.js +7 -10
  13. package/dist/runtime/actors/actor-request-deadline.d.ts +1 -3
  14. package/dist/runtime/actors/actor-request-deadline.js +4 -29
  15. package/dist/runtime/actors/actor-routed-join-transport.d.ts +2 -3
  16. package/dist/runtime/backend/contracts/index.d.ts +1 -4
  17. package/dist/runtime/backend/node/node-backend-adapter-support.d.ts +2 -0
  18. package/dist/runtime/backend/node/node-backend-adapter-support.js +35 -4
  19. package/dist/runtime/backend/node/node-dealer-channel-client-transport.d.ts +1 -1
  20. package/dist/runtime/backend/node/node-dealer-channel-client-transport.js +1 -2
  21. package/dist/runtime/backend/node/node-raw-binding-port.js +10 -27
  22. package/dist/runtime/backend/node/node-socket-backend-adapter.js +1 -1
  23. package/dist/runtime/channels/channel-clients.js +8 -10
  24. package/dist/runtime/channels/channel-envelope.d.ts +1 -1
  25. package/dist/runtime/channels/channel-envelope.js +4 -10
  26. package/dist/runtime/channels/channel-outbound-operations.d.ts +2 -2
  27. package/dist/runtime/channels/channel-outbound-operations.js +20 -36
  28. package/dist/runtime/channels/channel-runtime-manager.d.ts +4 -4
  29. package/dist/runtime/channels/channel-runtime-manager.js +8 -8
  30. package/dist/runtime/channels/channel-socket-options.js +0 -10
  31. package/dist/runtime/channels/channel-socket-registry.d.ts +1 -1
  32. package/dist/runtime/channels/channel-socket-registry.js +3 -14
  33. package/dist/runtime/channels/channel-transports.d.ts +10 -14
  34. package/dist/runtime/channels/channel-transports.js +11 -14
  35. package/dist/runtime/channels/local-spot-route-transport.d.ts +1 -1
  36. package/dist/runtime/channels/local-spot-route-transport.js +1 -3
  37. package/dist/runtime/channels/router-socket-spot-route-transport.d.ts +1 -1
  38. package/dist/runtime/channels/router-socket-spot-route-transport.js +2 -2
  39. package/dist/runtime/channels/source-spot-router.d.ts +1 -1
  40. package/dist/runtime/channels/source-spot-router.js +2 -4
  41. package/dist/runtime/channels/spot-node-route-transport.d.ts +1 -1
  42. package/dist/runtime/channels/spot-node-route-transport.js +2 -3
  43. package/dist/runtime/channels/spot-route-bridge-transport.d.ts +1 -1
  44. package/dist/runtime/channels/spot-route-bridge-transport.js +2 -2
  45. package/dist/runtime/channels/spot-route-dispatch-strategy.d.ts +2 -4
  46. package/dist/runtime/channels/spot-route-dispatch-strategy.js +11 -12
  47. package/dist/runtime/foundation/raw-service-mesh-runtime.js +17 -11
  48. package/dist/runtime/host/actor-packet-relay.d.ts +2 -2
  49. package/dist/runtime/host/actor-packet-relay.js +8 -10
  50. package/dist/runtime/host/index.js +1 -15
  51. package/dist/runtime/host/remote-bound-session-relay.js +8 -8
  52. package/dist/runtime/host/spot-address-transport.d.ts +1 -9
  53. package/dist/runtime/host/spot-address-transport.js +46 -86
  54. package/dist/runtime/locations/location-store-repository.js +6 -4
  55. package/dist/runtime/messaging/request-deadline.d.ts +3 -0
  56. package/dist/runtime/messaging/request-deadline.js +39 -0
  57. package/dist/runtime/messaging/submission-result.d.ts +2 -1
  58. package/dist/runtime/messaging/submission-result.js +11 -4
  59. package/dist/runtime/spots/spot-outbound.d.ts +3 -5
  60. package/dist/runtime/spots/spot-outbound.js +12 -15
  61. package/dist/runtime/streams/bound-actor-relay-sender.d.ts +2 -2
  62. package/dist/runtime/streams/bound-actor-relay-sender.js +14 -14
  63. package/dist/runtime/streams/bound-session-service.js +1 -1
  64. package/dist/runtime/streams/index.d.ts +2 -2
  65. package/dist/runtime/streams/index.js +2 -2
  66. package/dist/runtime/streams/managed-stream.d.ts +2 -2
  67. package/dist/runtime/streams/managed-stream.js +3 -5
  68. package/dist/runtime/streams/native-fallback-bound-session.js +13 -16
  69. package/dist/runtime/streams/session-calls.d.ts +5 -7
  70. package/dist/runtime/streams/session-calls.js +6 -23
  71. package/dist/runtime/streams/session-context.d.ts +4 -4
  72. package/dist/runtime/streams/session-context.js +3 -6
  73. package/package.json +3 -3
  74. package/src/contracts/Actors/ZLinkActorClient.ts +1 -1
  75. package/src/contracts/Channels/Calls.ts +1 -1
  76. package/src/contracts/Configuration/Builders.ts +0 -1
  77. package/src/contracts/Configuration/Configs.ts +0 -1
  78. package/src/contracts/Configuration/RegistrationBuilders.ts +0 -3
  79. package/src/contracts/Configuration/RegistrationTypes.ts +0 -5
  80. package/src/contracts/Configuration/RegistrationValidators.ts +0 -4
  81. package/src/contracts/Spots/Contracts.ts +1 -1
  82. package/src/contracts/Streams/BoundSessionContracts.ts +1 -1
  83. package/src/contracts/Streams/IZLinkSession.ts +2 -3
  84. package/src/contracts/Streams/IZLinkSessionActor.ts +2 -6
  85. package/src/runtime/actors/actor-client.ts +9 -15
  86. package/src/runtime/actors/actor-request-deadline.ts +4 -49
  87. package/src/runtime/actors/actor-routed-join-transport.ts +3 -5
  88. package/src/runtime/backend/contracts/index.ts +1 -8
  89. package/src/runtime/backend/node/node-backend-adapter-support.ts +45 -5
  90. package/src/runtime/backend/node/node-dealer-channel-client-transport.ts +0 -2
  91. package/src/runtime/backend/node/node-raw-binding-port.ts +15 -41
  92. package/src/runtime/backend/node/node-socket-backend-adapter.ts +1 -1
  93. package/src/runtime/channels/channel-clients.ts +9 -19
  94. package/src/runtime/channels/channel-envelope.ts +16 -28
  95. package/src/runtime/channels/channel-outbound-operations.ts +36 -38
  96. package/src/runtime/channels/channel-runtime-manager.ts +6 -28
  97. package/src/runtime/channels/channel-socket-options.ts +0 -13
  98. package/src/runtime/channels/channel-socket-registry.ts +3 -17
  99. package/src/runtime/channels/channel-transports.ts +7 -33
  100. package/src/runtime/channels/local-spot-route-transport.ts +1 -5
  101. package/src/runtime/channels/router-socket-spot-route-transport.ts +2 -6
  102. package/src/runtime/channels/source-spot-router.ts +2 -9
  103. package/src/runtime/channels/spot-node-route-transport.ts +2 -7
  104. package/src/runtime/channels/spot-route-bridge-transport.ts +5 -12
  105. package/src/runtime/channels/spot-route-dispatch-strategy.ts +11 -30
  106. package/src/runtime/foundation/raw-service-mesh-runtime.ts +17 -14
  107. package/src/runtime/host/actor-packet-relay.ts +8 -15
  108. package/src/runtime/host/index.ts +2 -26
  109. package/src/runtime/host/remote-bound-session-relay.ts +8 -16
  110. package/src/runtime/host/spot-address-transport.ts +106 -165
  111. package/src/runtime/locations/location-store-repository.ts +7 -4
  112. package/src/runtime/messaging/request-deadline.ts +58 -0
  113. package/src/runtime/messaging/submission-result.ts +18 -4
  114. package/src/runtime/spots/spot-outbound.ts +14 -24
  115. package/src/runtime/streams/bound-actor-relay-sender.ts +12 -26
  116. package/src/runtime/streams/bound-session-service.ts +1 -1
  117. package/src/runtime/streams/index.ts +2 -4
  118. package/src/runtime/streams/managed-stream.ts +3 -13
  119. package/src/runtime/streams/native-fallback-bound-session.ts +13 -25
  120. package/src/runtime/streams/session-calls.ts +8 -34
  121. package/src/runtime/streams/session-context.ts +6 -15
@@ -20,6 +20,7 @@ import {
20
20
  import {
21
21
  requireOneWayCompletion,
22
22
  requirePublishCompletion,
23
+ requireClassicFanoutCompletion,
23
24
  throwAlreadySubmitted,
24
25
  ZLinkSubmitStatus,
25
26
  type ZLinkSubmitResult
@@ -176,14 +177,13 @@ export class DefaultZLinkRouteClient implements ZLinkRouteClient {
176
177
  sendToNode(meshName: string, targetNodeRid: string, message: unknown): ZLinkSendCall {
177
178
  return new DefaultZLinkSendCall(
178
179
  () => this.requireMesh(meshName),
179
- async (packetName, metadata, signal) =>
180
+ async (packetName, metadata) =>
180
181
  normalizeSubmitResult(
181
182
  await this.requireTransport().submit(
182
183
  meshName,
183
184
  targetNodeRid,
184
185
  packetName,
185
186
  message,
186
- signal,
187
187
  metadata
188
188
  )
189
189
  )
@@ -210,7 +210,7 @@ export class DefaultZLinkRouteClient implements ZLinkRouteClient {
210
210
  sendToChannel(channelName: string, message: unknown): ZLinkSendCall {
211
211
  return new DefaultZLinkSendCall(
212
212
  () => this.requireChannelRoute(channelName),
213
- async (packetName, metadata, signal) => {
213
+ async (packetName, metadata) => {
214
214
  const route = this.requireChannelRoute(channelName);
215
215
  if (route.kind === 'route-mesh') {
216
216
  return normalizeSubmitResult(
@@ -219,19 +219,12 @@ export class DefaultZLinkRouteClient implements ZLinkRouteClient {
219
219
  channelName,
220
220
  packetName,
221
221
  message,
222
- signal,
223
222
  metadata
224
223
  )
225
224
  );
226
225
  }
227
226
  return normalizeSubmitResult(
228
- await this.requireChannelTransport().send(
229
- channelName,
230
- packetName,
231
- message,
232
- signal,
233
- metadata
234
- )
227
+ await this.requireChannelTransport().send(channelName, packetName, message, metadata)
235
228
  );
236
229
  }
237
230
  );
@@ -271,9 +264,8 @@ export class DefaultZLinkRouteClient implements ZLinkRouteClient {
271
264
  () => {
272
265
  this.requireSpotTransport();
273
266
  },
274
- async (_packetName, metadata, signal) => {
267
+ async (_packetName, metadata) => {
275
268
  await sendToSpotHandle(this.requireSpotTransport(), spot, message, {
276
- signal,
277
269
  metadata,
278
270
  spotRouterChannelIdForMesh: this.spotRouterChannelIdForMesh
279
271
  });
@@ -431,8 +423,7 @@ class DefaultZLinkSendCall implements ZLinkSendCall {
431
423
  private readonly validate: () => void,
432
424
  private readonly submitter: (
433
425
  packetName: string | undefined,
434
- metadata: ReadonlyMap<string, string>,
435
- signal?: AbortSignal
426
+ metadata: ReadonlyMap<string, string>
436
427
  ) => Promise<ZLinkSubmitResult>
437
428
  ) {}
438
429
 
@@ -450,12 +441,11 @@ class DefaultZLinkSendCall implements ZLinkSendCall {
450
441
  return this;
451
442
  }
452
443
 
453
- async submit(signal?: AbortSignal): Promise<void> {
444
+ async submit(): Promise<void> {
454
445
  ensureNotExecuted(this.executed);
455
446
  this.validate();
456
447
  this.executed = true;
457
- throwIfAborted(signal);
458
- const result = await this.submitter(undefined, new Map(this.selectedMetadata), signal);
448
+ const result = await this.submitter(undefined, new Map(this.selectedMetadata));
459
449
  requireOneWayCompletion(result, 'One-way send');
460
450
  }
461
451
  }
@@ -580,6 +570,6 @@ class DefaultZLinkFanoutPublishCall implements ZLinkFanoutPublishCall {
580
570
  this.executed = true;
581
571
  throwIfAborted(signal);
582
572
  const result = await this.submitter(signal);
583
- requireOneWayCompletion(result, 'Classic fanout publish');
573
+ requireClassicFanoutCompletion(result, 'Classic fanout publish');
584
574
  }
585
575
  }
@@ -86,33 +86,18 @@ export function encodeChannelEnvelopeParts(
86
86
  createFlow = true,
87
87
  metadata: ReadonlyMap<string, string> = EMPTY_OUTBOUND_METADATA
88
88
  ): readonly MessageLike[] {
89
- const messageName = resolveFrameworkPacketName(payload, packetName, 'Channel');
90
- const encoded = encodePayload(
89
+ return encodeChannelEnvelopePartsAtDeadline(
90
+ kind,
91
+ channelName,
92
+ packetName,
91
93
  payload,
92
- codecsForFrameworkPacket(messageName, codecs),
93
- messageName,
94
- 'payload'
94
+ timeoutMs === undefined ? undefined : Date.now() + timeoutMs,
95
+ topic,
96
+ codecs,
97
+ correlationId,
98
+ createFlow,
99
+ metadata
95
100
  );
96
- const flow = createFlow ? currentOrCreateFlow('Application') : undefined;
97
- const envelopeCorrelationId = correlationIdForOutboundKind(kind, correlationId);
98
- return [
99
- encodeChannelHeader(
100
- kind,
101
- channelName,
102
- messageName,
103
- encoded.contentType,
104
- envelopeCorrelationId,
105
- timeoutMs === undefined ? null : new Date(Date.now() + timeoutMs).toISOString(),
106
- topic ?? null,
107
- null,
108
- null,
109
- undefined,
110
- applicationMetadataRecord(metadata),
111
- flow?.flowId,
112
- flow?.flowOrigin
113
- ),
114
- encoded.message
115
- ];
116
101
  }
117
102
 
118
103
  /**
@@ -126,14 +111,17 @@ export function encodeChannelEnvelopePartsAtDeadline(
126
111
  channelName: string,
127
112
  packetName: string | undefined,
128
113
  payload: unknown,
129
- deadlineUnixMs: number,
114
+ deadlineUnixMs: number | undefined,
130
115
  topic?: string,
131
116
  codecs?: ZLinkChannelEnvelopeCodecRegistry,
132
117
  correlationId?: string,
133
118
  createFlow = true,
134
119
  metadata: ReadonlyMap<string, string> = EMPTY_OUTBOUND_METADATA
135
120
  ): readonly MessageLike[] {
136
- if (!Number.isSafeInteger(deadlineUnixMs) || deadlineUnixMs <= 0) {
121
+ if (
122
+ deadlineUnixMs !== undefined &&
123
+ (!Number.isSafeInteger(deadlineUnixMs) || deadlineUnixMs <= 0)
124
+ ) {
137
125
  throw new RangeError('deadlineUnixMs must be a positive safe integer.');
138
126
  }
139
127
  const messageName = resolveFrameworkPacketName(payload, packetName, 'Channel');
@@ -152,7 +140,7 @@ export function encodeChannelEnvelopePartsAtDeadline(
152
140
  messageName,
153
141
  encoded.contentType,
154
142
  envelopeCorrelationId,
155
- new Date(deadlineUnixMs).toISOString(),
143
+ deadlineUnixMs === undefined ? null : new Date(deadlineUnixMs).toISOString(),
156
144
  topic ?? null,
157
145
  null,
158
146
  null,
@@ -4,9 +4,14 @@ import {
4
4
  internalFrameworkErrorKind,
5
5
  requestResultToPublicErrorKind
6
6
  } from '../framework-errors-internal';
7
+ import { waitRequestReply, remainingRequestTimeout } from '../messaging/request-deadline';
7
8
  import { isZLinkBackendResultError } from '../backend/runtime-values';
8
9
  import type { Message } from '../../contracts/Common/Message';
9
- import { ZLinkSubmitStatus, type ZLinkSubmitResult } from '../messaging/submission-result';
10
+ import {
11
+ ZLinkSubmitStatus,
12
+ classifySubmitResult,
13
+ type ZLinkSubmitResult
14
+ } from '../messaging/submission-result';
10
15
  import {
11
16
  ZLinkRuntimeMessageFlowOutcome as ZLinkMessageFlowOutcome,
12
17
  type ZLinkRuntimeMessageFlowResult,
@@ -18,6 +23,7 @@ import {
18
23
  closeMessages,
19
24
  decodeChannelReply,
20
25
  encodeChannelEnvelopeParts,
26
+ encodeChannelEnvelopePartsAtDeadline,
21
27
  newChannelCorrelationId,
22
28
  type ZLinkChannelEnvelopeCodecRegistry,
23
29
  ZLinkChannelMessageKind
@@ -52,13 +58,12 @@ export class ZLinkChannelOutboundOperations {
52
58
  channelName: string,
53
59
  packetName: string | undefined,
54
60
  message: unknown,
55
- signal?: AbortSignal,
56
61
  metadata: ReadonlyMap<string, string> = EMPTY_OUTBOUND_METADATA
57
62
  ): Promise<ZLinkSubmitResult> {
58
63
  // Call-scoped flow (spec 27 §4): the envelope encoder and the trace
59
64
  // points below share one ambient flow that does not outlive this call.
60
65
  return runWithOutboundFlow(this.dispatchServices.flowCreationEnabled(), () =>
61
- this.sendScoped(channelName, packetName, message, signal, metadata)
66
+ this.sendScoped(channelName, packetName, message, metadata)
62
67
  );
63
68
  }
64
69
 
@@ -66,13 +71,11 @@ export class ZLinkChannelOutboundOperations {
66
71
  channelName: string,
67
72
  packetName: string | undefined,
68
73
  message: unknown,
69
- signal?: AbortSignal,
70
74
  metadata: ReadonlyMap<string, string> = EMPTY_OUTBOUND_METADATA
71
75
  ): Promise<ZLinkSubmitResult> {
72
- throwIfAborted(signal);
73
- const dealer = await this.sockets.awaitClientDealerForOutbound(channelName, signal);
76
+ const dealer = await this.sockets.awaitClientDealerForOutbound(channelName);
74
77
  if (dealer === undefined) {
75
- return { status: ZLinkSubmitStatus.TimedOut };
78
+ return { status: ZLinkSubmitStatus.Shutdown };
76
79
  }
77
80
  const parts = encodeChannelEnvelopeParts(
78
81
  ZLinkChannelMessageKind.Command,
@@ -90,17 +93,8 @@ export class ZLinkChannelOutboundOperations {
90
93
  await dealer.send(parts);
91
94
  } catch (error) {
92
95
  closeMessages(parts);
93
- if (isSubmitDeadline(error)) {
94
- this.dispatchServices.beginOutbound(ZLinkMessageFlowOutcome.Backpressured)?.trace({
95
- surface: ZLinkDispatchErrorSurface.Channel,
96
- messageKind: ZLinkDispatchMessageKind.Send,
97
- channelName,
98
- channelRouteKind: 'client_server',
99
- packetName,
100
- correlationId: undefined,
101
- result: 'backpressured'
102
- });
103
- return { status: ZLinkSubmitStatus.TimedOut };
96
+ if (isZLinkBackendResultError(error) && error.operation === 'submit') {
97
+ return classifySubmitResult(error.result, 'One-way send', error.phase);
104
98
  }
105
99
  throw error;
106
100
  }
@@ -151,6 +145,8 @@ export class ZLinkChannelOutboundOperations {
151
145
  signal?: AbortSignal,
152
146
  metadata?: ReadonlyMap<string, string>
153
147
  ): Promise<TReply> {
148
+ const deadlineMs = timeoutMs === undefined ? undefined : performance.now() + timeoutMs;
149
+ const deadlineUnixMs = timeoutMs === undefined ? undefined : Date.now() + timeoutMs;
154
150
  let correlationId: string | undefined;
155
151
  let selectedServerRid: string | undefined;
156
152
  let terminalRecorded = false;
@@ -170,7 +166,16 @@ export class ZLinkChannelOutboundOperations {
170
166
  };
171
167
  try {
172
168
  throwIfAborted(signal);
173
- const dealer = await this.sockets.awaitClientDealerForOutbound(channelName, signal);
169
+ const readyWait = new AbortController();
170
+ const readySignal =
171
+ signal === undefined ? readyWait.signal : AbortSignal.any([signal, readyWait.signal]);
172
+ const dealer = await waitRequestReply(
173
+ this.sockets.awaitClientDealerForOutbound(channelName, readySignal),
174
+ `Channel request '${channelName}'`,
175
+ deadlineMs,
176
+ signal,
177
+ () => readyWait.abort()
178
+ );
174
179
  if (dealer === undefined) {
175
180
  throw createInternalFrameworkException(
176
181
  ZLinkFrameworkInternalErrorKind.DeadlineExceeded,
@@ -180,12 +185,12 @@ export class ZLinkChannelOutboundOperations {
180
185
  const serverRid = this.sockets.selectedClientServerRid(channelName, dealer);
181
186
  selectedServerRid = serverRid;
182
187
  correlationId = newChannelCorrelationId();
183
- const parts = encodeChannelEnvelopeParts(
188
+ const parts = encodeChannelEnvelopePartsAtDeadline(
184
189
  ZLinkChannelMessageKind.Request,
185
190
  channelName,
186
191
  packetName,
187
192
  request,
188
- timeoutMs,
193
+ deadlineUnixMs,
189
194
  undefined,
190
195
  this.codecs,
191
196
  correlationId,
@@ -205,7 +210,13 @@ export class ZLinkChannelOutboundOperations {
205
210
  let replyParts: readonly Message[] = [];
206
211
  try {
207
212
  try {
208
- replyParts = await awaitWithAbort(dealer.request(parts, timeoutMs), signal);
213
+ replyParts = await awaitWithAbort(
214
+ dealer.request(
215
+ parts,
216
+ remainingRequestTimeout(`Channel request '${channelName}'`, deadlineMs)
217
+ ),
218
+ signal
219
+ );
209
220
  } catch (error) {
210
221
  if (signal?.aborted === true) throw error;
211
222
  // Spec 32-framework-error-model:81-92 — classify the backend request
@@ -325,11 +336,10 @@ export class ZLinkChannelOutboundOperations {
325
336
  targetNodeRid: string,
326
337
  packetName: string | undefined,
327
338
  message: unknown,
328
- signal?: AbortSignal,
329
339
  metadata: ReadonlyMap<string, string> = EMPTY_OUTBOUND_METADATA
330
340
  ): Promise<ZLinkSubmitResult> {
331
341
  return runWithOutboundFlow(this.dispatchServices.flowCreationEnabled(), () =>
332
- this.routeSubmitScoped(routerChannelId, targetNodeRid, packetName, message, signal, metadata)
342
+ this.routeSubmitScoped(routerChannelId, targetNodeRid, packetName, message, metadata)
333
343
  );
334
344
  }
335
345
 
@@ -338,10 +348,8 @@ export class ZLinkChannelOutboundOperations {
338
348
  targetNodeRid: string,
339
349
  packetName: string | undefined,
340
350
  message: unknown,
341
- signal?: AbortSignal,
342
351
  metadata: ReadonlyMap<string, string> = EMPTY_OUTBOUND_METADATA
343
352
  ): Promise<ZLinkSubmitResult> {
344
- throwIfAborted(signal);
345
353
  const router = this.sockets.routeRouter(routerChannelId);
346
354
  const parts = encodeChannelEnvelopeParts(
347
355
  ZLinkChannelMessageKind.Command,
@@ -358,18 +366,8 @@ export class ZLinkChannelOutboundOperations {
358
366
  try {
359
367
  await router.send(targetNodeRid, parts);
360
368
  } catch (error) {
361
- if (isSubmitDeadline(error)) {
362
- this.dispatchServices.beginOutbound(ZLinkMessageFlowOutcome.Backpressured)?.trace({
363
- surface: ZLinkDispatchErrorSurface.RouteMeshChannel,
364
- messageKind: ZLinkDispatchMessageKind.Send,
365
- channelName: routerChannelId,
366
- channelRouteKind: 'route_mesh',
367
- packetName,
368
- correlationId: undefined,
369
- targetRid: targetNodeRid,
370
- result: 'backpressured'
371
- });
372
- return { status: ZLinkSubmitStatus.TimedOut };
369
+ if (isZLinkBackendResultError(error) && error.operation === 'submit') {
370
+ return classifySubmitResult(error.result, 'One-way send', error.phase);
373
371
  }
374
372
  throw error;
375
373
  }
@@ -233,10 +233,9 @@ export class ZLinkChannelRuntimeManager {
233
233
  channelName: string,
234
234
  packetName: string | undefined,
235
235
  message: unknown,
236
- signal?: AbortSignal,
237
236
  metadata?: ReadonlyMap<string, string>
238
237
  ): Promise<ZLinkSubmitResult> {
239
- return this.outbound.send(channelName, packetName, message, signal, metadata);
238
+ return this.outbound.send(channelName, packetName, message, metadata);
240
239
  }
241
240
 
242
241
  async request<TReply>(
@@ -283,17 +282,9 @@ export class ZLinkChannelRuntimeManager {
283
282
  targetNodeRid: string,
284
283
  packetName: string | undefined,
285
284
  message: unknown,
286
- signal?: AbortSignal,
287
285
  metadata?: ReadonlyMap<string, string>
288
286
  ): Promise<ZLinkSubmitResult> {
289
- return this.outbound.routeSubmit(
290
- routerChannelId,
291
- targetNodeRid,
292
- packetName,
293
- message,
294
- signal,
295
- metadata
296
- );
287
+ return this.outbound.routeSubmit(routerChannelId, targetNodeRid, packetName, message, metadata);
297
288
  }
298
289
 
299
290
  async routeRequest<TReply>(
@@ -320,18 +311,9 @@ export class ZLinkChannelRuntimeManager {
320
311
  spotRouteTarget: ZLinkSpotRouteTarget,
321
312
  packetName: string | undefined,
322
313
  message: unknown,
323
- signal?: AbortSignal,
324
- metadata?: ReadonlyMap<string, string>,
325
- timeoutMs?: number
314
+ metadata?: ReadonlyMap<string, string>
326
315
  ): Promise<void> {
327
- return this.spotRoutes.routeSendToSpot(
328
- spotRouteTarget,
329
- packetName,
330
- message,
331
- signal,
332
- metadata,
333
- timeoutMs
334
- );
316
+ return this.spotRoutes.routeSendToSpot(spotRouteTarget, packetName, message, metadata);
335
317
  }
336
318
 
337
319
  async routeRequestToSpot<TReply>(
@@ -375,18 +357,14 @@ export class ZLinkChannelRuntimeManager {
375
357
  spotRouteTarget: ZLinkSpotRouteTarget,
376
358
  packetName: string | undefined,
377
359
  message: unknown,
378
- signal?: AbortSignal,
379
- metadata?: ReadonlyMap<string, string>,
380
- timeoutMs?: number
360
+ metadata?: ReadonlyMap<string, string>
381
361
  ): Promise<void> {
382
362
  return this.spotRoutes.routeSendFromSpotToSpot(
383
363
  sourceSpot,
384
364
  spotRouteTarget,
385
365
  packetName,
386
366
  message,
387
- signal,
388
- metadata,
389
- timeoutMs
367
+ metadata
390
368
  );
391
369
  }
392
370
 
@@ -59,15 +59,6 @@ class ZLinkLiveSocketConfig implements ZLinkSocketConfig {
59
59
  requireValidSendTimeoutMs('receiveTimeoutMs', value);
60
60
  this.socket.receiveTimeoutMs = value;
61
61
  }
62
-
63
- get sendTimeoutMs(): number {
64
- return this.socket.sendTimeoutMs;
65
- }
66
-
67
- set sendTimeoutMs(value: number) {
68
- validateSendTimeout(value);
69
- this.socket.sendTimeoutMs = value;
70
- }
71
62
  }
72
63
 
73
64
  class ZLinkServerRuntimeOptions {
@@ -155,7 +146,3 @@ function validateHighWaterMark(value: number, label: string): void {
155
146
  throw new ZLinkConfigurationException(`${label} must be a non-negative integer.`);
156
147
  }
157
148
  }
158
-
159
- function validateSendTimeout(value: number): void {
160
- requireValidSendTimeoutMs('sendTimeoutMs', value);
161
- }
@@ -300,8 +300,7 @@ export class ZLinkChannelSocketRegistry {
300
300
  dealer.setRoutingId(deriveRoutingId(channel.routingId, 'dealer'));
301
301
  }
302
302
  applySocketConfig(dealer, {
303
- ...client,
304
- sendTimeoutMs: configuredSendTimeoutMs(client.sendTimeoutMs)
303
+ ...client
305
304
  });
306
305
  return dealer;
307
306
  }
@@ -455,8 +454,7 @@ export class ZLinkChannelSocketRegistry {
455
454
  dealer.setChannelName(channelName);
456
455
  dealer.setRoutingId(`cs-client-${randomUUID()}`);
457
456
  applySocketConfig(dealer, {
458
- ...client,
459
- sendTimeoutMs: configuredSendTimeoutMs(client.sendTimeoutMs)
457
+ ...client
460
458
  });
461
459
  connection.readablePoller = this.adapter.createReadablePoller(dealer);
462
460
  created.push(connection.readablePoller);
@@ -692,7 +690,7 @@ export class ZLinkChannelSocketRegistry {
692
690
  return undefined;
693
691
  }
694
692
 
695
- /** Observes discovery changes until the client DEALER admission deadline. */
693
+ /** Observes discovery changes until a server is ready or the runtime closes. */
696
694
  async awaitClientDealerForOutbound(
697
695
  channelName: string,
698
696
  signal?: AbortSignal
@@ -711,12 +709,8 @@ export class ZLinkChannelSocketRegistry {
711
709
  };
712
710
  const dealer = select();
713
711
  if (dealer !== undefined) return dealer;
714
- const sendTimeoutMs = configuredSendTimeoutMs(
715
- this.registration.channels.get(channelName)?.client?.sendTimeoutMs
716
- );
717
712
  return new Promise((resolve, reject) => {
718
713
  const cleanup = (): void => {
719
- clearTimeout(deadline);
720
714
  unsubscribe();
721
715
  signal?.removeEventListener('abort', abort);
722
716
  };
@@ -737,10 +731,6 @@ export class ZLinkChannelSocketRegistry {
737
731
  }
738
732
  };
739
733
  const unsubscribe = this.clientServerDiscovery.onClientServerChanged(changed);
740
- const deadline = setTimeout(() => {
741
- cleanup();
742
- resolve(undefined);
743
- }, sendTimeoutMs);
744
734
  signal?.addEventListener('abort', abort, { once: true });
745
735
  // Registration and selection share one event-loop turn; recheck after subscribing.
746
736
  changed();
@@ -2016,7 +2006,6 @@ function applySocketConfig(
2016
2006
  readonly sendHighWaterMark?: number;
2017
2007
  readonly receiveHighWaterMark?: number;
2018
2008
  readonly receiveTimeoutMs?: number;
2019
- readonly sendTimeoutMs?: number;
2020
2009
  readonly maxMessageSize?: number;
2021
2010
  }
2022
2011
  ): void {
@@ -2029,9 +2018,6 @@ function applySocketConfig(
2029
2018
  if (config.receiveTimeoutMs !== undefined) {
2030
2019
  socket.receiveTimeoutMs = config.receiveTimeoutMs;
2031
2020
  }
2032
- if (config.sendTimeoutMs !== undefined) {
2033
- socket.sendTimeoutMs = config.sendTimeoutMs;
2034
- }
2035
2021
  if (config.maxMessageSize !== undefined) {
2036
2022
  socket.maxMessageSize = config.maxMessageSize;
2037
2023
  }
@@ -66,7 +66,6 @@ export interface ZLinkChannelClientTransport {
66
66
  channelName: string,
67
67
  packetName: string | undefined,
68
68
  message: unknown,
69
- signal?: AbortSignal,
70
69
  metadata?: ReadonlyMap<string, string>
71
70
  ): void | ZLinkSubmitResult | Promise<void | ZLinkSubmitResult>;
72
71
  request<TReply>(
@@ -123,7 +122,6 @@ export interface ZLinkRouteClientTransport {
123
122
  targetNodeRid: string,
124
123
  packetName: string | undefined,
125
124
  message: unknown,
126
- signal?: AbortSignal,
127
125
  metadata?: ReadonlyMap<string, string>
128
126
  ): void | ZLinkSubmitResult | Promise<void | ZLinkSubmitResult>;
129
127
  request<TReply>(
@@ -140,7 +138,6 @@ export interface ZLinkRouteClientTransport {
140
138
  channelName: string,
141
139
  packetName: string | undefined,
142
140
  message: unknown,
143
- signal?: AbortSignal,
144
141
  metadata?: ReadonlyMap<string, string>
145
142
  ): void | ZLinkSubmitResult | Promise<void | ZLinkSubmitResult>;
146
143
  requestToChannel<TReply>(
@@ -157,8 +154,6 @@ export interface ZLinkRouteClientTransport {
157
154
  message: unknown,
158
155
  options: {
159
156
  readonly packetName?: string;
160
- readonly timeoutMs?: number;
161
- readonly signal?: AbortSignal;
162
157
  readonly metadata?: ReadonlyMap<string, string>;
163
158
  }
164
159
  ): Promise<ZLinkSubmitResult>;
@@ -179,7 +174,6 @@ interface ZLinkChannelTransportRuntime {
179
174
  channelName: string,
180
175
  packetName: string | undefined,
181
176
  message: unknown,
182
- signal?: AbortSignal,
183
177
  metadata?: ReadonlyMap<string, string>
184
178
  ): Promise<ZLinkSubmitResult>;
185
179
  request<TReply>(
@@ -212,7 +206,6 @@ interface ZLinkChannelTransportRuntime {
212
206
  targetNodeRid: string,
213
207
  packetName: string | undefined,
214
208
  message: unknown,
215
- signal?: AbortSignal,
216
209
  metadata?: ReadonlyMap<string, string>
217
210
  ): Promise<ZLinkSubmitResult>;
218
211
  routeRequest<TReply>(
@@ -228,18 +221,14 @@ interface ZLinkChannelTransportRuntime {
228
221
  spotRouteTarget: ZLinkSpotRouteTarget,
229
222
  packetName: string | undefined,
230
223
  message: unknown,
231
- signal?: AbortSignal,
232
- metadata?: ReadonlyMap<string, string>,
233
- timeoutMs?: number
224
+ metadata?: ReadonlyMap<string, string>
234
225
  ): Promise<void>;
235
226
  routeSendFromSpotToSpot(
236
227
  sourceSpot: ZLinkBackendSpot,
237
228
  spotRouteTarget: ZLinkSpotRouteTarget,
238
229
  packetName: string | undefined,
239
230
  message: unknown,
240
- signal?: AbortSignal,
241
- metadata?: ReadonlyMap<string, string>,
242
- timeoutMs?: number
231
+ metadata?: ReadonlyMap<string, string>
243
232
  ): Promise<void>;
244
233
  routeRequestToSpot<TReply>(
245
234
  spotRouteTarget: ZLinkSpotRouteTarget,
@@ -323,13 +312,12 @@ export class ZLinkRuntimeRouteTransport implements ZLinkRouteClientTransport {
323
312
  targetNodeRid: string,
324
313
  packetName: string | undefined,
325
314
  message: unknown,
326
- signal?: AbortSignal,
327
315
  metadata?: ReadonlyMap<string, string>
328
316
  ): Promise<ZLinkSubmitResult> {
329
317
  // Call-scoped flow (spec 27 §4): the envelope flow pair lives only for
330
318
  // the duration of this outbound call, never in the caller's context.
331
319
  return runWithOutboundFlow(this.flowCreationEnabled(), () =>
332
- this.submitNode(meshName, targetNodeRid, packetName, message, signal, metadata, false)
320
+ this.submitNode(meshName, targetNodeRid, packetName, message, metadata, false)
333
321
  );
334
322
  }
335
323
 
@@ -338,11 +326,10 @@ export class ZLinkRuntimeRouteTransport implements ZLinkRouteClientTransport {
338
326
  targetNodeRid: string,
339
327
  packetName: string | undefined,
340
328
  message: unknown,
341
- signal?: AbortSignal,
342
329
  metadata?: ReadonlyMap<string, string>
343
330
  ): Promise<ZLinkSubmitResult> {
344
331
  return runWithOutboundFlow(this.flowCreationEnabled(), () =>
345
- this.submitNode(meshName, targetNodeRid, packetName, message, signal, metadata, true)
332
+ this.submitNode(meshName, targetNodeRid, packetName, message, metadata, true)
346
333
  );
347
334
  }
348
335
 
@@ -351,7 +338,6 @@ export class ZLinkRuntimeRouteTransport implements ZLinkRouteClientTransport {
351
338
  targetNodeRid: string,
352
339
  packetName: string | undefined,
353
340
  message: unknown,
354
- signal: AbortSignal | undefined,
355
341
  metadata: ReadonlyMap<string, string> | undefined,
356
342
  allowObjectClientTarget: boolean
357
343
  ): Promise<ZLinkSubmitResult> {
@@ -362,11 +348,9 @@ export class ZLinkRuntimeRouteTransport implements ZLinkRouteClientTransport {
362
348
  targetNodeRid,
363
349
  packetName,
364
350
  message,
365
- signal,
366
351
  metadata
367
352
  );
368
353
  }
369
- throwIfAborted(signal);
370
354
  if (
371
355
  !allowObjectClientTarget &&
372
356
  node.isObjectClientNodeDirectTarget?.(toBackendRoutingId(targetNodeRid)) === true
@@ -536,11 +520,10 @@ export class ZLinkRuntimeRouteTransport implements ZLinkRouteClientTransport {
536
520
  channelName: string,
537
521
  packetName: string | undefined,
538
522
  message: unknown,
539
- signal?: AbortSignal,
540
523
  metadata?: ReadonlyMap<string, string>
541
524
  ): Promise<ZLinkSubmitResult> {
542
525
  return runWithOutboundFlow(this.flowCreationEnabled(), () =>
543
- this.submitToChannelScoped(meshName, channelName, packetName, message, signal, metadata)
526
+ this.submitToChannelScoped(meshName, channelName, packetName, message, metadata)
544
527
  );
545
528
  }
546
529
 
@@ -549,10 +532,8 @@ export class ZLinkRuntimeRouteTransport implements ZLinkRouteClientTransport {
549
532
  channelName: string,
550
533
  packetName: string | undefined,
551
534
  message: unknown,
552
- signal?: AbortSignal,
553
535
  metadata?: ReadonlyMap<string, string>
554
536
  ): Promise<ZLinkSubmitResult> {
555
- throwIfAborted(signal);
556
537
  const node = this.requireMeshNode(meshName);
557
538
  const parts = this.encodeMessage(
558
539
  ZLinkChannelMessageKind.Command,
@@ -693,13 +674,10 @@ export class ZLinkRuntimeRouteTransport implements ZLinkRouteClientTransport {
693
674
  spotRouteTarget,
694
675
  options.packetName,
695
676
  message,
696
- options.signal,
697
- options.metadata,
698
- options.timeoutMs
677
+ options.metadata
699
678
  );
700
679
  return { status: ZLinkSubmitStatus.Submitted };
701
680
  }
702
- throwIfAborted(options.signal);
703
681
  const operation = `MeshNode '${spotRouteTarget.routerChannelId}' send to Spot '${spotRouteTarget.spotId}'`;
704
682
  try {
705
683
  const encoded = this.encodeMessage(
@@ -747,8 +725,6 @@ export class ZLinkRuntimeRouteTransport implements ZLinkRouteClientTransport {
747
725
  message: unknown,
748
726
  options: {
749
727
  readonly packetName?: string;
750
- readonly timeoutMs?: number;
751
- readonly signal?: AbortSignal;
752
728
  readonly metadata?: ReadonlyMap<string, string>;
753
729
  }
754
730
  ): Promise<ZLinkSubmitResult> {
@@ -757,9 +733,7 @@ export class ZLinkRuntimeRouteTransport implements ZLinkRouteClientTransport {
757
733
  spotRouteTarget,
758
734
  options.packetName,
759
735
  message,
760
- options.signal,
761
- options.metadata,
762
- options.timeoutMs
736
+ options.metadata
763
737
  );
764
738
  return { status: ZLinkSubmitStatus.Submitted };
765
739
  }