@autofleet/rabbit 4.1.0-beta.0 → 4.1.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 (60) hide show
  1. package/dist/index.d.ts +81 -76
  2. package/dist/index.js +581 -472
  3. package/dist/index.js.map +1 -0
  4. package/dist/lib/celery.js +1 -0
  5. package/dist/lib/celery.js.map +1 -0
  6. package/dist/lib/consts.d.ts +12 -4
  7. package/dist/lib/consts.js +12 -3
  8. package/dist/lib/consts.js.map +1 -0
  9. package/dist/lib/rabbitError.js +1 -0
  10. package/dist/lib/rabbitError.js.map +1 -0
  11. package/dist/lib/redis.d.ts +2 -1
  12. package/dist/lib/redis.js +3 -8
  13. package/dist/lib/redis.js.map +1 -0
  14. package/dist/lib/types.d.ts +18 -5
  15. package/dist/lib/types.js +1 -0
  16. package/dist/lib/types.js.map +1 -0
  17. package/dist/lib/utils.d.ts +12 -3
  18. package/dist/lib/utils.js +23 -13
  19. package/dist/lib/utils.js.map +1 -0
  20. package/dist/logger.js +1 -0
  21. package/dist/logger.js.map +1 -0
  22. package/dist/{mock.d.ts → mock/index.d.ts} +1 -1
  23. package/dist/{mock.js → mock/index.js} +2 -1
  24. package/dist/mock/index.js.map +1 -0
  25. package/dist/mock/vitest.d.ts +13 -0
  26. package/dist/mock/vitest.js +18 -0
  27. package/dist/mock/vitest.js.map +1 -0
  28. package/package.json +24 -19
  29. package/src/index.ts +702 -591
  30. package/src/lib/consts.ts +17 -4
  31. package/src/lib/redis.ts +2 -7
  32. package/src/lib/types.ts +22 -7
  33. package/src/lib/utils.ts +35 -12
  34. package/src/{mock.ts → mock/index.ts} +2 -2
  35. package/src/mock/vitest.ts +24 -0
  36. package/src/redis-lock.d.ts +5 -3
  37. package/tsconfig.build.json +5 -0
  38. package/tsconfig.json +2 -2
  39. package/vitest.config.ts +17 -0
  40. package/coverage/clover.xml +0 -669
  41. package/coverage/coverage-final.json +0 -9
  42. package/coverage/lcov-report/base.css +0 -224
  43. package/coverage/lcov-report/block-navigation.js +0 -87
  44. package/coverage/lcov-report/favicon.png +0 -0
  45. package/coverage/lcov-report/index.html +0 -131
  46. package/coverage/lcov-report/prettify.css +0 -1
  47. package/coverage/lcov-report/prettify.js +0 -2
  48. package/coverage/lcov-report/sort-arrow-sprite.png +0 -0
  49. package/coverage/lcov-report/sorter.js +0 -196
  50. package/coverage/lcov-report/src/index.html +0 -131
  51. package/coverage/lcov-report/src/index.ts.html +0 -3826
  52. package/coverage/lcov-report/src/lib/celery.ts.html +0 -352
  53. package/coverage/lcov-report/src/lib/consts.ts.html +0 -142
  54. package/coverage/lcov-report/src/lib/index.html +0 -191
  55. package/coverage/lcov-report/src/lib/rabbitError.ts.html +0 -103
  56. package/coverage/lcov-report/src/lib/redis.ts.html +0 -133
  57. package/coverage/lcov-report/src/lib/types.ts.html +0 -268
  58. package/coverage/lcov-report/src/lib/utils.ts.html +0 -142
  59. package/coverage/lcov-report/src/logger.ts.html +0 -100
  60. package/coverage/lcov.info +0 -1076
