serverless-plugins
serverless-plugins copied to clipboard
serverless-offline-sqs: Cannot create queue with RedrivePolicy
I'm not sure whether this is an issue with the plugin or the core serverless-offline itself, so apologies if it's the latter. I have an SQS queue with the following Serverless YAML config:
Type: AWS::SQS::Queue
Properties:
QueueName: '${self:service}-event-source-${self:custom.environment}'
VisibilityTimeout: '${self:custom.sqs.visibilityTimeout.${self:custom.environment}, self:custom.sqs.visibilityTimeout.default}'
DelaySeconds: '${self:custom.sqs.delaySeconds.${self:custom.environment}, self:custom.sqs.delaySeconds.default}'
KmsMasterKeyId: ${self:custom.kmsKeyId}
RedrivePolicy:
deadLetterTargetArn: !GetAtt SqsEventSourceDlq.Arn
maxReceiveCount: '${self:custom.sqs.maxReceiveCount.${self:custom.environment}, self:custom.sqs.maxReceiveCount.default}'
In serverless-offline 5.x with serverless-offline-sqs 3.x, the queue is created and functions correctly. The dead letter queue is not created, but I'm aware there is already an issue open about this (#65), and this is not important to our local setup.
In serverless-offline 6.x with serverless-offline-sqs 4.x, the queue fails to create with the following error (SLS_DEBUG on):
AWS.SimpleQueueService.NonExistentQueue: AWS.SimpleQueueService.NonExistentQueue; see the SQS docs.
at Request.extractError (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/protocol/query.js:50:29)
at Request.callListeners (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/sequential_executor.js:106:20)
at Request.emit (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/sequential_executor.js:78:10)
at Request.emit (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/request.js:688:14)
at Request.transition (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/request.js:22:10)
at AcceptorStateMachine.runTo (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/state_machine.js:14:12)
at /home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/state_machine.js:26:10
at Request.<anonymous> (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/request.js:38:9)
at Request.<anonymous> (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/request.js:690:12)
at Request.callListeners (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/sequential_executor.js:116:18)
at Request.emit (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/sequential_executor.js:78:10)
at Request.emit (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/request.js:688:14)
at Request.transition (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/request.js:22:10)
at AcceptorStateMachine.runTo (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/state_machine.js:14:12)
at /home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/state_machine.js:26:10
at Request.<anonymous> (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/request.js:38:9)
at Request.<anonymous> (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/request.js:690:12)
at Request.callListeners (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/sequential_executor.js:116:18)
at callNextListener (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/sequential_executor.js:96:12)
at IncomingMessage.onEnd (/home/node/app/node_modules/serverless-offline-sqs/node_modules/aws-sdk/lib/event_listeners.js:313:13)
at IncomingMessage.emit (events.js:203:15)
at IncomingMessage.EventEmitter.emit (domain.js:448:20)
at endReadableNT (_stream_readable.js:1143:12)
at process._tickCallback (internal/process/next_tick.js:63:19)
From previous event:
at PluginManager.invoke (/home/node/app/node_modules/serverless/lib/classes/PluginManager.js:498:22)
at getHooks.reduce.then (/home/node/app/node_modules/serverless/lib/classes/PluginManager.js:533:24)
From previous event:
at PluginManager.run (/home/node/app/node_modules/serverless/lib/classes/PluginManager.js:533:8)
at variables.populateService.then (/home/node/app/node_modules/serverless/lib/Serverless.js:162:33)
From previous event:
at Serverless.run (/home/node/app/node_modules/serverless/lib/Serverless.js:149:74)
at serverless.init.then.then (/home/node/app/node_modules/serverless/scripts/serverless.js:58:26)
at runCallback (timers.js:705:18)
at tryOnImmediate (timers.js:676:5)
at processImmediate (timers.js:658:5)
at process.topLevelDomainCallback (domain.js:126:23)
From previous event:
at Object.<anonymous> (/home/node/app/node_modules/serverless/scripts/serverless.js:58:4)
at Module._compile (internal/modules/cjs/loader.js:778:30)
at Object.Module._extensions..js (internal/modules/cjs/loader.js:789:10)
at Module.load (internal/modules/cjs/loader.js:653:32)
at tryModuleLoad (internal/modules/cjs/loader.js:593:12)
at Function.Module._load (internal/modules/cjs/loader.js:585:3)
at Module.require (internal/modules/cjs/loader.js:692:17)
at require (internal/modules/cjs/helpers.js:25:18)
at Object.<anonymous> (/home/node/app/node_modules/serverless/bin/serverless.js:41:1)
at Module._compile (internal/modules/cjs/loader.js:778:30)
at Object.Module._extensions..js (internal/modules/cjs/loader.js:789:10)
at Module.load (internal/modules/cjs/loader.js:653:32)
at tryModuleLoad (internal/modules/cjs/loader.js:593:12)
at Function.Module._load (internal/modules/cjs/loader.js:585:3)
at Function.Module.runMain (internal/modules/cjs/loader.js:831:12)
at startup (internal/bootstrap/node.js:283:19)
at bootstrapNodeJSCore (internal/bootstrap/node.js:623:3)
Investigating this, we discovered that, if the RedrivePolicy
is removed, the queue will be created successfully. This would be a workaround; however, we need the RedrivePolicy when we deploy to production, and it doesn't seem possible to put a condition on a RedrivePolicy.
Essentially, something that used to work with an old version of the plugin is broken with the current one, which means we can't upgrade to the current version. It's also not a configuration error on our side as it works with 'online' Serverless.
We have exactly the same problem! Would appreciate a solution :)
@jlippitt - After a few attempts, I found a temporary solution / workaround for our local environment.
The problem seems to be the "Autostart" function. Maybe a timing issue?
Our solution looks like this:
serverless-offline-sqs:
autoCreate: false
Create SQS Queues on Docker startup manually:
aws sqs create-queue --queue-name <YOUR-QUEUE_NAME>-local --endpoint-url http://sqs:9324 --region eu-central-1
Can confirm was having the same issue but @davidjung1977 workaround worked for me.
This is also affecting us. We're going with the above mentioned workaround temporarily but we're still hoping this get's fixed soon so that we can use "autoCreate: true" as intended.
We are facing the same problem, would be nice to have a "real" fix. For now we are going to try out the fix that is mentioned by @davidjung1977
Hi guys, I'm seeing this open conversation and would like to ask you about a problem I'm facing at the moment. Basically, I managed to set up the serverless-offline-sqs locally but it's not working when I run the solution locally in Debugging mode. Has one of you encountered this problem before, please?
For everyone having this problem and also using elasticmq, instead of the problematic autoCreate: true
you can use a config for elasticmq pretty easily:
https://github.com/softwaremill/elasticmq#automatically-creating-queues-on-startup
Actually seems like there's no support for SQS Queues with RedrivePolicy from this plugin. My workaround was just to use the serverless-plugin-ifelse
to exclude the RedrivePolicy property definition in a local
stage. It worked and let me create the SQS Queues i needed. Here's what I did:
serverless.yml
custom:
serverlessIfElse:
- If: '"${opt:stage}" == "local"'
Exclude:
- resources.Resources.JobProcessQueue.Properties.RedrivePolicy
- resources.Resources.JobEventProcessQueue.Properties.RedrivePolicy
serverless-offline-sqs:
autoCreate: true
apiVersion: "2012-11-05"
endpoint: http://localhost:9324
region: us-east-1
skipCacheInvalidation: false
plugins:
- serverless-plugin-ifelse
- serverless-offline-sqs
- serverless-offline
And voila! It worked perfectly. Hope this help anybody else
We are facing the same problem, would be nice to have a "real" fix. For now we are going to try out the fix that is mentioned by @davidjung1977
+1
If your dead letter queue follows a consistent naming schema you can replace the following function in src/sqs.js:
create(events) {
return Promise.all(events.map(({functionKey, sqs}) => this._create(functionKey, sqs)));
}
with this one:
create(events) {
const sortedEvents = events.sort((a, b) => {
const aContainsDlq = a.functionKey.includes('-dlq-');
const bContainsDlq = b.functionKey.includes('-dlq-');
return bContainsDlq - aContainsDlq;
});
return sortedEvents.reduce((promiseChain, event) => {
return promiseChain.then(() => this._create(event.functionKey, event.sqs));
}, Promise.resolve());
}
Just replace -dlq-
with your naming schema.