convert is the explicit one: you say which files, which format, and what quality. For running a
whole folder through sensible defaults, use optimize instead.
Arguments
string[]
required
What to convert. Takes any mix of files, directories (expanded recursively to the image files
inside), and glob patterns — quote patterns so your shell doesn’t expand them first.
Names containing glob characters are handled literally when the file exists —
holiday (1).png
converts without any escaping.Options
string
required
Target format, or several separated by commas:
jpeg, png, webp, avif. Each input
produces one output per format.number
default:"82"
Encode quality from 1 to 100. Ignored for PNG, which is always lossless.
boolean
default:"false"
Use lossless encoding where the format supports it.
string
Directory to write results into. Defaults to writing next to each input file.
number
Scale so the longest side is at most this many pixels. Never upscales. Mutually exclusive with
--resize-percent.number
Scale to a percentage of the original dimensions. Mutually exclusive with
--resize-max.boolean
default:"false"
Keep EXIF/XMP in the output. Metadata is stripped unless you pass this.
boolean
Don’t apply EXIF orientation before encoding. By default photos are rotated upright first, so
they stay correct once the metadata is gone.
string
default:"rename"
What to do when the output name already exists:
rename, overwrite, or skip.string
Write a JSON report of the results to this path.
boolean
default:"false"
Report what would be written without writing it.
Several formats at once
Pass a comma-separated list and each input produces one output per format — useful for shipping a modern format with a fallback:Not overwriting things
By default a name collision gets a numeric suffix —photo.webp, then photo (1).webp. Your
originals are never touched.
rename (default)
rename (default)
Adds
(1), (2) and so on. Nothing is lost.overwrite
overwrite
Replaces an existing output of the same name. Useful for repeatable builds where the output
directory is disposable.
skip
skip
Leaves the existing file alone and reports the input as skipped. Good for resuming a large
batch.
Dry runs
--dry-run does the full decode and encode — so the reported sizes are real — but writes nothing:
Manifests
--manifest writes a JSON report, which is what you’d parse in CI:
results.json
files has:
string
required
The file that was read.
string
Where the result was written. Absent when the file failed.
string
required
One of
succeeded, failed, or skipped.number
required
Size of the original, in bytes.
number
Size of the result, in bytes. Absent when the file failed.
number
Fraction from 0 to 1. Positive means smaller — negative means the output grew.
string
Why the file failed. Present only on failure.