package/src/lib/consts.ts CHANGED
@@ -1,4 +1,7 @@
1
- export const DEFAULT_DEAD_TTL_TWO_DAYS = 60000 * 60 * 12;
1
+ import type { BackoffOptions } from 'exponential-backoff';
2
+ import type { ConsumeOptions } from './types';
3
+
4
+ export const DEFAULT_DEAD_TTL_TWO_DAYS = 60_000 * 60 * 12;
2
5
  export const DEFAULT_LOCK_TIMEOUT = 1000 * 5;
3
6
  export const RETRY_HEADER = 'x-retry-count';
4
7
  export const TRACING_HEADER = 'x-trace-id';
@@ -6,8 +9,6 @@ export const USER_TRACING_HEADER = 'x-af-user-id';
6
9
  export const AUTOMATION_ID_HEADER = 'x-af-automation-id';
7
10
  export const USER_OBJECT = 'userObject';
8
11
  export const DEFAULT_USE_CONSUME_WITH_LOCK = false;
9
- export const CONNECTION_CREATED_CONST = 'connectionCreated';
10
- export const CONNECTION_FAILED_CONST = 'connectionFailed';
11
12
  export const DEFAULT_OPTIONS = {
12
13
  limit: 1,
13
14
  retries: 1,
@@ -16,4 +17,16 @@ export const DEFAULT_OPTIONS = {
16
17
  useConsumeWithLock: DEFAULT_USE_CONSUME_WITH_LOCK,
17
18
  auditContext: null,
18
19
  enableRabbitTrace: false,
19
- };
20
+ } satisfies ConsumeOptions;
21
+
22
+ export const ASSERT_VHOST_EXPONENTIAL_BACKOFF_DEV_ENV_CONFIG = {
23
+ startingDelay: 500,
24
+ timeMultiple: 4,
25
+ numOfAttempts: 5,
26
+ } satisfies BackoffOptions;
27
+
28
+ export const ASSERT_VHOST_EXPONENTIAL_BACKOFF_PROD_CONFIG = {
29
+ startingDelay: 1,
30
+ timeMultiple: 1,
31
+ numOfAttempts: 5,
32
+ } satisfies BackoffOptions;
package/src/lib/redis.ts CHANGED
@@ -1,9 +1,4 @@
1
- import bluebird from 'bluebird';
2
-
3
- const redis = require('redis');
4
-
5
- bluebird.promisifyAll(redis.RedisClient.prototype);
6
- bluebird.promisifyAll(redis.Multi.prototype);
1
+ import { createClient } from 'redis';
7
2
 
