@onlineapps/conn-infra-mq 1.1.31 → 1.1.33

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@onlineapps/conn-infra-mq",
3
- "version": "1.1.31",
3
+ "version": "1.1.33",
4
4
  "description": "A promise-based, broker-agnostic client for sending and receiving messages via RabbitMQ",
5
5
  "main": "src/index.js",
6
6
  "repository": {
@@ -295,62 +295,68 @@ class QueueManager {
295
295
 
296
296
  // CRITICAL: Use assertQueue directly - if queue exists with different args (406), that's OK
297
297
  // BUT: 406 PRECONDITION-FAILED closes the channel in amqplib!
298
- // Solution: Catch 406, recreate channel, and continue
298
+ // Solution: Catch 406, recreate channel immediately, and continue
299
+ let queueCreated = false;
299
300
  try {
300
- // Check if channel is still open before each operation
301
- if (!channel || channel.closed) {
302
- console.error(`[QueueManager] DEBUG: Channel closed before creating ${queueName}, recreating...`);
303
- // Recreate channel if closed
304
- channel = await transport._connection.createChannel();
305
- transport.queueChannel = channel;
306
- console.log(`[QueueManager] DEBUG: Channel recreated for ${queueName}`);
307
- }
308
-
309
301
  console.log(`[QueueManager] DEBUG: About to assertQueue ${queueName} with options:`, JSON.stringify(queueOptions, null, 2));
310
- console.log(`[QueueManager] DEBUG: Channel state before assertQueue: closed=${channel.closed}`);
311
302
 
312
303
  await channel.assertQueue(queueName, queueOptions);
313
304
 
314
- console.log(`[QueueManager] DEBUG: assertQueue succeeded for ${queueName}, channel closed=${channel.closed}`);
305
+ console.log(`[QueueManager] DEBUG: assertQueue succeeded for ${queueName}`);
315
306
  queues[queueInfo.type] = queueName;
307
+ queueCreated = true;
316
308
  console.info(`[QueueManager] ✓ Created business queue: ${queueName}`);
317
309
  } catch (assertErr) {
318
310
  console.error(`[QueueManager] DEBUG: assertQueue failed for ${queueName}:`, assertErr.message);
319
- console.error(`[QueueManager] DEBUG: Error code: ${assertErr.code}, channel closed: ${channel ? channel.closed : 'N/A'}`);
311
+ console.error(`[QueueManager] DEBUG: Error code: ${assertErr.code}`);
320
312
 
321
- // If 406 PRECONDITION-FAILED, queue exists with different args - channel is closed, recreate it
313
+ // If 406 PRECONDITION-FAILED, queue exists with different args - channel is closed, recreate it IMMEDIATELY
322
314
  // CRITICAL: amqplib closes channel on 406, so we MUST recreate it to continue
323
315
  if (assertErr.code === 406) {
324
- console.warn(`[QueueManager] Queue ${queueName} exists with different arguments (406), channel closed. Recreating channel...`);
316
+ console.warn(`[QueueManager] Queue ${queueName} exists with different arguments (406), channel will be closed. Recreating channel...`);
325
317
 
326
- // Recreate channel - 406 closes it
318
+ // Recreate channel IMMEDIATELY - 406 closes it synchronously
327
319
  try {
320
+ // Wait a tiny bit for channel close event to propagate
321
+ await new Promise(resolve => setImmediate(resolve));
328
322
  channel = await transport._connection.createChannel();
329
323
  transport.queueChannel = channel;
330
- console.log(`[QueueManager] DEBUG: Channel recreated after 406 for ${queueName}, channel closed=${channel.closed}`);
324
+ console.log(`[QueueManager] DEBUG: Channel recreated after 406 for ${queueName}`);
331
325
  } catch (recreateErr) {
332
326
  throw new Error(`Failed to recreate channel after 406 for ${queueName}: ${recreateErr.message}`);
333
327
  }
334
328
 
335
329
  // Queue exists (just with different args) - accept it
336
330
  queues[queueInfo.type] = queueName;
331
+ queueCreated = true;
337
332
  } else {
338
- // Other error - check if channel closed
339
- if (!channel || channel.closed) {
340
- console.error(`[QueueManager] DEBUG: Channel was closed during assertQueue for ${queueName}`);
333
+ // Other error - check if it's a channel closed error
334
+ if (assertErr.message && assertErr.message.includes('Channel closed')) {
335
+ console.error(`[QueueManager] DEBUG: Channel was closed during assertQueue for ${queueName}, recreating...`);
341
336
  // Try to recreate channel
342
337
  try {
338
+ await new Promise(resolve => setImmediate(resolve));
343
339
  channel = await transport._connection.createChannel();
344
340
  transport.queueChannel = channel;
345
- console.log(`[QueueManager] DEBUG: Channel recreated after error for ${queueName}`);
341
+ console.log(`[QueueManager] DEBUG: Channel recreated after channel closed error for ${queueName}`);
346
342
  } catch (recreateErr) {
347
343
  throw new Error(`Channel closed during assertQueue for ${queueName} and failed to recreate: ${recreateErr.message}`);
348
344
  }
345
+ // Retry assertQueue with new channel (but only if it's not 406)
346
+ if (assertErr.code !== 406) {
347
+ throw new Error(`Failed to create business queue ${queueName}: ${assertErr.message}`);
348
+ }
349
+ } else {
350
+ // Other error - critical, cannot continue
351
+ throw new Error(`Failed to create business queue ${queueName}: ${assertErr.message}`);
349
352
  }
350
- // Other error - critical, cannot continue
351
- throw new Error(`Failed to create business queue ${queueName}: ${assertErr.message}`);
352
353
  }
353
354
  }
355
+
356
+ // Verify queue was created/confirmed
357
+ if (!queueCreated) {
358
+ throw new Error(`Failed to create or confirm business queue ${queueName}`);
359
+ }
354
360
  }
355
361
 
356
362
  // Setup DLQ exchange and bindings