How to Drain an SQS Queue (Without Reprocessing)

If your SQS consumer 'processes' messages but the queue never empties, you're missing one call: delete_message. SQS only removes a message when you delete it - otherwise the visibility timeout expires and it comes back. Here's the correct loop.

Backend Engineerawssqspython

Why messages keep reappearing

SQS doesn't remove a message when you receive it - it just hides it for the visibility timeout. You're expected to process it and then explicitly delete it. If you don't delete, the timeout expires and SQS redelivers it, so the same messages get processed again and again and the depth never drops. That's at-least-once delivery working as designed - you just skipped the acknowledgement.

The correct receive -> process -> delete loop

import boto3
sqs = boto3.client("sqs")
url = "https://sqs.../orders"

while True:
    resp = sqs.receive_message(QueueUrl=url, MaxNumberOfMessages=10, WaitTimeSeconds=20)
    msgs = resp.get("Messages", [])
    if not msgs:
        break                          # queue drained
    for m in msgs:
        process(m)                     # do the work
        sqs.delete_message(            # ACK it - this is what removes it
            QueueUrl=url, ReceiptHandle=m["ReceiptHandle"])

delete_message with the message's ReceiptHandle is the acknowledgement. No delete = redelivery.

The details that matter

Want to try it hands-on? HeyDevJob gives you this exact setup in a live cloud workspace in your browser - edit it, run it, and see it work. Free, nothing to install.

Try it in a workspace →

What you'll practice

FAQ

Why do my SQS messages keep coming back after processing?

You didn't delete them. SQS only hides a message for the visibility timeout on receive; you must call delete_message with its ReceiptHandle to remove it. Without the delete, the timeout expires and SQS redelivers it.

When should I delete an SQS message?

Only after processing succeeds. If processing fails, skip the delete so the message reappears and retries - and configure a dead-letter queue so a message that keeps failing eventually moves off the main queue.

What is the SQS visibility timeout?

The window after a message is received during which it's hidden from other consumers. It must be longer than your processing time, or SQS redelivers the message while you're still working on it (causing duplicate processing).

Keep learning

Return the Correct HTTP Status CodeBackend projectRepair Broken API PaginationBackend projectAdd CORS Middleware to an Express APIBackend projectBackend roadmapStep by step to hiredBackend interview questionsSTAR answersAll Backend projectsProjects hub

Learn it by doing. Open this in a live cloud workspace, make the change yourself, and keep a record of the work you can share.

Open the workspace →