Get started Dashboard
Troubleshooting ·

AsyncEventsDropped: diagnose Lambda async event loss

Explore with AI

AsyncEventsDropped counts Lambda asynchronous events discarded without successful function execution. Events can exceed maximum age, exhaust function-error retries, or be diverted immediately when reserved concurrency is zero. Compare event age, errors and throttles, inspect the exact invocation target's configuration, and verify failure capture.

Ongoing incident? Our founding team can help you get your AWS app back up.
On this page

AsyncEventsDropped counts Lambda asynchronous events discarded without successful function execution. The official metric definition names maximum event age, exhausted retries and reserved concurrency zero as reasons. Compare event age, errors and throttles, then inspect failure capture for the exact function, version or alias the producer invokes.

A retained failure can still count as dropped. The metric describes failed original processing; the destination or DLQ tells you whether a recoverable payload survived.

Meaning: acceptance is not completion

An asynchronous Invoke uses InvocationType=Event. HTTP 202 acknowledges acceptance into Lambda’s internal queue, not the handler’s successful result. Later execution can fail, retry, wait for capacity or expire.

AsyncEventsReceived counts queued events, whereas Invocations counts function executions, including retries. Do not subtract them to estimate loss over a short interval. One event can cause several executions, queued work can cross the interval boundary, and Lambda’s eventually consistent queue can deliver duplicates even without an error.

Dropped also does not mean never attempted. A handler might complete a side effect and then fail. Check the original business ID in the downstream system before replaying; the metric alone cannot establish whether that side effect happened.

Causes: age, retries and unavailable capacity

AWS documents separate retry paths in asynchronous error handling:

  • Function errors, including timeouts: by default two retries after the initial execution, waiting one minute and then two minutes.
  • Throttling and system errors: Lambda returns the event to its queue and retries for up to six hours by default. Intervals increase from one second to a maximum of five minutes, and a large queue can further slow retries and reads.

The configuration API accepts MaximumEventAgeInSeconds from 60 to 21,600 and MaximumRetryAttempts from zero to two. Retry attempts govern function errors; they do not turn the throttling path into a two-retry policy. A short maximum age can expire an event before capacity or a dependency recovers.

Reserved concurrency zero is a special case. AWS states that new async events begin going directly to the configured DLQ or on-failure destination without retries. Restoring concurrency does not automatically replay records already sent there. Check whether zero was intentional and identify the resulting recovery backlog.

Do not invent a most-common cause from the metric name. Use errors, throttles, age and configuration changes to determine which documented path occurred for your function.

In CloudWatch → Metrics → All metrics → Lambda, select the affected function and graph AsyncEventsDropped with Sum at a one-minute period. Align the same window with these signals from the metric guide:

MetricStatisticDiagnostic question
AsyncEventsReceivedSumAre producers successfully enqueueing?
AsyncEventAgeMaximum and useful percentilesHow long did events wait before invocation?
ErrorsSumAre handlers failing or timing out?
ThrottlesSumIs execution capacity unavailable?
ConcurrentExecutionsMaximumIs concurrency reaching a configured limit?
DestinationDeliveryFailuresSumDid invocation-record delivery fail?
DeadLetterErrorsSumDid DLQ delivery fail?

AsyncEventAge is observed when Lambda invokes the function; it is not a complete inventory of every event still waiting in the queue. Rising age is useful evidence of delayed processing but not a payload-level queue inspector.

Use a precise UTC incident range for a terminal query:

export AWS_REGION=us-east-1
FUNCTION=orders-worker
aws cloudwatch get-metric-statistics --region "$AWS_REGION" \
  --namespace AWS/Lambda --metric-name AsyncEventsDropped \
  --dimensions Name=FunctionName,Value="$FUNCTION" \
  --start-time 2026-10-06T10:00:00Z --end-time 2026-10-06T11:00:00Z \
  --period 60 --statistics Sum

Replace the sample times. Sort returned datapoints by timestamp before aligning them with logs. Missing points are not proof of successful processing: confirm producer traffic, account, Region and the resource dimension being queried.

Inspect the producer’s actual target

If the producer uses orders-worker:live, inspect the alias and configuration rather than assuming $LATEST settings apply:

aws lambda get-alias --function-name "$FUNCTION" --name live
aws lambda get-function-event-invoke-config \
  --function-name "$FUNCTION" --qualifier live
aws lambda list-function-event-invoke-configs --function-name "$FUNCTION"
aws lambda get-function-concurrency --function-name "$FUNCTION"
aws lambda get-function-configuration --function-name "$FUNCTION" \
  --query '{Timeout:Timeout,DLQ:DeadLetterConfig,Role:Role}'

In the console, inspect Configuration → Asynchronous invocation and Configuration → Concurrency, with the relevant version or alias selected. Save the maximum age, retries, failure destination, DLQ, execution role and any concurrency change during the incident.