8
3
  export type RedisConfig = {
9
4
  host: string;
@@ -11,6 +6,6 @@ export type RedisConfig = {
11
6
  prefix?: string;
12
7
  }
13
8
 
14
- const getRedisInstance = (config: RedisConfig): any => redis.createClient(config);
9
+ const getRedisInstance = (config: RedisConfig): ReturnType<typeof createClient> => createClient({ socket: config });
15
10
 
16
11
  export default getRedisInstance;
package/src/lib/types.ts CHANGED
@@ -1,25 +1,25 @@
1
- import { ConsumeMessage, Options, Replies } from 'amqplib';
1
+ import type { AmqpConnectionManager } from 'amqp-connection-manager';
2
+ import type { ConsumeMessage, Options, Replies } from 'amqplib';
2
3
 
3
4
  export interface ExchangesCache {
4
- [key: string]: any
5
+ [key: string]: Replies.AssertExchange | undefined;
5
6
  }
6
7
 
7
8
  export interface QueuesCache {
8
- [key: string]: any
9
+ [key: string]: Replies.AssertQueue | undefined;
9
10
  }
10
11
 
11
12
  export interface QueueSetupPromisesDictionary {
12
- [key: string]: Promise<Replies.AssertQueue> | undefined
13
+ [key: string]: Promise<Replies.AssertQueue> | undefined;
13
14
  }
14
15
 
15
16
  export interface AssertExchangePromisesDictionary {
16
- [key: string]: Promise<Replies.AssertExchange> | undefined
17
+ [key: string]: Promise<Replies.AssertExchange> | undefined;
17
18
  }
18
19
 
19
20
  export type CustomMessageHeaders = {
20
21
  redisTimestampValidationKey?: string;
21
22
  }
22
- export type RedisLockType = (args0?: string, arg1?: number) => Promise<any>
23
23
  export type ConsumeMessageOrNull = ConsumeMessage | null;
24
24
 
25
25
  export interface ConsumeOptions {
@@ -31,10 +31,17 @@ export interface ConsumeOptions {
31
31
  useConsumeWithLock?: boolean;
32
32
  auditContext?: any;
33
33
  enableRabbitTrace?: boolean;
34
+ // TODO: [QUORUM-PHASE-3] Redundant because all the queues are quorum queues
34
35
  isQuorumQueue?: boolean;
35
36
  }
36
37
 
37
- export type CallbackFunction = (msg: ConsumeMessage, ack: any, nack: any) => Promise<any>
38
+ export interface NackOptions {
39
+ skipRetry?: boolean;
40
+ }
41
+
42
+ export type Message = Omit<ConsumeMessage, 'content'> & { content: any; };
43
+
44
+ export type CallbackFunction = (msg: Message, ack: () => Promise<void>, nack: (ignored: ConsumeMessageOrNull, nackOptions?: NackOptions) => Promise<void>) => Promise<void>;
38
45
 
39
46
  export type newChannelOpts = {
40
47
  name?: string;
@@ -60,3 +67,11 @@ export const CONSUMER_DEFAULT_OPTIONS: Options.Consume = {
60
67
  [HA_PROMOTE_ON_SHUTDOWN]: 'always',
61
68
  },
62
69
  };
70
+
71
+ export type ConnectionData = {
72
+ amqpConnection: AmqpConnectionManager | null;
73
+ creatingConnection: boolean;
74
+ connectionCreatedEventName: string;
75
+ connectionFailedEventName: string;
76
+ blockReconnect: boolean;
77
+ };
package/src/lib/utils.ts CHANGED
@@ -1,19 +1,42 @@
1
- import { ChannelWrapper } from 'amqp-connection-manager';
2
- import { ConfirmChannel, Replies } from 'amqplib';
1
+ import type { ConfirmChannel, Replies } from 'amqplib';
2
+ import type { ChannelWrapper } from 'amqp-connection-manager';
3
+ import type { BackoffOptions } from 'exponential-backoff';
4
+ import { ASSERT_VHOST_EXPONENTIAL_BACKOFF_PROD_CONFIG, ASSERT_VHOST_EXPONENTIAL_BACKOFF_DEV_ENV_CONFIG } from './consts';
5
+
6
+ const { PROJECT_ID } = process.env;
3
7
 
4
8
  export const assertExchangeFanout = async (
5
9
  c: ChannelWrapper | ConfirmChannel,
6
10
  exchangeName: string,
7
11
  ): Promise<Replies.AssertExchange> => c.assertExchange(exchangeName, 'fanout');
8
12
 
9
- export const wrapSetImmediate = (callback: () => any) => new Promise<any>((resolve, reject) => {
10
- setImmediate(async () => {
11
- try {
12
- const value = await callback();
13
- resolve(value);
14
- } catch (error) {
15
- reject(error);
16
- }
13
+ export const rand = (): number => Math.floor(Math.random() * 100_000);
14
+
15
+ interface PromiseWithResolvers<T> {
16
+ promise: Promise<T>;
17
+ resolve: (value: T | PromiseLike<T>) => void;
18
+ reject: (reason?: any) => void;
19
+ }
20
+ interface PromiseCls extends PromiseConstructor {
21
+ withResolvers<T>(): PromiseWithResolvers<T>;
22
+ }
23
+ /** This is polyfill for `Promise.withResolvers` which exists only on Node v22 and onwards */
24
+ export const createDeferredPromise = <T = void>(): PromiseWithResolvers<T> => {
25
+ if ((Promise as PromiseCls).withResolvers) {
26
+ return (Promise as PromiseCls).withResolvers<T>();
27
+ }
28
+ let resolve!: PromiseWithResolvers<T>['resolve'];
29
+ let reject!: PromiseWithResolvers<T>['reject'];
30
+ const promise = new Promise<T>((res, rej) => {
31
+ resolve = res;
32
+ reject = rej;
17
33
  });
18
- });
19
- export const rand = () => Math.floor(Math.random() * 100000);
34
+ return { promise, resolve, reject };
35
+ };
36
+
37
+ const isDevEnv = (): boolean => ['af-experiment-manager', 'dev1-experiment-manager'].includes(PROJECT_ID || '');
38
+
39
+ export const getAssertVhostExponentialBackoffConfig = (): BackoffOptions => (
40
+ isDevEnv()
41
+ ? ASSERT_VHOST_EXPONENTIAL_BACKOFF_DEV_ENV_CONFIG
42
+ : ASSERT_VHOST_EXPONENTIAL_BACKOFF_PROD_CONFIG);
@@ -1,6 +1,6 @@
1
- // eslint-disable-next-line import/no-extraneous-dependencies
1
+ // eslint-disable-next-line import/no-unresolved
2
2
  import 'jest';
3
- import { IAfRabbitMq } from './index';
3
+ import type { IAfRabbitMq } from '../index';
4
4
 
5
5
  class RabbitMq implements IAfRabbitMq {
6
6
  ack: any = jest.fn();
@@ -0,0 +1,24 @@
1
+ import { vi } from 'vitest';
2
+ import { IAfRabbitMq } from '../index';
3
+
4
+ class RabbitMq implements IAfRabbitMq {
5
+ ack = vi.fn();
6
+
7
+ nack = vi.fn();
8
+
9
+ assertChannel = vi.fn();
10
+
11
+ assertExchange = vi.fn();
12
+
13
+ assertQueue = vi.fn();
14
+
15
+ consume = vi.fn();
16
+
17
+ consumeFromExchange = vi.fn();
18
+
19
+ publish = vi.fn();
20
+
21
+ sendToQueue = vi.fn();
22
+ }
23
+
24
+ export default RabbitMq;
@@ -1,4 +1,6 @@
1
1
  declare module 'redis-lock' {
2
- const lock: any;
3
- export = lock;
4
- }
2
+ import type { createClient } from 'redis';
3
+
4
+ declare function redisLock(client: ReturnType<typeof createClient>, retryDelay?: number): (lockName: string, timeout?: number) => Promise<() => Promise<void>>;
5
+ export = redisLock;
6
+ }
@@ -0,0 +1,5 @@
1
+ {
2
+ "extends": "./tsconfig.json",
3
+ "include": ["src"],
4
+ "exclude": ["node_modules", "dist", "src/example.ts", "**/*.test.ts"],
5
+ }
package/tsconfig.json CHANGED
@@ -9,8 +9,8 @@
9
9
  "experimentalDecorators": true,
10
10
  "emitDecoratorMetadata": true,
11
11
  "skipLibCheck": true,
12
- "types": ["@types/jest"]
12
+ "sourceMap": true,
13
13
  },
14
14
  "exclude": ["node_modules"],
15
- "include": ["src/**/*.ts"]
15
+ "include": ["src/", "vitest.config.ts"],
16
16
  }
@@ -0,0 +1,17 @@
1
+ // eslint-disable-next-line import/no-unresolved
2
+ import { defineConfig } from 'vitest/config';
3
+
4
+ export default defineConfig({
5
+ test: {
6
+ coverage: {
7
+ provider: 'v8',
8
+ include: ['src/**/*.ts'],
9
+ exclude: ['src/example.ts', 'src/mock/*.ts'],
10
+ reporter: 'text',
11
+ thresholds: {
12
+ // TO DO: Increase the coverage threshold back to 75 in phase 3
13
+ lines: 65,
14
+ },
15
+ },
16
+ },
17
+ });