Amazon SQS Limits: Max Number of Messages per Receive, in a Queue and in Flight, OverLimit, FIFO Throughput, Message Size and Every Quota
The maximum number of messages in Amazon SQS depends on which limit you mean. Per receive call: up to 10 (MaxNumberOfMessages takes 1 to 10, default 1), and batch send and delete also take 10. In the queue: unlimited; there is no cap on stored messages. In flight (received but not yet deleted): about 120,000 for a standard queue, where short polling then returns an OverLimit error, and 120,000 for a FIFO queue, which returns no error but slows down. The other key limits: messages up to 1 MiB, retention from 60 seconds to 14 days (default 4 days), visibility timeout up to 12 hours, delay up to 15 minutes, long polling up to 20 seconds, standard queues with nearly unlimited throughput, and FIFO queues at 300 calls per second per action (3,000 messages with batching) or up to 70,000 per second in high throughput mode in the biggest Regions. Below: every quota in one table, which ones you can raise, the in-flight trap and how to fix OverLimit, FIFO throughput by Region, the request math behind the bill, and the errors each limit produces.
Jake's image pipeline had worked for a year with twenty workers. For a sale weekend he scaled to two hundred, each pulling ten messages at a time and taking a few minutes per image. Halfway through Saturday the workers started logging OverLimit and the queue stopped draining, even though there were millions of messages waiting. The queue was not full; it cannot be. Too many messages were out on loan at once.
New to SQS, or chasing a related problem? The cards below cover what SQS is, the message size error, missing messages and dead-letter queues.
Every Amazon SQS limit in one table
| Limit | Value | Can you raise it? |
|---|---|---|
| Messages per ReceiveMessage call | 1 to 10 (default 1) | No |
| Messages per batch send, delete or visibility change | 10, and 1 MiB per batch in total | No |
| Messages stored in a queue (backlog) | Unlimited | Not needed |
| In-flight messages, standard queue | About 120,000 | Yes, through a quota request |
| In-flight messages, FIFO queue | 120,000 | Yes, through AWS Support |
| Message size | 1 byte to 1 MiB (1,048,576 bytes) | No; use S3 for bigger payloads |
| Message retention | 60 seconds to 14 days, default 4 days | No |
| Visibility timeout | 0 seconds to 12 hours, default 30 seconds | No |
| Delay (queue or per message) | 0 to 15 minutes | No |
| Long polling wait | Up to 20 seconds | No |
| Message attributes | 10 per message | No |
| Queue name | 80 characters: letters, numbers, - and _; FIFO names end in .fifo | No |
| Queues listed per ListQueues call | 1,000 (use the next token for more) | No |
| Tags per queue | 50 suggested maximum; tagging calls 30 per second per account | Tagging rate, yes |
| Batch entry ID | 80 characters | No |
| MessageGroupId | 128 characters; required on FIFO queues | No |
| Queue access policy | 8,192 bytes, 20 statements, 50 principals, 10 conditions | No |
| Dead-letter maxReceiveCount | You choose; 10 is the usual starting point | Your setting |
The headline: SQS will store as many messages as you send it. The limits you will actually hit are the per-call batch of 10, the in-flight ceiling, FIFO throughput, and the time limits that decide how long your message can wait or hide. If you only remember one row, make it the in-flight one: it is the limit that stops your consumers while your queue looks healthy.
Max number of messages per receive: 10
One ReceiveMessage call returns at most 10 messages. MaxNumberOfMessages accepts 1 to 10 and defaults to 1, which is why code that leaves it out crawls along one message per call. Ask for 11 and the call fails with "Value 11 for parameter MaxNumberOfMessages is invalid. Reason: Must be between 1 and 10, if provided."
import boto3
sqs = boto3.client("sqs", region_name="eu-west-2")
url = sqs.get_queue_url(QueueName="image-jobs")["QueueUrl"]
while True:
resp = sqs.receive_message(
QueueUrl=url,
MaxNumberOfMessages=10, # the maximum
WaitTimeSeconds=20, # long polling: fewer empty responses
VisibilityTimeout=300, # longer than one batch takes to process
)
msgs = resp.get("Messages", [])
if not msgs:
continue
for m in msgs:
process(m["Body"])
sqs.delete_message_batch(
QueueUrl=url,
Entries=[{"Id": str(i), "ReceiptHandle": m["ReceiptHandle"]} for i, m in enumerate(msgs)],
)
From the CLI, the same call is aws sqs receive-message --queue-url URL --max-number-of-messages 10 --wait-time-seconds 20.
Why you get fewer than 10. With short polling (WaitTimeSeconds=0), SQS samples only some of its servers, so a queue with fewer than about 1,000 messages often returns fewer than you asked for, and sometimes none at all even when messages are waiting. Long polling up to 20 seconds asks all the servers and waits for messages to arrive, which fills batches better and cuts empty, billable responses. FIFO queues can also return fewer, because messages from a group that already has a message in flight are held back to keep the order. If messages seem stuck rather than slow, our messages not received guide walks through every cause.
Jake: "Can I ask for 100 at once if I raise a quota?"
Ethan: "No, 10 is fixed. For more throughput, run more receive calls in parallel."
Max number of messages in a queue: unlimited
An SQS queue can hold an unlimited number of messages. A backlog of millions is normal during a spike; the only time pressure is the retention period, after which unread messages are deleted (4 days by default, 14 days at most). To see how many messages are in a queue:
aws sqs get-queue-attributes --queue-url https://sqs.eu-west-2.amazonaws.com/111122223333/image-jobs \ --attribute-names ApproximateNumberOfMessages ApproximateNumberOfMessagesNotVisible ApproximateNumberOfMessagesDelayed
- ApproximateNumberOfMessages: waiting to be received (the backlog).
- ApproximateNumberOfMessagesNotVisible: in flight, received but not yet deleted. Watch this one against the 120,000 limit.
- ApproximateNumberOfMessagesDelayed: sent with a delay that has not expired.
The numbers are approximate because SQS is distributed, so your count may jump around for about a minute before it settles. In CloudWatch, the same values are the ApproximateNumberOfMessagesVisible and ApproximateNumberOfMessagesNotVisible metrics, and ApproximateAgeOfOldestMessage warns you before retention starts deleting anything.
The life of an SQS message: stored, in flight, deleted
Every SQS limit makes more sense once you picture the three states a message goes through:
- Stored: a producer sent it, and it waits in the queue. There is no limit on how many messages can be stored; the retention period decides how long each one may wait.
- In flight: a consumer received it, and it is hidden from other consumers for the visibility timeout. This is the state with the 120,000 limit.
- Deleted: the consumer finished and called
DeleteMessagewith the receipt handle. Only now is the message gone.
If the consumer never deletes it, the visibility timeout expires and the message returns to the stored state, with its receive count one higher, until maxReceiveCount sends it to the dead-letter queue or the retention period deletes it. Each receive returns a new receipt handle, and only the latest one can delete or extend the message, so store the handle from the receive you are working on, not from an earlier attempt. Receiving is not consuming: a message is only done when your code deletes it, which is why forgotten deletes are behind so many duplicate-processing and in-flight problems.
The in-flight limit and the OverLimit error
A message is in flight from the moment a consumer receives it until it is deleted or its visibility timeout runs out. Standard queues allow about 120,000 in-flight messages (the exact ceiling depends on traffic and backlog); FIFO queues allow 120,000. What happens at the limit:
- Standard queue, short polling:
ReceiveMessagefails withOverLimit, "the specified action violates a limit". - Standard queue, long polling: no error; receives simply come back empty.
- FIFO queue: no error, but processing slows until messages are deleted.
Jake's arithmetic shows how fast you get there: 200 workers × 10 messages × several minutes each, plus messages that were received, failed and sat hidden for the whole visibility timeout. The fixes, roughly in order:
- Delete each message as soon as it is processed, ideally with
DeleteMessageBatch. Workers that delete only at the end of a long batch keep everything in flight for the whole batch. - Size the visibility timeout to the real work: a 12-hour timeout on a job that takes 2 minutes keeps failed messages in flight for 12 hours. Use
ChangeMessageVisibilityto extend only the messages that genuinely need longer. - Receive only what a worker can process: a worker that takes 10 messages and handles them one by one over 20 minutes holds 9 of them in flight for no reason.
- Send poison messages to a dead-letter queue, so messages that fail again and again stop cycling through flight; our DLQ guide sets this up.
- Split the work across more queues if one queue truly needs more than 120,000 messages in progress at once.
- Request a quota increase in Service Quotas (standard) or through AWS Support (FIFO) if the design really needs it.
Jake: "So adding workers made it worse?"
Ethan: "Adding workers that hold messages for minutes did. Delete as you go and the same two hundred will fly."
SQS max receive count: how many retries before the dead-letter queue
The maxReceiveCount in a queue's redrive policy is the number of times a message can be received without being deleted before SQS moves it to the dead-letter queue (DLQ). Every receive counts, including ones where your consumer crashed or ran past the visibility timeout, and the message's ApproximateReceiveCount attribute shows how many times it has been received so far.
aws sqs set-queue-attributes --queue-url https://sqs.eu-west-2.amazonaws.com/111122223333/image-jobs \
--attributes '{"RedrivePolicy": "{\"deadLetterTargetArn\":\"arn:aws:sqs:eu-west-2:111122223333:image-jobs-dlq\",\"maxReceiveCount\":\"5\"}"}'
How to choose the number:
- Not 1: a single failed receive (a deploy restarting your workers, a brief database blip) would send good messages to the DLQ.
- 3 to 5 suits most workers: enough for transient errors to clear, few enough that a poison message does not cycle for long.
- Higher with Lambda batches: if a whole batch is retried when one message fails, the good messages in it are received again too; use partial batch responses, or a higher count, so they are not pushed to the DLQ by their neighbors' failures.
Three rules from how SQS handles DLQs. The DLQ must be the same type (standard or FIFO) and in the same account and Region as the source queue. On standard queues, a message keeps its original enqueue timestamp when it moves, so a DLQ with the same retention as the source deletes failed messages sooner than you expect; give the DLQ a longer retention, ideally the 14-day maximum. FIFO queues reset the timestamp when a message moves. And on standard queues with a maxReceiveCount above 3, a message received three or more times without deletion is moved to the back of the queue, so one poison message does not block the others. When the cause is fixed, use DLQ redrive in the console or API to move the messages back to the source queue; our DLQ redrive guide walks through it.
Jake: "Half our good orders ended up in the dead-letter queue during the deploy."
Ethan: "maxReceiveCount was 1. Every worker restart counted as a failure. Set it to 5."
SQS throughput limits: standard vs FIFO
Standard queues support a nearly unlimited number of calls per second for each action (SendMessage, ReceiveMessage, DeleteMessage). You have no per-queue rate to plan around; you scale your producers and consumers, and SQS keeps up. The trade-off is at-least-once delivery and best-effort ordering, covered in our duplicates guide.
FIFO queues are limited by API calls, not messages. Without high throughput mode, each partition handles 300 calls per second per action, which is 3,000 messages per second if every call carries a batch of 10. High throughput mode (set DeduplicationScope to messageGroup and FifoThroughputLimit to perMessageGroupId) raises the ceiling by Region:
| Region | Calls per second (no batching) | Messages per second (batches of 10) |
|---|---|---|
| US East (N. Virginia), US West (Oregon), Europe (Ireland) | 70,000 | 700,000 |
| US East (Ohio), Europe (Frankfurt) | 19,000 | 190,000 |
| Mumbai, Singapore, Sydney, Tokyo, Spain | 9,000 | 90,000 |
| Europe (London), South America (Sao Paulo) | 4,500 | 45,000 |
| All other Regions | 2,400 | 24,000 |
High throughput only helps if your messages are spread across many message group IDs, because messages within one group are still delivered one after another. A FIFO queue where every message uses the same group ID behaves like a single lane however high the quota. There is no limit on the number of message groups, so use a natural key such as a customer or order ID. Our MessageGroupId guide covers choosing one. Going past these rates gives throttling errors; ask for more through Service Quotas.
Batch calls: 10 at a time, and check the failures
Batch versions exist for sending, deleting and changing visibility, each taking up to 10 entries. They cut requests (and cost) by up to ten times, with one catch: a batch call can partly succeed. The call itself returns success while some entries fail, listed in the response's Failed array:
resp = sqs.send_message_batch(QueueUrl=url, Entries=[
{"Id": str(i), "MessageBody": body} for i, body in enumerate(bodies) # up to 10
])
for failure in resp.get("Failed", []):
print("retry needed:", failure["Id"], failure["Code"], failure.get("Message"))
Code that ignores Failed silently loses messages on send, or leaves messages undeleted (and in flight) on delete. Retry the failed entries, and log the ones whose SenderFault is true, since those will fail again until the request is fixed. Batch IDs only need to be unique within one call; 0 to 9 is fine.
Batching pays off most on the consumer side, where every received message must also be deleted. A worker that receives 10 messages and deletes them one by one makes 11 calls; the same worker with DeleteMessageBatch makes 2. Group deletes by when the work finishes, not by when messages arrived, so a slow message does not hold nine finished ones in flight while you wait to fill a batch.
Long jobs: extending the visibility timeout
For jobs whose length varies, setting a huge visibility timeout for everything keeps failed messages hidden far too long. The better pattern is a heartbeat: start with a modest timeout, and while the job is still running, call ChangeMessageVisibility every few minutes to extend it. If the worker dies, the heartbeats stop and the message reappears quickly for another worker.
There is a ceiling: a message's visibility cannot be extended beyond 12 hours from when it was received, so jobs that might run longer belong in a different design, such as Step Functions or a job table in a database, with SQS only carrying the start signal. Our duplicates guide covers what happens when the timeout runs out mid-job.
Encryption and its cost at scale
Queues are encrypted at rest by default with SQS-managed keys (SSE-SQS), at no extra charge. Switching to a customer managed KMS key (SSE-KMS) gives you control over the key and its policy, but SQS then calls KMS for data keys, and those calls are billed. The KmsDataKeyReusePeriodSeconds setting, from 60 seconds to 24 hours with a default of 5 minutes, controls how long SQS reuses a data key: a longer period means fewer KMS calls and a smaller bill, a shorter one limits how much data one key protects. Producers and consumers also need permission to use the key (kms:GenerateDataKey to send, kms:Decrypt to receive), and a missing key permission shows up as a KmsAccessDenied error rather than an SQS permission error.
FIFO queue limits and rules in detail
FIFO queues trade throughput for ordering and exactly-once processing, and they have rules standard queues do not:
- Names end in
.fifo, and the suffix counts toward the 80-character limit. You cannot convert a standard queue to FIFO or back; create a new queue and move producers and consumers over. MessageGroupIdis required on every message (up to 128 characters). Messages with the same group ID are delivered strictly in order, one batch at a time; different groups proceed in parallel.- Deduplication uses a 5-minute interval: a message with the same
MessageDeduplicationIdsent again within 5 minutes is accepted but not delivered twice. Turn on content-based deduplication to have SQS hash the body for you instead of supplying an ID. - In-flight messages block their group: while a message from a group is in flight, no later message from that group is delivered, so a slow or stuck consumer stalls that whole group until the visibility timeout ends.
- Dead-letter queues break strict order: a message moved to the DLQ lets later messages in its group continue, which is fine for most work but wrong where every step depends on the one before.
- Per-message delay is not supported: only a queue-level delay applies to FIFO queues.
The throughput figures above apply per action, so a busy FIFO queue spends its calls on sends, receives and deletes separately; batching all three is what lets one queue carry thousands of messages per second.
Time limits: retention, visibility timeout, delay and long polling
Four settings decide how long a message can wait, hide or be held back. Set them per queue with set-queue-attributes:
aws sqs set-queue-attributes --queue-url https://sqs.eu-west-2.amazonaws.com/111122223333/image-jobs \ --attributes MessageRetentionPeriod=1209600,VisibilityTimeout=300,ReceiveMessageWaitTimeSeconds=20,DelaySeconds=0
- MessageRetentionPeriod: 60 to 1,209,600 seconds (14 days), default 345,600 (4 days). Lowering it can delete existing messages older than the new value, and the change can take up to 15 minutes to apply.
- VisibilityTimeout: 0 to 43,200 seconds (12 hours), default 30. Set it a little longer than your processing time; too short gives duplicates, too long delays retries and fills the in-flight count.
- DelaySeconds: 0 to 900 seconds (15 minutes) for the whole queue, or per message with
DelaySecondson send (standard queues only). For longer delays, use EventBridge Scheduler or Step Functions. - ReceiveMessageWaitTimeSeconds: 0 to 20 seconds. Set 20 as the queue default to turn on long polling for every consumer.
Most attribute changes take up to 60 seconds to reach every SQS server, so test a minute after you change them.
Jake: "Can I keep failed orders for a month while we fix the bug?"
Ethan: "Not in SQS; 14 days is the ceiling. Move them to a dead-letter queue and copy anything you need longer into S3."
Message size limit: 1 MiB
A message can be up to 1,048,576 bytes (1 MiB), counting the body and all its attributes, and a batch of up to 10 messages has the same 1 MiB total. The queue's MaximumMessageSize can be set lower (from 1 KiB), which is the usual cause of size errors on queues created years ago with the old 256 KiB value. For anything bigger, store the payload in S3 and send a pointer; the Extended Client Libraries for Java and Python do this automatically, for payloads up to 2 GB. Our message size guide covers the "must be shorter than 262144 bytes" error and its fixes, and our attributes guide explains how the 10 attributes count toward the size.
Message attribute limits
Message attributes carry metadata next to the body, such as a content type, a tenant ID or a trace ID, and they have their own limits: up to 10 attributes per message, names up to 256 characters (letters, numbers, underscores, hyphens and periods, not starting with AWS. or Amazon.), and data types of String, Number or Binary. Names, types and values all count toward the 1 MiB message size. Consumers must ask for them explicitly with MessageAttributeNames=["All"] on receive, or they arrive without them, which is the most common "my attributes disappeared" question. When you need more than 10 values, put them in the JSON body instead and keep attributes for the few fields a consumer or an SNS filter must read without parsing the body. Our attributes vs body guide covers when to use each.
Jake: "We need 14 attributes per message for the new billing service."
Ethan: "Keep the two the router needs as attributes and move the rest into the JSON body."
SQS limits with Lambda: batch size and concurrency
When Lambda reads the queue for you, you stop calling ReceiveMessage yourself, and the limits you tune move to the event source mapping:
- Batch size: up to 10,000 messages per invocation for standard queues (above 10 you must set a batching window of at least 1 second), and up to 10 for FIFO queues.
- Payload: the whole batch must fit Lambda's 6 MB invocation payload, which caps large messages long before 10,000.
- Visibility timeout: set the queue's to at least six times the function timeout, so your retries stay apart.
- Maximum concurrency: a setting on the mapping (2 to 1,000) that limits how many functions the queue can run at once, so a backlog does not take all your account's Lambda concurrency.
- Partial batch failures: return
batchItemFailuresso only the failed messages go back to the queue instead of the whole batch.
If Lambda cannot read the queue at all, the cause is usually permissions; our Lambda SQS AccessDenied guide fixes the policy side.
Monitoring SQS before you hit a limit
Every limit on this page shows up in CloudWatch before it hurts, if you watch the right metrics in the AWS/SQS namespace:
- ApproximateNumberOfMessagesNotVisible: in-flight messages. Alarm well below the ceiling, for example at 80,000 on a standard queue.
- ApproximateAgeOfOldestMessage: how long the oldest message has waited. Alarm at a fraction of your retention period, so messages are never deleted unread.
- ApproximateNumberOfMessagesVisible: the backlog. A steady rise means consumers cannot keep up.
- NumberOfEmptyReceives: wasted, billable polls; a high number means long polling is off.
- The DLQ's ApproximateNumberOfMessagesVisible: anything above zero means messages are failing; alarm on it.
aws cloudwatch put-metric-alarm --alarm-name image-jobs-in-flight \ --namespace AWS/SQS --metric-name ApproximateNumberOfMessagesNotVisible \ --dimensions Name=QueueName,Value=image-jobs --statistic Maximum \ --period 300 --evaluation-periods 2 --threshold 80000 \ --comparison-operator GreaterThanThreshold \ --alarm-actions arn:aws:sns:eu-west-2:111122223333:ops-alerts
Use alarm periods of five minutes rather than one: SQS metrics can arrive with gaps, especially for queues that go quiet, and a very short period turns those gaps into false alarms or "insufficient data". Our CloudWatch alarm guide explains how to treat those gaps.
Scaling consumers to stay inside the limits
Most SQS limit problems are really consumer problems: too few workers and the backlog grows, too many slow ones and the in-flight count explodes. Scale on the right signal:
- ECS or EC2 workers: scale on backlog per worker (visible messages divided by running tasks), with a target your workers can clear in an acceptable time. Scaling on CPU misses the point when workers are waiting on I/O.
- Lambda: Lambda adds concurrent functions as the backlog grows; set maximum concurrency on the event source mapping so a backlog cannot exhaust the account's Lambda concurrency or overwhelm a database.
- Downstream limits first: the right number of consumers is often set by what they call (a database's connection limit, a partner API's rate limit), not by SQS. Size the worker pool to that, and let the queue absorb the peaks; that is what it is for.
Jake: "So the queue isn't the bottleneck, the workers are?"
Ethan: "Nearly always. The queue holds millions without blinking; your database doesn't."
Checking and raising SQS quotas
The adjustable SQS quotas live in Service Quotas: open the console, choose AWS services, then Amazon Simple Queue Service, or list them from the CLI with aws service-quotas list-service-quotas --service-code sqs. Requests for higher in-flight limits on standard queues go through Service Quotas; FIFO in-flight increases and some throughput increases go through AWS Support with a description of your workload. Raise a quota only after the fixes above: a higher in-flight limit postpones the problem if consumers hold messages too long. When you do ask, include your peak message rate, average processing time and the in-flight peak you measured, since a request with numbers is answered faster than one without.
Fixed limits (10 messages per receive, 1 MiB per message, 14-day retention, 12-hour visibility timeout, 15-minute delay) cannot be raised by anyone, so designs that need more must change shape: S3 for big payloads, a database or Step Functions for long waits, or several queues for more parallelism.
SNS to SQS fan-out: limits along the way
When SNS delivers to SQS (one message to many queues), the stricter limit wins at each step. SNS has its own maximum message size, smaller than SQS's 1 MiB, so a large message is rejected by SNS before SQS sees it; our message size guide covers that case. Turn on raw message delivery on the subscription if your consumers want the original body rather than SNS's JSON envelope, and remember that message attributes travel too and count toward the size. For FIFO fan-out, both the topic and the queues must be FIFO.
Two more fan-out limits matter in practice. Each SQS queue subscribed to a topic needs a queue policy that allows that topic to send to it; a missing policy makes delivery fail quietly from the publisher's point of view, so watch the topic's failed-delivery metrics. And SNS subscription filter policies let each queue receive only the messages it cares about, which saves the receive and delete requests your consumers would otherwise spend throwing irrelevant messages away.
Designing around the fixed limits
When a requirement runs into a limit that cannot be raised, the answer is a small change of design rather than a workaround:
- Payloads over 1 MiB: store the payload in S3 and send its key in the message (the Extended Client Libraries automate this); set an S3 lifecycle rule so the payloads do not outlive their messages.
- Delays over 15 minutes: schedule the message instead of delaying it. EventBridge Scheduler's one-time
at()schedules can send to SQS at an exact future time; our EventBridge scheduling guide shows how. - Keeping messages over 14 days: move them to S3 or a database when they arrive, and use the queue only for work in progress.
- More than 10 per receive: run more receive calls in parallel, from more threads or more workers.
- Ordering at high volume: FIFO with many message group IDs, or a standard queue with ordering handled in the consumer using sequence numbers in the message.
SQS limits compared with SNS and EventBridge
Teams often pick between SQS, SNS and EventBridge partly on their limits. The ones that usually decide it:
| SQS | SNS | EventBridge | |
|---|---|---|---|
| Model | Queue: consumers pull | Topic: pushes to subscribers | Event bus: routes by rules |
| Message size | 1 MiB | 256 KB | 256 KB per event |
| Holding messages | Up to 14 days, unlimited backlog | No storage; retries delivery | No queue; retries up to 24 hours, optional archive |
| Batching | 10 per call | 10 per publish batch | 10 entries per PutEvents |
| Best for | Buffering work for consumers at their own pace | Fan-out to many subscribers | Routing events between services by content |
They are often used together: EventBridge or SNS routes and fans out, and an SQS queue in front of each consumer absorbs bursts and holds work when a consumer is down. That combination gives you the routing of the first two and the backlog and retry control of SQS.
Testing a queue before a busy day
- Copy the production setup to a test queue: same type, visibility timeout, DLQ and consumer code.
- Send a realistic burst with batch sends from a few parallel scripts, at the peak rate you expect and then double it.
- Watch the in-flight and age metrics while consumers work through it, and note where in-flight messages level off.
- Kill a consumer mid-test and confirm its messages reappear after the visibility timeout and get processed.
- Check the DLQ and the downstream systems: the queue will cope; the question is whether your database and APIs do.
- Delete the test queue and its messages afterwards, so test data cannot leak into real processing.
A one-hour test the week before a sale is cheap insurance; the requests for a few million test messages cost a couple of dollars.
Run the test in the same Region and account setup as production, since quotas and network paths differ between accounts. Write down what you learn: the in-flight peak, how long the backlog took to drain, and which downstream system slowed first. Those three numbers tell you how many workers to run on the day, which alarms to set, and where to add capacity, far better than any limit table. Repeat the test after big code changes, since a slower consumer changes every number, and keep the results with the runbook.
How SQS counts requests (and the free tier)
Every SQS action is a request, and every 64 KB chunk of payload counts as one request. A single call can carry 1 to 10 messages up to 1 MiB in total, so batching is the cheapest way to move volume. The first 1 million requests a month are free for every account. After that, standard queues cost about $0.40 per million requests and FIFO queues about $0.50 in US East, with lower rates at very high volume.
Long polling shows the effect of request counting most clearly. One consumer short-polling an empty queue once a second makes about 2.6 million receive calls a month (86,400 a day for 30 days), most of them empty, which costs around a dollar beyond the free tier for a single idle worker. The same consumer with 20-second long polling makes at most about 130,000 calls a month, and every one has a chance of returning work. Multiply by a fleet of workers and the difference becomes a real line on the bill.
Three steps cut your request count, in the order that usually saves you the most:
- Batch everything: when you send 10 small messages in one
SendMessageBatch, you pay for 1 request instead of 10, and the same goes forDeleteMessageBatch. - Turn on long polling: your empty receives are billed too, and 20-second waits cut them sharply on quiet queues.
- Keep messages small: a 256 KB message is 4 requests and a 1 MiB message is 16, so if you send big payloads, put them in S3 and send a pointer.
Jake: "Our bill says 900 million requests, but we only send 50 million messages."
Ethan: "Count the empty receives from short polling and the deletes one by one. Batch and long-poll, and you lose most of that."
Errors each SQS limit produces
OverLimit: too many in-flight messages (short polling on a standard queue), or too many permissions on a queue. Fix with the in-flight steps above.- "Value 11 for parameter MaxNumberOfMessages is invalid": ask for 10 or fewer.
TooManyEntriesInBatchRequest: more than 10 entries in a batch call; split into groups of 10.BatchRequestTooLong: the batch adds up to more than 1 MiB; send fewer or smaller messages per batch.BatchEntryIdsNotDistinct: two entries in one batch share anId; use 0 to 9.- "Message must be shorter than ... bytes": the message or the queue's
MaximumMessageSize; see the size section. RequestThrottled: a FIFO queue past its call rate, or tagging past 30 calls per second.InvalidAttributeValue: a setting outside its range, such as a visibility timeout over 43,200 or retention over 1,209,600.MissingParameterfor MessageGroupId: FIFO queues need it on every message.
To branch on these codes in Python, read e.response["Error"]["Code"]; our ClientError guide shows the pattern.
Frequently asked questions
What is the maximum number of messages in an SQS queue?
Unlimited. SQS stores any number of messages; they are deleted only when consumed or when the retention period (up to 14 days) ends.
What is the max number of messages SQS returns per receive?
10. MaxNumberOfMessages accepts 1 to 10 and defaults to 1.
What is the SQS in-flight message limit?
About 120,000 for standard queues and 120,000 for FIFO queues; messages count from receipt until they are deleted or become visible again.
What does OverLimit mean in SQS?
The queue reached its in-flight limit (or a permission limit); delete processed messages promptly and shorten long visibility timeouts.
What is the SQS message size limit?
1 MiB (1,048,576 bytes) per message including attributes, and 1 MiB per batch; use S3 with the Extended Client for larger payloads.
How long can a message stay in SQS?
Between 60 seconds and 14 days, set by MessageRetentionPeriod; the default is 4 days.
What is the maximum SQS visibility timeout?
12 hours (43,200 seconds); the default is 30 seconds.
What is the SQS FIFO throughput limit?
300 calls per second per action per partition, or 3,000 messages with batching; high throughput mode reaches 70,000 calls per second in the largest Regions.
How many messages can I send in one SQS batch?
Up to 10 messages per SendMessageBatch, with a combined size of 1 MiB.
Why does SQS return fewer messages than MaxNumberOfMessages?
Short polling samples only some servers; use long polling with WaitTimeSeconds up to 20, and remember FIFO holds back messages from busy groups.
What is the maximum SQS delay?
15 minutes (900 seconds), for a queue or for an individual standard-queue message.
What is the SQS long polling maximum?
20 seconds per ReceiveMessage call.
How long can an SQS queue name be?
80 characters of letters, numbers, hyphens and underscores; FIFO queue names must end in .fifo, which counts toward the 80.
What is the maximum Lambda batch size for SQS?
10,000 for standard queues with a batching window, and 10 for FIFO queues.
Can I increase SQS limits?
The in-flight limits and some throughput quotas can be raised; batch size, message size, retention and timeout ranges are fixed.
How many message attributes can an SQS message have?
Up to 10, and they count toward the 1 MiB size limit.
Why are SQS message attributes missing when I receive?
The receive call must request them with MessageAttributeNames=["All"] (or specific names); otherwise they are not returned.
How long can an SQS message attribute name be?
Up to 256 characters of letters, numbers, underscores, hyphens and periods, not starting with AWS. or Amazon.
What is the difference between SQS, SNS and EventBridge limits?
SQS holds up to 1 MiB messages for up to 14 days with an unlimited backlog; SNS and EventBridge cap messages at 256 KB and push them on rather than storing them.
Should I put an SQS queue behind SNS or EventBridge?
Often yes: the queue absorbs bursts and holds messages while a consumer is down, which push-based services do not do on their own.
How do I delay an SQS message longer than 15 minutes?
Schedule it instead: an EventBridge Scheduler one-time at() schedule can send the message to SQS at the exact time you need.
How do I load test an SQS queue?
Send a realistic burst to a copy of the queue with batch sends, watch in-flight and message-age metrics, kill a consumer to test recovery, and check downstream systems.
What happens if I ignore failures in SendMessageBatch?
Those messages are lost: the call succeeds overall while failed entries are listed in the Failed array, which you must check and retry.
How do I run SQS jobs longer than 12 hours?
Visibility cannot be extended past 12 hours from receipt; use Step Functions or a job table for long work and SQS only to start it.
Does SQS encryption cost extra?
SSE-SQS is free; SSE-KMS with your own key adds KMS request charges, reduced by a longer data key reuse period.
What does in flight mean in SQS?
A message that a consumer has received but not yet deleted; it is hidden from others until deleted or until its visibility timeout ends.
What is maxReceiveCount in SQS?
The number of times a message can be received without being deleted before SQS moves it to the dead-letter queue; 3 to 5 suits most workers.
What retention should an SQS dead-letter queue have?
Longer than the source queue, ideally 14 days, because standard-queue messages keep their original enqueue time when they move.
Can I convert a standard SQS queue to FIFO?
No. Create a new FIFO queue (its name must end in .fifo) and move producers and consumers to it.
What is the SQS FIFO deduplication interval?
5 minutes: a message with the same deduplication ID sent again within that time is accepted but not delivered twice.
Which CloudWatch metrics show SQS limits?
ApproximateNumberOfMessagesNotVisible for in-flight, ApproximateAgeOfOldestMessage for retention risk, and the DLQ's visible messages for failures.
How do I request an SQS quota increase?
Use Service Quotas for adjustable SQS quotas, or AWS Support for FIFO in-flight and some throughput increases.
Is SQS free?
The first 1 million requests a month are free for every account; after that you pay per million requests, with each 64 KB chunk counting as one request.
How do I see how many messages are in an SQS queue?
Read ApproximateNumberOfMessages and ApproximateNumberOfMessagesNotVisible with get-queue-attributes or in CloudWatch.
For readers preparing for an AWS certification
We have been covering AWS certifications alongside our fixes, so here is a short extra for readers studying for one. If you only came for the fix, you already have it; feel free to skip this part.
Exams that test this topic: Developer – Associate (DVA-C03 from December 1, 2026) • Solutions Architect – Associate (SAA-C03) • CloudOps Engineer – Associate (SOA-C03).
Here are the exam-style questions this topic tends to raise, with the reasoning you need to answer them:
1. What is the maximum number of messages one SQS ReceiveMessage call can return?
10.
2. Consumers on a standard queue get OverLimit errors while millions of messages wait. What is the likely cause?
Too many in-flight messages (about 120,000); delete messages promptly and shorten long visibility timeouts.
3. Which setting reduces empty responses and cost when polling a quiet SQS queue?
Long polling, with a wait time of up to 20 seconds.
4. What is the maximum SQS message retention period?
14 days (the default is 4 days).
5. How can a FIFO queue exceed 300 transactions per second per action?
Batch up to 10 messages per call and enable high throughput mode with many message group IDs.
6. An application must send 5 MB payloads through SQS. What is the standard approach?
Store the payload in S3 and send a reference, for example with the SQS Extended Client Library.
7. What should the queue visibility timeout be when Lambda consumes an SQS queue?
At least six times the function timeout.
Exam codes and dates change often. Our AWS certification changes page keeps track of what is current.
The fix for Jake's sale weekend took an hour: workers now delete each message right after processing, take five messages instead of ten, and use a 6-minute visibility timeout instead of 2 hours. In-flight messages peaked at 30,000 the next Saturday, with three hundred workers, and the backlog of millions drained before lunch.
📌 If you keep one line from this page
SQS returns at most 10 messages per receive, stores an unlimited number, and allows about 120,000 in flight; most "limit" problems are really messages held in flight too long, fixed by deleting promptly and right-sizing the visibility timeout.
1 MiB per message · 14 days max retention · 12 hours max visibility · FIFO 300 calls/s per action without high throughput.
Revision note. Written October 20, 2026. The queue is rarely full; it is usually busy holding messages nobody has deleted.