66
77namespace NATS . Client . Core . Internal ;
88
9- internal record struct SidMetadata ( NatsSubscriptionProps Properties , WeakReference < NatsSubBase > WeakReference ) ;
9+ internal record struct SidMetadata ( NatsSubscribeProps Properties , WeakReference < NatsSubBase > WeakReference ) ;
1010
1111internal sealed record SubscriptionMetadata ( int Sid ) ;
1212
@@ -41,7 +41,8 @@ public SubscriptionManager(NatsConnection connection, string inboxPrefix)
4141 _cleanupInterval = _connection . Opts . SubscriptionCleanUpInterval ;
4242 _timer = Task . Run ( CleanupAsync ) ;
4343 InboxSubBuilder = new InboxSubBuilder ( connection . Opts . LoggerFactory . CreateLogger < InboxSubBuilder > ( ) ) ;
44- _inboxSubSentinel = new InboxSub ( InboxSubBuilder , new NatsSubscriptionProps ( nameof ( _inboxSubSentinel ) , _connection . InboxPrefix ) , default , connection , this ) ;
44+ var sid = GetNextSid ( ) ;
45+ _inboxSubSentinel = new InboxSub ( InboxSubBuilder , new NatsSubscribeProps ( nameof ( _inboxSubSentinel ) ) { SubscriptionId = sid } , default , connection , this ) ;
4546 _inboxSub = _inboxSubSentinel ;
4647 }
4748
@@ -51,7 +52,13 @@ public SubscriptionManager(NatsConnection connection, string inboxPrefix)
5152
5253 public ValueTask SubscribeAsync ( NatsSubBase sub , CancellationToken cancellationToken )
5354 {
54- var props = new NatsSubscriptionProps ( sub . Subject , _connection . InboxPrefix , sub . QueueGroup ) ;
55+ var props = sub . SubscriptionProps ;
56+
57+ if ( props . SubscriptionId == 0 )
58+ {
59+ props . SubscriptionId = GetNextSid ( ) ;
60+ }
61+
5562 if ( Telemetry . HasListeners ( ) )
5663 {
5764 using var activity = Telemetry . StartSendActivity ( $ "{ _connection . SpanDestinationName ( sub . Subject ) } { Telemetry . Constants . SubscribeActivityName } ", _connection , sub . Subject , null , null ) ;
@@ -126,7 +133,7 @@ public ValueTask PublishToClientHandlersAsync(NatsProcessProps props, in ReadOnl
126133 {
127134 try
128135 {
129- return _connection . UnsubscribeAsync ( new NatsSubscriptionProps ( props . SubscriptionId ) ) ;
136+ return _connection . UnsubscribeAsync ( props ? . Subscription ?? new NatsUnsubscribeProps ( props . SubscriptionId ) ) ;
130137 }
131138 catch ( Exception e )
132139 {
@@ -216,7 +223,7 @@ internal async ValueTask WriteReconnectCommandsAsync(CommandWriter commandWriter
216223
217224 foreach ( var ( sub , sid ) in subs )
218225 {
219- await sub . WriteReconnectCommandsAsync ( commandWriter , new NatsSubscriptionProps ( sid ) ) . ConfigureAwait ( false ) ;
226+ await sub . WriteReconnectCommandsAsync ( commandWriter , sub . SubscriptionProps ) . ConfigureAwait ( false ) ;
220227
221228 if ( _debug )
222229 {
@@ -225,7 +232,7 @@ internal async ValueTask WriteReconnectCommandsAsync(CommandWriter commandWriter
225232 }
226233 }
227234
228- internal INatsSubscriptionManager GetManagerFor ( NatsSubscriptionProps props )
235+ internal INatsSubscriptionManager GetManagerFor ( NatsSubscribeProps props )
229236 {
230237 if ( props . IsInboxSubject ( _connection . InboxPrefix ) )
231238 return InboxSubBuilder ;
@@ -241,14 +248,14 @@ internal async Task InitializeInboxSubscriptionAsync(CancellationToken cancellat
241248 {
242249 if ( Interlocked . CompareExchange ( ref _inboxSub , _inboxSubSentinel , _inboxSubSentinel ) == _inboxSubSentinel )
243250 {
244- var inboxSubject = new NatsSubscriptionProps ( $ "{ _inboxPrefix } .*", _connection . InboxPrefix ) ;
251+ var props = new NatsSubscribeProps ( $ "{ _inboxPrefix } .*") ;
252+ props . SubscriptionId = GetNextSid ( ) ;
245253
246254 // We need to subscribe to the real inbox subject before we can register the internal subject.
247255 // We use 'default' options here since options provided by the user are for the internal subscription.
248256 // For example if the user provides a timeout, we don't want to timeout the real inbox subscription
249257 // since it must live duration of the connection.
250- _inboxSub = InboxSubBuilder . Build ( inboxSubject , opts : default , _connection , manager : this ) ;
251- var props = new NatsSubscriptionProps ( _inboxSub . Subject , _connection . InboxPrefix , _inboxSub . QueueGroup ) ;
258+ _inboxSub = InboxSubBuilder . Build ( props , opts : default , _connection , manager : this ) ;
252259 await SubscribeInternalAsync (
253260 props ,
254261 _inboxSub ,
@@ -262,16 +269,16 @@ await SubscribeInternalAsync(
262269 }
263270 }
264271
272+ internal int GetNextSid ( ) => Interlocked . Increment ( ref _sid ) ;
273+
265274 private async ValueTask SubscribeInboxAsync ( NatsSubBase sub , CancellationToken cancellationToken )
266275 {
267276 await InitializeInboxSubscriptionAsync ( cancellationToken ) . ConfigureAwait ( false ) ;
268277 await InboxSubBuilder . RegisterAsync ( sub ) . ConfigureAwait ( false ) ;
269278 }
270279
271- private async ValueTask SubscribeInternalAsync ( NatsSubscriptionProps props , NatsSubBase sub , CancellationToken cancellationToken )
280+ private async ValueTask SubscribeInternalAsync ( NatsSubscribeProps props , NatsSubBase sub , CancellationToken cancellationToken )
272281 {
273- props . SubscriptionId = GetNextSid ( ) ;
274-
275282 if ( sub is InboxSub )
276283 {
277284 Interlocked . Exchange ( ref _inboxSid , props . SubscriptionId ) ;
@@ -309,8 +316,6 @@ private async ValueTask SubscribeInternalAsync(NatsSubscriptionProps props, Nats
309316 }
310317 }
311318
312- private int GetNextSid ( ) => Interlocked . Increment ( ref _sid ) ;
313-
314319 private async Task CleanupAsync ( )
315320 {
316321 while ( ! _cts . Token . IsCancellationRequested )
@@ -352,7 +357,7 @@ private async ValueTask UnsubscribeSidsAsync(List<int> sids)
352357 try
353358 {
354359 _logger . LogWarning ( NatsLogEvents . Subscription , "Unsubscribing orphan subscription {Sid}" , sid ) ;
355- await _connection . UnsubscribeAsync ( new NatsSubscriptionProps ( sid ) ) . ConfigureAwait ( false ) ;
360+ await _connection . UnsubscribeAsync ( new NatsUnsubscribeProps ( sid ) ) . ConfigureAwait ( false ) ;
356361 }
357362 catch ( Exception e )
358363 {
0 commit comments