A missing explicit configuration does not mean “no retries.” Compare default behavior and all configured target settings before deciding which policy governed the call. Match the producer’s ARN to what you inspected.

Fix the cause and retain future failures

For rising Errors, read timeout and exception logs and repair the handler or its dependency. For rising Throttles and age, inspect reserved and account concurrency and other workloads consuming capacity. Raising concurrency helps only if the downstream service can absorb the resulting load. Initialization failures such as EC2ThrottledException need their own preparation/API investigation.

Increase maximum age only if delayed processing still has business value. A late report may be acceptable; a stale time-limited authorization may not be. Retain idempotency even when the immediate failure is fixed, because retries and duplicates remain part of the invocation model.

Configure failure capture before the next incident. This example targets an existing standard SQS queue; replace its ARN and grant the function execution role sqs:SendMessage on it first:

aws lambda update-function-event-invoke-config \
  --function-name "$FUNCTION" --qualifier live \
  --maximum-event-age-in-seconds 21600 \
  --maximum-retry-attempts 2 \
  --destination-config '{"OnFailure":{"Destination":"arn:aws:sqs:us-east-1:123456789012:orders-async-failures"}}'

The configuration guide recommends update for selected changes; put overwrites configuration and removes omitted settings. Re-read both failure and any existing success settings after updating. If there is no explicit configuration yet, check the API result and configure the initial policy intentionally rather than treating a missing resource response as success.

AWS supports standard SQS, standard SNS, Lambda and EventBridge destinations, plus S3 for failures only. Invocation records include request payload, response context and the failure condition. A Lambda DLQ instead carries the original event with error attributes and supports standard SQS or SNS. Destination settings can be per function, version or alias; DLQ settings are function-level.

Check permissions, encryption policies, resource existence and payload size. Unsupported FIFO destinations fail delivery. SNS’s 256 KB maximum can be exceeded by a large async payload plus record metadata. Alarm on delivery-failure metrics separately: a configured target ARN does not guarantee successful retention.

Verify capture and replay without duplicating effects

Use a test alias or disposable function to exercise a known failure. Confirm that the record reached the destination, inspect its failure condition and original payload, and check delivery-failure metrics. Then send a known successful event through the repaired path and verify its business result.

Replay only retained operations that still need completion. A destination wraps the original input in requestPayload; sending the entire record changes the handler’s input schema. A DLQ body has a different shape. Extract the intended payload, retain the original idempotency key and rate-limit replay so it does not recreate the backlog.

Without successful capture, the metric cannot reconstruct the event. Check an upstream retained source or audit trail for replay options instead of promising recovery from CloudWatch counts. Restoring capacity is not the same as completing all discarded work.

SQS-triggered Lambda uses polling and synchronous batch invocation. Its recovery policy belongs on the source queue. Follow ChangeMessageVisibility for visibility and Lambda mapping settings rather than applying this async-queue policy to SQS messages.

Prevention

Alert on dropped events where every accepted event matters, and earlier on event age relative to your processing deadline. Group age, errors and throttles into one incident with the likely cause and impact. Monitor failure-target backlog and age too: captured work that nobody reprocesses is still unfinished.

Polylane’s AWS integration connects it to AWS, so it can see when a function starts dropping events and work out why. The AWS overview has more. Retention, idempotency and replay still need to be configured in AWS and the application.

Running on AWS? See how Polylane monitors AWS in production.

Common questions.

Does AsyncEventsDropped mean the function never ran?

Not necessarily. An event can be discarded after function-error retries were exhausted, so the handler may have run and failed several times. Others expire before execution or are diverted with reserved concurrency zero.

Does a DLQ keep AsyncEventsDropped at zero?

No. Capturing a failed event does not make original processing successful. Check the failure target and DeadLetterErrors or DestinationDeliveryFailures as well as dropped-event counts.

Does MaximumRetryAttempts control throttling retries?

It controls function-error retries, from zero to two. Throttling and system errors follow the queue retry path and are bounded by maximum event age, rather than the same two-retry limit.

Does this metric describe SQS-triggered Lambda processing?

No. SQS event source mappings poll the queue and invoke synchronous batches. Inspect the SQS visibility timeout, redrive policy and mapping instead of Lambda's internal asynchronous queue.

Can CloudWatch recover the dropped payload?

No. The metric is a count, not event storage. Recover from a successfully delivered failure destination, a DLQ or an upstream replay source. Without retained payloads the count cannot reconstruct an event.

Sources (6)

  1. Lambda metric definitions
  2. Asynchronous errors and retries
  3. Retaining asynchronous invocation records
  4. Asynchronous configuration API
  5. Configuring asynchronous error handling
  6. Polylane AWS integration

About the author

Boris Tane

Founder of Polylane

Boris Tane is the founder of Polylane. He previously founded Baselime, observability for the future of the cloud, which Cloudflare acquired. At Cloudflare he built and led the Workers observability team.

Related

Nobody should be on-call. Polylane watches your infra, finds what broke, and writes the fix.

Get started for free