RequestEntityTooLargeException: Request must be smaller than 6291456 bytes for the InvokeFunction operation

Short answer

The request or response exceeded Lambda's payload limit: 6 MB synchronous, 256 KB asynchronous. These are hard service limits — they cannot be raised by a quota increase, so the fix is always to move the data rather than to ask for more room.

What it means

Lambda caps how much data can cross the invocation boundary in either direction, and the two limits are far apart. A synchronous invocation may carry 6 MB in and 6 MB out. An asynchronous one may carry 256 KB. Both are hard service limits: they are not adjustable quotas, and no support request will move them.

The gap between the two is where most surprises live. The same payload that works perfectly through a synchronous call fails immediately when the same function is invoked from EventBridge, SNS, or with InvocationType=Event — a twenty-fourfold reduction in headroom that arrives with a change that looks purely architectural. Moving a call from synchronous to asynchronous is normally a scaling improvement, and this is the one way it can silently break.

Direction is worth reading carefully, because it changes where to look. A request that is too large never reaches your function: there is no START line, no logging of yours, nothing in the log group for that attempt at all, and the error surfaces at whatever tried to invoke you. A response that is too large means the handler ran to completion — the query ran, the rows were assembled, the work was paid for — and only then was the result rejected. That second shape is particularly frustrating because the invocation shows every sign of success right up until it fails.

The limits also have a habit of being reached long after the code is written. An endpoint returning every order for a customer is comfortable at a hundred orders and fine at a thousand. Somewhere past that it crosses six megabytes, and the failure lands on the largest, most valuable customers first. That is why pagination or a claim-check pointer is the durable answer rather than trimming fields to buy headroom — the size of the response should not depend on how much data exists behind it.

Depends

CloudWatch’s Errors metric: Whether CloudWatch’s Errors metric counts this depends on whether the error escaped your handler, which the log line alone does not settle. Counted when the error escapes the handler — which is the usual case on the response side, since the runtime cannot deliver an oversized return value. LogStitch classified the example below from its log level rather than an extracted error type.

What it looks like in CloudWatch

This is the shape the failure arrives in: the lines of one invocation scattered among everything else the log group received at the same moment.

CloudWatch Logs Before

6 raw lines, in the order CloudWatch delivered them.

2026-08-30T17:12:08.114Z START RequestId: 7a4c1e93-0b25-4f68-8d31-9e6b2a5c7f04 Version: $LATEST
2026-08-30T17:12:08.118Z 7a4c1e93-0b25-4f68-8d31-9e6b2a5c7f04 INFO Export requested range=2026-07-01..2026-07-31
2026-08-30T17:12:10.244Z 7a4c1e93-0b25-4f68-8d31-9e6b2a5c7f04 INFO Assembled 41882 rows
2026-08-30T17:12:10.402Z 7a4c1e93-0b25-4f68-8d31-9e6b2a5c7f04 ERROR RequestEntityTooLargeException: Request must be smaller than 6291456 bytes for the InvokeFunction operation
2026-08-30T17:12:10.588Z END RequestId: 7a4c1e93-0b25-4f68-8d31-9e6b2a5c7f04
2026-08-30T17:12:10.588Z REPORT RequestId: 7a4c1e93-0b25-4f68-8d31-9e6b2a5c7f04 Duration: 2474.11 ms Billed Duration: 2475 ms Memory Size: 1024 MB Max Memory Used: 412 MB Status: error

LogStitch After

The same lines, grouped into the invocation they belong to.

Error7a4c1e93-0b25-4f68-8d31-9e6b2a5c7f04dur 2.47sbilled 2.48smem 412/1024MBlogs 6
  1. 17:12:08.114PLAT
    START RequestId: 7a4c1e93-0b25-4f68-8d31-9e6b2a5c7f04 Version: $LATEST
  2. 17:12:08.118INFO
    INFO	Export requested range=2026-07-01..2026-07-31
  3. 17:12:10.244INFO
    INFO	Assembled 41882 rows
  4. 17:12:10.402ERROR
    ERROR	RequestEntityTooLargeException: Request must be smaller than 6291456 bytes for the InvokeFunction operation
  5. 17:12:10.588PLAT
    END RequestId: 7a4c1e93-0b25-4f68-8d31-9e6b2a5c7f04
  6. 17:12:10.588PLAT
    REPORT RequestId: 7a4c1e93-0b25-4f68-8d31-9e6b2a5c7f04	Duration: 2474.11 ms	Billed Duration: 2475 ms	Memory Size: 1024 MB	Max Memory Used: 412 MB	Status: error
Error
Status
2.47s
Duration
2.48s
Billed
412/1024MB
Memory
60%
Headroom
No
Cold start
LogLevelError
Error type

