Skip to content

createImageSizes decodes the source once per image size, all at once, so one upload can take hundreds of MB #18531

Open

Description

@saadshahd

Describe the Bug

createImageSizes builds every configured image size at once (Promise.all over imageSizes). Each size pipeline decodes the whole source image, so one upload holds one full decoded copy per size at the same time. Peak memory is roughly sizes x width x height x channels.

A small file can therefore take hundreds of MB. A flat 7000x7000 PNG of ~320 KB with four imageSizes grows the process by ~600 MB. In a memory-limited container that is enough for the kernel to kill the process, and since the client retries, each retry takes down the next replica.

Measured on 3.90.1 (sharp 0.34.3), one payload.create on a collection with WebP imageSizes, peak RSS growth:

imageSizes growth
0 4 MB
1 138 MB
4 591 MB
4, sizes built one after another 162 MB

The code is unchanged in 3.90.2: packages/payload/src/uploads/image-resizing/createImageSizes.ts.

Link to the code that reproduces this issue

Not a public repo. Minimal config below.

Reproduction Steps

  1. Collection with upload.imageSizes of four WebP sizes, for example widths 1600, 1240, 960 and 690, with withoutEnlargement: true.
  2. Pass sharp in the config.
  3. Upload a 7000x7000 PNG with a flat background (a few hundred KB).
  4. Watch process RSS during the create: it grows by about four decoded copies of the image.

Building the sizes in sequence (for ... of in place of Promise.all(imageSizes.map(...)), with continue for the omit branch) brings the peak down to about one decoded copy.

Which area(s) are affected?

area: core, Uploads

Environment Info

payload: 3.90.1
sharp: 0.34.3
node: 24
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions