Skip to navigation Skip to main content
Eleventy
Eleventy Documentation
Stable
3.0.0
Canary
3.0.1-alpha.1
Toggle Menu
Eleventy 1.93s
Astro 22.90s

Image (as Data Files)

Contents
Eleventy Image Usage Types
  • Image HTML Transform: Recommended—start with this one! It’s the easiest to configure and is compatible with all template syntax.
WARNING:
This is a nontraditional use case—you probably don’t want to use it, but you can!

Head back to the Image HTML Transform docs for the recommended way to optimize images.

Added in v2.0.0 Eleventy’s Custom Data File Formats features an example of processing Images as data files to feed EXIF data into the Data Cascade. You can use the same feature to add the metadata stats returned from the Image utility directly to the Data Cascade for use in your templates.

  • Benefits:
    • Processing happens in the data cascade so this works in any template language.
    • Images stored in the global data folder will be processed and available to all templates
  • Drawbacks:
    • You can’t customize the Image options (e.g. widths or formats) from the template code. It is set globally in the config.
  • Both a benefit and a drawback:

Configuration

eleventy.config.js
import path from "node:path";
import Image from "@11ty/eleventy-img";

export default function (eleventyConfig) {
eleventyConfig.addDataExtension("png,jpeg", {
read: false, // Don’t read the input file, argument is now a file path
parser: async (imagePath) => {
let stats = await Image(imagePath, {
widths: ["auto"],
formats: ["avif", "webp", "jpeg"],
outputDir: path.join(eleventyConfig.dir.output, "img", "built"),
});

return {
image: {
stats,
},
};
},
});

// This works sync or async: images were processed ahead of time in the data cascade
eleventyConfig.addShortcode("dataCascadeImage", (stats, alt, sizes) => {
let imageAttributes = {
alt,
sizes,
loading: "lazy",
decoding: "async",
};
return Image.generateHTML(stats, imageAttributes);
});
};
const path = require("node:path");
const Image = require("@11ty/eleventy-img");

module.exports = function (eleventyConfig) {
eleventyConfig.addDataExtension("png,jpeg", {
read: false, // Don’t read the input file, argument is now a file path
parser: async (imagePath) => {
let stats = await Image(imagePath, {
widths: ["auto"],
formats: ["avif", "webp", "jpeg"],
outputDir: path.join(eleventyConfig.dir.output, "img", "built"),
});

return {
image: {
stats,
},
};
},
});

// This works sync or async: images were processed ahead of time in the data cascade
eleventyConfig.addShortcode("dataCascadeImage", (stats, alt, sizes) => {
let imageAttributes = {
alt,
sizes,
loading: "lazy",
decoding: "async",
};
return Image.generateHTML(stats, imageAttributes);
});
};

With a template my-blog-post.md and an image file my-blog-post.jpeg, you could use the above configuration code in your template like this:

Filename my-blog-post.md
{% dataCascadeImage image.stats, "My alt text" %}

Note this also means that folder/folder.jpeg would be processed for all templates in folder/* and any images stored in your global _data would also be populated into the data cascade based on their folder structure.