@@ -159,6 +159,94 @@ def test_failing_lambda_retries_after_visibility_timeout(
159
159
)
160
160
161
161
162
+ @pytest .mark .skip_snapshot_verify (
163
+ paths = [
164
+ # AWS returns empty lists for these values, even though they are not implemented yet
165
+ # https://docs.aws.amazon.com/AWSSimpleQueueService/latest/APIReference/API_MessageAttributeValue.html
166
+ "$..stringListValues" ,
167
+ "$..binaryListValues" ,
168
+ ]
169
+ )
170
+ @pytest .mark .aws_validated
171
+ def test_message_body_and_attributes_passed_correctly (
172
+ create_lambda_function ,
173
+ sqs_create_queue ,
174
+ sqs_queue_arn ,
175
+ lambda_su_role ,
176
+ snapshot ,
177
+ cleanups ,
178
+ aws_client ,
179
+ ):
180
+ # create queue used in the lambda to send events to (to verify lambda was invoked)
181
+ destination_queue_name = f"destination-queue-{ short_uid ()} "
182
+ destination_url = sqs_create_queue (QueueName = destination_queue_name )
183
+ snapshot .match (
184
+ "get_destination_queue_url" , aws_client .sqs .get_queue_url (QueueName = destination_queue_name )
185
+ )
186
+
187
+ # timeout in seconds, used for both the lambda and the queue visibility timeout
188
+ retry_timeout = 5
189
+ retries = 2
190
+
191
+ # set up lambda function
192
+ function_name = f"lambda-{ short_uid ()} "
193
+ create_lambda_function (
194
+ func_name = function_name ,
195
+ handler_file = LAMBDA_SQS_INTEGRATION_FILE ,
196
+ runtime = LAMBDA_RUNTIME_PYTHON38 ,
197
+ role = lambda_su_role ,
198
+ timeout = retry_timeout , # timeout needs to be <= than visibility timeout
199
+ )
200
+
201
+ # create dlq for event source queue
202
+ event_dlq_url = sqs_create_queue (QueueName = f"event-dlq-{ short_uid ()} " )
203
+ event_dlq_arn = sqs_queue_arn (event_dlq_url )
204
+
205
+ # create event source queue
206
+ event_source_url = sqs_create_queue (
207
+ QueueName = f"source-queue-{ short_uid ()} " ,
208
+ Attributes = {
209
+ # the visibility timeout is implicitly also the time between retries
210
+ "VisibilityTimeout" : str (retry_timeout ),
211
+ "RedrivePolicy" : json .dumps (
212
+ {"deadLetterTargetArn" : event_dlq_arn , "maxReceiveCount" : retries }
213
+ ),
214
+ },
215
+ )
216
+ event_source_arn = sqs_queue_arn (event_source_url )
217
+
218
+ # wire everything with the event source mapping
219
+ mapping_uuid = aws_client .awslambda .create_event_source_mapping (
220
+ EventSourceArn = event_source_arn ,
221
+ FunctionName = function_name ,
222
+ BatchSize = 1 ,
223
+ )["UUID" ]
224
+ cleanups .append (lambda : aws_client .awslambda .delete_event_source_mapping (UUID = mapping_uuid ))
225
+ _await_event_source_mapping_enabled (aws_client .awslambda , mapping_uuid )
226
+
227
+ # trigger lambda with a message and pass the result destination url. the event format is expected by the
228
+ # lambda_sqs_integration.py lambda.
229
+ event = {"destination" : destination_url , "fail_attempts" : 0 }
230
+ aws_client .sqs .send_message (
231
+ QueueUrl = event_source_url ,
232
+ MessageBody = json .dumps (event ),
233
+ MessageAttributes = {
234
+ "Title" : {"DataType" : "String" , "StringValue" : "The Whistler" },
235
+ "Author" : {"DataType" : "String" , "StringValue" : "John Grisham" },
236
+ "WeeksOn" : {"DataType" : "Number" , "StringValue" : "6" },
237
+ },
238
+ )
239
+
240
+ # now wait for the first invocation result which is expected to fail
241
+ response = aws_client .sqs .receive_message (
242
+ QueueUrl = destination_url ,
243
+ WaitTimeSeconds = 15 ,
244
+ MaxNumberOfMessages = 1 ,
245
+ )
246
+ assert "Messages" in response
247
+ snapshot .match ("first_attempt" , response )
248
+
249
+
162
250
@pytest .mark .skip_snapshot_verify (
163
251
paths = [
164
252
"$..ParallelizationFactor" ,
0 commit comments