The panel on the right is generated by running the excerpt on the left through the same parser that powers the free web stitcher — it is what the tool actually produces for this input, not an illustration of it.

How to confirm it from the logs

The byte count in the message tells you which limit you hit. 6291456 is 6 MiB, the synchronous invocation limit, and it applies to the request going in and the response coming back. 262144 is 256 KiB, the asynchronous limit, which is far smaller and catches people who moved a working synchronous call to an event-driven one.

Direction matters and the wording distinguishes it. A message about the request means the event was too big to deliver and your code never ran, so there will be no START line for it at all. A message about the response payload means your handler ran, did the work, and the return value could not be delivered — which appears after all of your own logging.

Causes, most likely first

1

The response contains a whole result set

How to confirm

Check what the handler returns on the failing path. An unpaginated query, a full export, or a list endpoint with no limit grows with the data behind it and eventually crosses 6 MB — a threshold that arrives suddenly, long after the code was written.

2

A file is being passed through the function

How to confirm

Look for base64 in the payload. Encoding inflates binary data by about a third, so a 5 MB file becomes roughly 6.7 MB in the event and exceeds the limit before anything processes it.

3

The invocation is asynchronous and the limit is 256 KB, not 6 MB

How to confirm

Check the invocation type. An event-source mapping, an EventBridge rule, an SNS subscription or an InvocationType=Event call all use the asynchronous path, whose limit is roughly twenty-four times smaller. A payload that worked when invoked synchronously fails immediately when the same call is made asynchronously.

4

The function is passing full payloads between steps

How to confirm

Look at whether one function invokes another with the accumulated data. Chained functions that hand entire result sets along accumulate size at every hop, and the limit is reached somewhere in the middle of a pipeline rather than at either end.

Fixes

Fix 1

Pass a pointer, not the payload

Write the data to S3 and pass the key. This is the standard pattern for anything that can grow — often called the claim-check pattern — and it removes the size ceiling from the request path entirely.

js// Instead of returning the whole export in the response:
const key = `exports/${crypto.randomUUID()}.json`;
await s3.send(new PutObjectCommand({
  Bucket: process.env.EXPORT_BUCKET,
  Key: key,
  Body: JSON.stringify(rows)
}));

return {
  statusCode: 200,
  body: JSON.stringify({
    key,
    url: await getSignedUrl(s3, new GetObjectCommand({
      Bucket: process.env.EXPORT_BUCKET, Key: key
    }), { expiresIn: 900 }),
    count: rows.length
  })
};
Fix 2

Paginate rather than returning everything

A limit and a cursor keep the response bounded regardless of how much data exists behind it, and they stop the endpoint from getting slower and larger as the table grows.

jsconst PAGE = 100;

const result = await doc.send(new QueryCommand({
  TableName: "orders",
  KeyConditionExpression: "customerId = :c",
  ExpressionAttributeValues: { ":c": customerId },
  Limit: PAGE,
  ExclusiveStartKey: event.queryStringParameters?.cursor
    ? JSON.parse(Buffer.from(event.queryStringParameters.cursor, "base64").toString())
    : undefined
}));

return {
  items: result.Items,
  cursor: result.LastEvaluatedKey
    ? Buffer.from(JSON.stringify(result.LastEvaluatedKey)).toString("base64")
    : null
};
Fix 3

Stream the response instead of buffering it

A response-streaming function writes to the client as it goes rather than assembling a single return value, which lifts the response ceiling well beyond 6 MB. It applies to Function URLs and direct invocations, not to every integration, so check the caller supports it.

jsexport const handler = awslambda.streamifyResponse(
  async (event, responseStream) => {
    for await (const chunk of rows()) {
      responseStream.write(JSON.stringify(chunk) + "\n");
    }
    responseStream.end();
  }
);
Fix 4

Upload directly to S3 rather than through the function

For file uploads, a presigned URL lets the client send the object straight to S3. The function issues the URL and never touches the bytes, so the payload limit stops being relevant at all.

Also seen as

The same underlying failure, worded differently by a different runtime, SDK version, or logging layer. All of these land here — there is no separate page for each phrasing.

Request must be smaller than 6291456 bytes for the InvokeFunction operationRequestEntityTooLargeException: Request must be smaller than 5120 bytes for the UpdateFunctionConfiguration operationAn error occurred (RequestEntityTooLargeException) when calling the UpdateFunctionCode operationlambda 5120 bytes updatefunctionconfigurationbody size is too longResponse payload size exceeded maximum allowed payload size (6291556 bytes)lambda 6mb payload limitlambda payload too large

Errors that show up alongside this one, or that people mistake for it.

References

LogStitch finds this automatically, across every invocation in your account.

Paste a log excerpt into the free web stitcher and see it grouped, classified, and measured in your browser — nothing is uploaded. Or run the Mac app against your own AWS profiles and get the same view over every function you own.