Configuration

For a repeatable setup, create a poops-images.json in your project root:

{
  "in": "src/images",
  "out": "dist/static/images",
  "sizes": [
    { "name": "thumbnail", "width": 150, "height": 150, "crop": true },
    { "name": "medium", "width": 300, "height": 300 },
    { "name": "large", "width": 1024, "height": 1024 }
  ]
}
npx poops-images

Where the config is looked for

In this order, first hit wins:

  1. An explicit path via -c
  2. poops-images.json in the working directory
  3. The images key inside poops.json
  4. The images key inside ๐Ÿ’ฉ.json

A misspelt key used to fail quietly

Most of this config fails quietly rather than loudly. A misspelt key is spread into the config and ignored โ€” skipOriginals never skips anything. A missing operation parameter is worse: { "type": "blur" } validates fine at load and throws mid-pipeline, per image, once the run is already going.

poops-images names the misspelt ones when the config loads, against the schema it ships:

[info] unknown key "quailty" โ€” ignored. Valid: $schema, in, out, sizes, format, quality, skipOriginal, include, exclude, concurrency, cache, preprocessors, verbose, configDir
[info] unknown key "widht" in sizes[0] โ€” ignored. Valid: name, width, height, crop

Key names only โ€” a wrong type is caught by the checks that already throw, and a missing operation parameter is still the pipeline's to find. The same warnings appear when Poops runs poops-images, since both go through the same config path.

Editor completion

Point $schema at the shipped JSON Schema and the editor catches all of it as you type, before the run:

{
  "$schema": "./node_modules/poops-images/schema/poops-images.schema.json",
  "in": "src/images",
  "out": "dist/static/images"
}

Or at the copy on GitHub, which needs nothing installed โ€” it tracks main, so it describes the latest release rather than the version you have pinned:

https://raw.githubusercontent.com/stamat/poops-images/main/schema/poops-images.schema.json

It covers the whole config, so it fits poops-images.json directly. Inside a poops.json the same object is the images value โ€” Poops' own schema describes that key loosely, and a local file gets you both, checked properly:

{
  "allOf": [{ "$ref": "https://stamat.info/poops/poops.schema.json" }],
  "properties": {
    "images": { "$ref": "https://raw.githubusercontent.com/stamat/poops-images/main/schema/poops-images.schema.json" }
  }
}

A test keeps the schema honest against validateConfig: everything the schema accepts, the validator accepts. It is stricter in one direction on purpose โ€” the validator ignores unknown keys, and the schema flags them, which is the entire point.

Full example

{
  "in": "src/images",
  "out": "dist/static/images",
  "sizes": [
    { "name": "thumbnail", "width": 150, "height": 150, "crop": true },
    { "name": "medium", "width": 300, "height": 300 },
    { "name": "medium_large", "width": 768, "height": 0 },
    { "name": "large", "width": 1024, "height": 1024 },
    { "name": "hero", "width": 1920, "height": 600, "crop": ["center", "top"] },
    {
      "name": "card",
      "width": 400,
      "height": 300,
      "crop": ["center", "center"]
    }
  ],
  "format": ["webp", "avif"],
  "quality": {
    "jpg": 82,
    "webp": 80,
    "avif": 60,
    "png": 90
  },
  "include": "**/*.{jpg,jpeg,png,tiff,tif,webp,heic,heif,svg,gif}",
  "exclude": [],
  "concurrency": 4,
  "skipOriginal": false,
  "cache": true,
  "preprocessors": [
    {
      "name": "lqip",
      "operations": [{ "type": "blur", "sigma": 30 }],
      "sizes": [{ "width": 32 }],
      "skipOriginal": true
    }
  ]
}

Every key

Field Type Default Description
in string "." Source directory
out string "." Output directory. May equal in: an output that would land on its own source is refused and counted as an error, suffixed variants are written
sizes array [] Size definitions. Empty = conversion-only
format false|string|array false Output format(s). false = normalize to web-ready, "smart" = smallest of jpg/webp, or explicit format(s) like "webp" or ["webp", "avif"]
quality number|object {jpg: 82, webp: 80, avif: 60, png: 90} Quality 1-100 for all formats, or per-format object
skipOriginal boolean false Skip the original (non-resized) compressed image
include string "**/*.{jpg,jpeg,png,tiff,tif,webp,heic,heif,svg,gif}" Glob pattern for source images. Governs every pipeline โ€” a narrowed include narrows SVG and GIF processing too
exclude array [] Glob patterns to exclude
concurrency number 4 Max parallel image operations
preprocessors array [] Preprocessor definitions
cache true|false|string true Cache behavior. true = default cache file in output dir, false = no cache, "path" = custom cache file path (relative to output dir or absolute)
verbose boolean false Per-file progress logs. false = only the end-of-run summary, config warnings and errors are printed (enable with CLI --verbose)