sqs-consumer 7.3.0 → 7.4.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.
@@ -18,3 +18,7 @@ jobs:
18
18
  days-before-issue-close: 5
19
19
  days-before-pr-close: 10
20
20
  operations-per-run: 90
21
+ exempt-issue-labels: keep
22
+ exempt-pr-labels: keep
23
+ exempt-all-assignees: true
24
+ exempt-all-milestones: true
@@ -9,6 +9,8 @@ export declare class Consumer extends TypedEventEmitter {
9
9
  private queueUrl;
10
10
  private handleMessage;
11
11
  private handleMessageBatch;
12
+ private preReceiveMessageCallback?;
13
+ private postReceiveMessageCallback?;
12
14
  private sqs;
13
15
  private handleMessageTimeout;
14
16
  private attributeNames;
@@ -21,6 +23,7 @@ export declare class Consumer extends TypedEventEmitter {
21
23
  private authenticationErrorTimeout;
22
24
  private pollingWaitTimeMs;
23
25
  private heartbeatInterval;
26
+ abortController: AbortController;
24
27
  constructor(options: ConsumerOptions);
25
28
  /**
26
29
  * Creates a new SQS consumer.
@@ -30,6 +33,10 @@ export declare class Consumer extends TypedEventEmitter {
30
33
  * Start polling the queue for messages.
31
34
  */
32
35
  start(): void;
36
+ /**
37
+ * A reusable options object for sqs.send that's used to avoid duplication.
38
+ */
39
+ private get sqsSendOptions();
33
40
  /**
34
41
  * Stop polling the queue for messages (pre existing requests will still be made until concluded).
35
42
  */
@@ -50,10 +57,6 @@ export declare class Consumer extends TypedEventEmitter {
50
57
  * @param message The message that the error occurred on
51
58
  */
52
59
  private emitError;
53
- /**
54
- * A reusable options object for sqs.send that's used to avoid duplication.
55
- */
56
- private sqsSendOptions;
57
60
  /**
58
61
  * Poll for new messages from SQS
59
62
  */
package/dist/consumer.js CHANGED
@@ -6,7 +6,6 @@ const emitter_1 = require("./emitter");
6
6
  const bind_1 = require("./bind");
7
7
  const errors_1 = require("./errors");
8
8
  const validation_1 = require("./validation");
9
- const controllers_1 = require("./controllers");
10
9
  const logger_1 = require("./logger");
11
10
  /**
12
11
  * [Usage](https://bbc.github.io/sqs-consumer/index.html#usage)
@@ -17,16 +16,12 @@ class Consumer extends emitter_1.TypedEventEmitter {
17
16
  super();
18
17
  this.pollingTimeoutId = undefined;
19
18
  this.stopped = true;
20
- /**
21
- * A reusable options object for sqs.send that's used to avoid duplication.
22
- */
23
- this.sqsSendOptions = {
24
- abortSignal: controllers_1.abortController.signal
25
- };
26
19
  (0, validation_1.assertOptions)(options);
27
20
  this.queueUrl = options.queueUrl;
28
21
  this.handleMessage = options.handleMessage;
29
22
  this.handleMessageBatch = options.handleMessageBatch;
23
+ this.preReceiveMessageCallback = options.preReceiveMessageCallback;
24
+ this.postReceiveMessageCallback = options.postReceiveMessageCallback;
30
25
  this.handleMessageTimeout = options.handleMessageTimeout;
31
26
  this.attributeNames = options.attributeNames || [];
32
27
  this.messageAttributeNames = options.messageAttributeNames || [];
@@ -58,12 +53,25 @@ class Consumer extends emitter_1.TypedEventEmitter {
58
53
  */
59
54
  start() {
60
55
  if (this.stopped) {
56
+ // Create a new abort controller each time the consumer is started
57
+ this.abortController = new AbortController();
61
58
  logger_1.logger.debug('starting');
62
59
  this.stopped = false;
63
60
  this.emit('started');
64
61
  this.poll();
65
62
  }
66
63
  }
64
+ /**
65
+ * A reusable options object for sqs.send that's used to avoid duplication.
66
+ */
67
+ get sqsSendOptions() {
68
+ var _a;
69
+ return {
70
+ // return the current abortController signal or a fresh signal that has not been aborted.
71
+ // This effectively defaults the signal sent to the AWS SDK to not aborted
72
+ abortSignal: ((_a = this.abortController) === null || _a === void 0 ? void 0 : _a.signal) || new AbortController().signal
73
+ };
74
+ }
67
75
  /**
68
76
  * Stop polling the queue for messages (pre existing requests will still be made until concluded).
69
77
  */
@@ -80,7 +88,7 @@ class Consumer extends emitter_1.TypedEventEmitter {
80
88
  }
81
89
  if (options === null || options === void 0 ? void 0 : options.abort) {
82
90
  logger_1.logger.debug('aborting');
83
- controllers_1.abortController.abort();
91
+ this.abortController.abort();
84
92
  this.emit('aborted');
85
93
  }
86
94
  this.emit('stopped');
@@ -167,7 +175,14 @@ class Consumer extends emitter_1.TypedEventEmitter {
167
175
  */
168
176
  async receiveMessage(params) {
169
177
  try {
170
- return await this.sqs.send(new client_sqs_1.ReceiveMessageCommand(params), this.sqsSendOptions);
178
+ if (this.preReceiveMessageCallback) {
179
+ await this.preReceiveMessageCallback();
180
+ }
181
+ const result = await this.sqs.send(new client_sqs_1.ReceiveMessageCommand(params), this.sqsSendOptions);
182
+ if (this.postReceiveMessageCallback) {
183
+ await this.postReceiveMessageCallback();
184
+ }
185
+ return result;
171
186
  }
172
187
  catch (err) {
173
188
  throw (0, errors_1.toSQSError)(err, `SQS receive message failed: ${err.message}`);
package/dist/types.d.ts CHANGED
@@ -102,6 +102,22 @@ export interface ConsumerOptions {
102
102
  * the successful messages only.
103
103
  */
104
104
  handleMessageBatch?(messages: Message[]): Promise<Message[] | void>;
105
+ /**
106
+ * An `async` function (or function that returns a `Promise`) to be called right
107
+ * before the SQS Client sends a receive message command.
108
+ *
109
+ * This function is usefull if SQS Client module exports have been modified, for
110
+ * example to add middlewares.
111
+ */
112
+ preReceiveMessageCallback?(): Promise<void>;
113
+ /**
114
+ * An `async` function (or function that returns a `Promise`) to be called right
115
+ * after the SQS Client sends a receive message command.
116
+ *
117
+ * This function is usefull if SQS Client module exports have been modified, for
118
+ * example to add middlewares.
119
+ */
120
+ postReceiveMessageCallback?(): Promise<void>;
105
121
  }
106
122
  export type UpdatableOptions = 'visibilityTimeout' | 'batchSize' | 'waitTimeSeconds';
107
123
  export interface StopOptions {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "sqs-consumer",
3
- "version": "7.3.0",
3
+ "version": "7.4.0",
4
4
  "description": "Build SQS-based Node applications without the boilerplate",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",
@@ -17,8 +17,8 @@
17
17
  "test:integration:init": "sh ./test/scripts/initIntTests.sh",
18
18
  "test:integration": "npm run test:integration:init && cucumber-js --config ./test/config/cucumber.js",
19
19
  "test": "npm run test:unit && npm run test:integration",
20
- "coverage": "nyc mocha && nyc report --reporter=html && nyc report --reporter=json-summary",
21
- "lcov": "nyc mocha && nyc report --reporter=lcov",
20
+ "coverage": "c8 mocha && c8 report --reporter=html && c8 report --reporter=json-summary",
21
+ "lcov": "c8 mocha && c8 report --reporter=lcov",
22
22
  "lint": "eslint . --ext .ts",
23
23
  "lint:fix": "eslint . --fix",
24
24
  "format": "prettier --loglevel warn --write \"**/*.{js,json,jsx,md,ts,tsx,html}\"",
@@ -41,37 +41,37 @@
41
41
  ],
42
42
  "license": "Apache-2.0",
43
43
  "devDependencies": {
44
- "@cucumber/cucumber": "^9.2.0",
45
- "@types/chai": "^4.3.5",
46
- "@types/mocha": "^10.0.1",
47
- "@types/node": "^20.4.1",
48
- "@types/sinon": "^10.0.15",
49
- "chai": "^4.3.7",
50
- "eslint": "^8.44.0",
51
- "eslint-config-iplayer-ts": "^4.1.1",
52
- "eslint-config-prettier": "^8.8.0",
44
+ "@cucumber/cucumber": "10.0.1",
45
+ "@types/chai": "^4.3.9",
46
+ "@types/mocha": "^10.0.3",
47
+ "@types/node": "^20.8.7",
48
+ "@types/sinon": "^10.0.20",
49
+ "chai": "^4.3.10",
50
+ "eslint": "^8.52.0",
51
+ "eslint-config-iplayer": "^9.1.0",
52
+ "eslint-config-prettier": "^9.0.0",
53
53
  "mocha": "^10.2.0",
54
- "nyc": "^15.1.0",
54
+ "c8": "^8.0.1",
55
55
  "p-event": "^4.2.0",
56
- "prettier": "^3.0.0",
57
- "sinon": "^15.2.0",
58
- "sqs-producer": "^3.2.1",
56
+ "prettier": "^3.0.3",
57
+ "sinon": "^17.0.0",
58
+ "sqs-producer": "^3.4.0",
59
59
  "ts-node": "^10.9.1",
60
- "typedoc": "^0.24.8",
61
- "typescript": "^4.9.4"
60
+ "typedoc": "^0.25.2",
61
+ "typescript": "^5.2.2"
62
62
  },
63
63
  "dependencies": {
64
- "@aws-sdk/client-sqs": "^3.363.0",
64
+ "@aws-sdk/client-sqs": "^3.428.0",
65
65
  "debug": "^4.3.4"
66
66
  },
67
67
  "peerDependencies": {
68
- "@aws-sdk/client-sqs": "^3.363.0"
68
+ "@aws-sdk/client-sqs": "^3.428.0"
69
69
  },
70
70
  "mocha": {
71
71
  "spec": "test/tests/**/**/*.test.ts",
72
72
  "require": "ts-node/register"
73
73
  },
74
- "nyc": {
74
+ "c8": {
75
75
  "include": [
76
76
  "src/**/*.ts"
77
77
  ],
@@ -86,7 +86,8 @@
86
86
  },
87
87
  "eslintConfig": {
88
88
  "extends": [
89
- "iplayer-ts",
89
+ "iplayer/base",
90
+ "iplayer/ts",
90
91
  "prettier"
91
92
  ],
92
93
  "parserOptions": {
package/src/consumer.ts CHANGED
@@ -26,7 +26,6 @@ import {
26
26
  isConnectionError
27
27
  } from './errors';
28
28
  import { validateOption, assertOptions, hasMessages } from './validation';
29
- import { abortController } from './controllers';
30
29
  import { logger } from './logger';
31
30
 
32
31
  /**
@@ -38,6 +37,8 @@ export class Consumer extends TypedEventEmitter {
38
37
  private queueUrl: string;
39
38
  private handleMessage: (message: Message) => Promise<Message | void>;
40
39
  private handleMessageBatch: (message: Message[]) => Promise<Message[] | void>;
40
+ private preReceiveMessageCallback?: () => Promise<void>;
41
+ private postReceiveMessageCallback?: () => Promise<void>;
41
42
  private sqs: SQSClient;
42
43
  private handleMessageTimeout: number;
43
44
  private attributeNames: string[];
@@ -50,6 +51,7 @@ export class Consumer extends TypedEventEmitter {
50
51
  private authenticationErrorTimeout: number;
51
52
  private pollingWaitTimeMs: number;
52
53
  private heartbeatInterval: number;
54
+ public abortController: AbortController;
53
55
 
54
56
  constructor(options: ConsumerOptions) {
55
57
  super();
@@ -57,6 +59,8 @@ export class Consumer extends TypedEventEmitter {
57
59
  this.queueUrl = options.queueUrl;
58
60
  this.handleMessage = options.handleMessage;
59
61
  this.handleMessageBatch = options.handleMessageBatch;
62
+ this.preReceiveMessageCallback = options.preReceiveMessageCallback;
63
+ this.postReceiveMessageCallback = options.postReceiveMessageCallback;
60
64
  this.handleMessageTimeout = options.handleMessageTimeout;
61
65
  this.attributeNames = options.attributeNames || [];
62
66
  this.messageAttributeNames = options.messageAttributeNames || [];
@@ -90,6 +94,8 @@ export class Consumer extends TypedEventEmitter {
90
94
  */
91
95
  public start(): void {
92
96
  if (this.stopped) {
97
+ // Create a new abort controller each time the consumer is started
98
+ this.abortController = new AbortController();
93
99
  logger.debug('starting');
94
100
  this.stopped = false;
95
101
  this.emit('started');
@@ -97,6 +103,17 @@ export class Consumer extends TypedEventEmitter {
97
103
  }
98
104
  }
99
105
 
106
+ /**
107
+ * A reusable options object for sqs.send that's used to avoid duplication.
108
+ */
109
+ private get sqsSendOptions(): { abortSignal: AbortSignal } {
110
+ return {
111
+ // return the current abortController signal or a fresh signal that has not been aborted.
112
+ // This effectively defaults the signal sent to the AWS SDK to not aborted
113
+ abortSignal: this.abortController?.signal || new AbortController().signal
114
+ };
115
+ }
116
+
100
117
  /**
101
118
  * Stop polling the queue for messages (pre existing requests will still be made until concluded).
102
119
  */
@@ -116,7 +133,7 @@ export class Consumer extends TypedEventEmitter {
116
133
 
117
134
  if (options?.abort) {
118
135
  logger.debug('aborting');
119
- abortController.abort();
136
+ this.abortController.abort();
120
137
  this.emit('aborted');
121
138
  }
122
139
 
@@ -163,13 +180,6 @@ export class Consumer extends TypedEventEmitter {
163
180
  }
164
181
  }
165
182
 
166
- /**
167
- * A reusable options object for sqs.send that's used to avoid duplication.
168
- */
169
- private sqsSendOptions = {
170
- abortSignal: abortController.signal
171
- };
172
-
173
183
  /**
174
184
  * Poll for new messages from SQS
175
185
  */
@@ -223,10 +233,18 @@ export class Consumer extends TypedEventEmitter {
223
233
  params: ReceiveMessageCommandInput
224
234
  ): Promise<ReceiveMessageCommandOutput> {
225
235
  try {
226
- return await this.sqs.send(
236
+ if (this.preReceiveMessageCallback) {
237
+ await this.preReceiveMessageCallback();
238
+ }
239
+ const result = await this.sqs.send(
227
240
  new ReceiveMessageCommand(params),
228
241
  this.sqsSendOptions
229
242
  );
243
+ if (this.postReceiveMessageCallback) {
244
+ await this.postReceiveMessageCallback();
245
+ }
246
+
247
+ return result;
230
248
  } catch (err) {
231
249
  throw toSQSError(err, `SQS receive message failed: ${err.message}`);
232
250
  }
package/src/types.ts CHANGED
@@ -103,6 +103,22 @@ export interface ConsumerOptions {
103
103
  * the successful messages only.
104
104
  */
105
105
  handleMessageBatch?(messages: Message[]): Promise<Message[] | void>;
106
+ /**
107
+ * An `async` function (or function that returns a `Promise`) to be called right
108
+ * before the SQS Client sends a receive message command.
109
+ *
110
+ * This function is usefull if SQS Client module exports have been modified, for
111
+ * example to add middlewares.
112
+ */
113
+ preReceiveMessageCallback?(): Promise<void>;
114
+ /**
115
+ * An `async` function (or function that returns a `Promise`) to be called right
116
+ * after the SQS Client sends a receive message command.
117
+ *
118
+ * This function is usefull if SQS Client module exports have been modified, for
119
+ * example to add middlewares.
120
+ */
121
+ postReceiveMessageCallback?(): Promise<void>;
106
122
  }
107
123
 
108
124
  export type UpdatableOptions =
@@ -1 +0,0 @@
1
- export declare const abortController: AbortController;
@@ -1,4 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.abortController = void 0;
4
- exports.abortController = new AbortController();
@@ -1 +0,0 @@
1
- export const abortController = new AbortController();