or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

docs

build-pipeline.mdconfiguration-api.mddata-system.mddevelopment-tools.mdindex.mdplugin-system.mdprogrammatic-api.mdtemplate-processing.md
tile.json

plugin-system.mddocs/

Plugin System

Extensible plugin architecture with built-in plugins and support for community plugins, providing a comprehensive system for extending Eleventy's functionality through reusable configuration packages.

Capabilities

Plugin Management

Add, configure, and manage Eleventy plugins.

/**
 * Add plugin to Eleventy configuration
 * @param plugin - Plugin function or object
 * @param options - Plugin configuration options
 */
addPlugin(plugin: PluginDefinition, options?: any): void;

/**
 * Resolve built-in plugin by name
 * @param name - Plugin package name
 * @returns Plugin function or Promise<Plugin>
 */
resolvePlugin(name: string): Function | Promise<Function>;

/**
 * Check if plugin is already added
 * @param plugin - Plugin name or definition
 * @returns Whether plugin is registered
 */
hasPlugin(plugin: string | PluginDefinition): boolean;

/**
 * Execute code within a plugin namespace to avoid naming conflicts
 * @param pluginNamespace - Namespace for plugin
 * @param callback - Function to execute in namespace
 */
namespace(pluginNamespace: string, callback: (eleventyConfig: UserConfig) => void): Promise<void>;

interface PluginDefinition {
  /** Plugin configuration function */
  configFunction?: (eleventyConfig: UserConfig, options?: any) => void | Promise<void>;
  
  /** Plugin package name for identification */
  eleventyPackage?: string;
  
  /** Plugin-specific options */
  eleventyPluginOptions?: {
    /** Only add plugin once (prevents duplicates) */
    unique?: boolean;
  };
}

Built-in Plugin Resolution Names:

  • @11ty/eleventy/render-plugin
  • @11ty/eleventy/i18n-plugin
  • @11ty/eleventy/html-base-plugin
  • @11ty/eleventy/inputpath-to-url-plugin

Usage Examples:

// Add built-in plugins
eleventyConfig.addPlugin(require("@11ty/eleventy").RenderPlugin, {
  tagName: "renderTemplate",
  filterName: "renderContent"
});

// Add community plugins
eleventyConfig.addPlugin(require("@11ty/eleventy-plugin-syntaxhighlight"), {
  theme: "okaidia"
});

// Resolve plugins dynamically
const i18nPlugin = await eleventyConfig.resolvePlugin("@11ty/eleventy/i18n-plugin");
eleventyConfig.addPlugin(i18nPlugin, {
  defaultLanguage: "en"
});

// Plugin with namespace
await eleventyConfig.namespace("myPlugin", (eleventyConfig) => {
  eleventyConfig.addFilter("myFilter", (content) => content.toUpperCase());
  eleventyConfig.addShortcode("myShortcode", () => "Hello from my plugin!");
});

// Check if plugin exists
if (!eleventyConfig.hasPlugin("@11ty/eleventy-plugin-rss")) {
  eleventyConfig.addPlugin(require("@11ty/eleventy-plugin-rss"));
}

RenderPlugin

Built-in plugin providing template rendering utilities and shortcodes.

/**
 * RenderPlugin configuration
 * @param eleventyConfig - Eleventy configuration instance
 * @param options - Plugin options
 */
function RenderPlugin(eleventyConfig: UserConfig, options?: RenderPluginOptions): void;

interface RenderPluginOptions {
  /** Template tag name for rendering templates */
  tagName?: string; // default: "renderTemplate"
  
  /** File template tag name for rendering files */
  tagNameFile?: string; // default: "renderFile"
  
  /** Filter name for rendering content */
  filterName?: string; // default: "renderContent"
  
  /** Template config instance */
  templateConfig?: TemplateConfig;
  
  /** Access global data in renders */
  accessGlobalData?: boolean; // default: false
}

/** RenderManager class for programmatic rendering */
class RenderManager {
  constructor();
  
  /** Get/set template configuration */
  get templateConfig(): TemplateConfig;
  set templateConfig(templateConfig: TemplateConfig): void;
  
  /** Initialize render manager */
  init(): Promise<boolean>;
  
  /** Configure render manager */
  config(callback: (eleventyConfig: UserConfig) => void): any;
  
  /** Get initial global data */
  get initialGlobalData(): any;
  
  /** Get data for rendering */
  getData(...data: any[]): Promise<object>;
  
  /** Compile template content */
  compile(content: string, templateLang: string, options?: any): Promise<Function>;
  
  /** Render compiled template */
  render(fn: Function, edgeData?: any, buildTimeData?: any): Promise<any>;
}

/** Named exports from RenderPlugin */
const compileFile: Function; // exported as "File"
const compile: Function;     // exported as "String"

Usage Examples:

// Add RenderPlugin with custom options
eleventyConfig.addPlugin(RenderPlugin, {
  tagName: "render",
  filterName: "renderString",
  accessGlobalData: true
});

// Using render shortcodes in templates
// {% render "partial.njk", { title: "Hello" } %}
// {% renderFile "includes/header.html" %}

// Using render filter
// {{ "# Hello World" | renderContent: "md" }}

// Programmatic usage
const { RenderManager } = require("@11ty/eleventy");
const renderManager = new RenderManager();
await renderManager.init();

const compiled = await renderManager.compile("Hello {{ name }}", "liquid");
const result = await renderManager.render(compiled, { name: "World" });

I18nPlugin

Built-in plugin for internationalization support with URL and content helpers.

/**
 * I18nPlugin configuration
 * @param eleventyConfig - Eleventy configuration instance
 * @param options - Plugin options
 */
function I18nPlugin(eleventyConfig: UserConfig, options: I18nPluginOptions): void;

interface I18nPluginOptions {
  /** Default language code (required) */
  defaultLanguage: string;
  
  /** Filter names configuration */
  filters?: {
    /** URL filter name */
    url?: string; // default: "locale_url"
    
    /** Links filter name */
    links?: string; // default: "locale_links"
  };
  
  /** Error handling mode */
  errorMode?: 'strict' | 'allow-fallback' | 'never'; // default: "strict"
}

/** Language utilities class */
class LangUtils {
  /** Extract language code from input path */
  static getLanguageCodeFromInputPath(filepath: string): string;
  
  /** Extract language code from URL */
  static getLanguageCodeFromUrl(url: string): string;
  
  /** Swap language code in string without validation */
  static swapLanguageCodeNoCheck(str: string, langCode: string): string;
  
  /** Swap language code in string with validation */
  static swapLanguageCode(str: string, langCode: string): string;
}

/** Language comparator utilities */
class Comparator {
  /** Check if string is a valid language code */
  static isLangCode(code: string): boolean;
  
  /** Check if URL contains specific language code */
  static urlHasLangCode(url: string, code: string): boolean;
}

Usage Examples:

// Add I18nPlugin
eleventyConfig.addPlugin(I18nPlugin, {
  defaultLanguage: "en",
  filters: {
    url: "locale_url",
    links: "locale_links"
  },
  errorMode: "strict"
});

// Using in templates
// {{ "/about/" | locale_url: "fr" }} → "/fr/about/"
// {{ collections.all | locale_links: "es" }} → filtered collection

// File structure example:
// src/en/index.md
// src/fr/index.md  
// src/es/index.md

// LangUtils usage
const { LangUtils } = require("@11ty/eleventy");
const lang = LangUtils.getLanguageCodeFromInputPath("./src/fr/about.md"); // "fr"
const swapped = LangUtils.swapLanguageCode("/en/about/", "fr"); // "/fr/about/"

HtmlBasePlugin

Built-in plugin for applying base href to relative URLs in HTML output.

/**
 * HtmlBasePlugin configuration
 * @param eleventyConfig - Eleventy configuration instance
 * @param options - Plugin options
 */
function HtmlBasePlugin(eleventyConfig: UserConfig, options?: HtmlBasePluginOptions): void;

interface HtmlBasePluginOptions {
  /** Base href URL (defaults to eleventyConfig.pathPrefix) */
  baseHref?: string;
  
  /** File extensions to process */
  extensions?: string; // default: "html"
}

/**
 * Transform URL utility function
 * @param url - URL to transform
 * @param base - Base URL to apply
 * @returns Transformed URL
 */
function transformUrl(url: string, base: string): string; // exported as "applyBaseToUrl"

Usage Examples:

// Add HtmlBasePlugin
eleventyConfig.addPlugin(HtmlBasePlugin, {
  baseHref: "/my-site/",
  extensions: "html"
});

// Or use pathPrefix automatically
eleventyConfig.setPathPrefix("/my-site/");
eleventyConfig.addPlugin(HtmlBasePlugin); // Uses pathPrefix

// Transform utility usage
const { transformUrl } = require("@11ty/eleventy");
const transformed = transformUrl("/about/", "/my-site/"); // "/my-site/about/"

// Transforms relative URLs in HTML:
// <a href="/about/">About</a> → <a href="/my-site/about/">About</a>
// <img src="/images/logo.png"> → <img src="/my-site/images/logo.png">

InputPathToUrl Plugins

Built-in plugins for transforming input paths to URLs.

/**
 * Transform version - processes HTML output
 * @param eleventyConfig - Eleventy configuration instance
 * @param options - Plugin options
 */
function TransformPlugin(eleventyConfig: UserConfig, options?: InputPathToUrlOptions): void;

/**
 * Filter version - provides template filter
 * @param eleventyConfig - Eleventy configuration instance
 * @param options - Plugin options
 */
function FilterPlugin(eleventyConfig: UserConfig, options?: InputPathToUrlOptions): void;

interface InputPathToUrlOptions {
  /** File extensions to process */
  extensions?: string; // default: "html"
}

Usage Examples:

// Add transform version (processes all HTML)
eleventyConfig.addPlugin(TransformPlugin, {
  extensions: "html"
});

// Add filter version (use in templates)
eleventyConfig.addPlugin(FilterPlugin);

// Using the filter in templates
// {{ "/src/posts/my-post.md" | inputPathToUrl }}
// Converts input paths to their corresponding URLs

IdAttributePlugin

Built-in plugin for automatically adding id attributes to headings.

/**
 * IdAttributePlugin configuration
 * @param eleventyConfig - Eleventy configuration instance
 * @param options - Plugin options
 */
function IdAttributePlugin(eleventyConfig: UserConfig, options?: IdAttributePluginOptions): void;

interface IdAttributePluginOptions {
  /** Custom slugify function */
  slugify?: (text: string) => string;
  
  /** CSS selector for elements to process */
  selector?: string; // default: "[id],h1,h2,h3,h4,h5,h6"
  
  /** Decode HTML entities in text */
  decodeEntities?: boolean; // default: true
  
  /** Check for duplicate IDs */
  checkDuplicates?: 'error' | boolean; // default: "error"
  
  /** Filter function for selective processing */
  filter?: (element: any) => boolean;
}

Usage Examples:

// Add IdAttributePlugin with custom options
eleventyConfig.addPlugin(IdAttributePlugin, {
  slugify: (text) => text.toLowerCase().replace(/[^a-z0-9]/g, '-'),
  selector: "h1,h2,h3,h4,h5,h6",
  checkDuplicates: "error",
  filter: (element) => !element.hasAttribute("data-no-id")
});

// Automatically converts:
// <h1>Hello World</h1> → <h1 id="hello-world">Hello World</h1>
// <h2 id="custom">Custom</h2> → <h2 id="custom">Custom</h2> (preserves existing)

BundlePlugin

Re-exported plugin from @11ty/eleventy-plugin-bundle for asset bundling.

/**
 * BundlePlugin for CSS/JS bundling and inlining
 * Re-exported from @11ty/eleventy-plugin-bundle
 */
const BundlePlugin: PluginDefinition;

Usage Examples:

// Add BundlePlugin
eleventyConfig.addPlugin(BundlePlugin);

// Using bundle shortcodes in templates
// {% css %}
// body { margin: 0; }
// {% endcss %}

// {% js %}
// console.log("Hello!");
// {% endjs %}

// {% getBundle "css" %} - outputs bundled CSS
// {% getBundle "js" %} - outputs bundled JavaScript

Custom Plugin Development

Create custom plugins for Eleventy.

/**
 * Custom plugin function signature
 * @param eleventyConfig - Eleventy configuration instance
 * @param options - Plugin options passed by user
 */
type PluginFunction = (eleventyConfig: UserConfig, options?: any) => void | Promise<void>;

/**
 * Plugin object format
 */
interface PluginObject {
  /** Plugin configuration function */
  configFunction: PluginFunction;
  
  /** Plugin package name for identification */
  eleventyPackage?: string;
  
  /** Initialization arguments */
  initArguments?: any;
  
  /** Plugin options */
  eleventyPluginOptions?: {
    /** Prevent duplicate plugin registration */
    unique?: boolean;
  };
}

Custom Plugin Examples:

// Simple plugin function
function myCustomPlugin(eleventyConfig, options = {}) {
  const { prefix = "my" } = options;
  
  // Add filters
  eleventyConfig.addFilter(`${prefix}Filter`, (content) => {
    return content.toUpperCase();
  });
  
  // Add shortcodes
  eleventyConfig.addShortcode(`${prefix}Shortcode`, (text) => {
    return `<span class="${prefix}-text">${text}</span>`;
  });
  
  // Add transforms
  eleventyConfig.addTransform(`${prefix}Transform`, (content, outputPath) => {
    if (outputPath && outputPath.endsWith(".html")) {
      return content.replace(/\bTODO\b/g, '<mark>TODO</mark>');
    }
    return content;
  });
}

// Plugin object format
const myPluginObject = {
  eleventyPackage: "my-custom-plugin",
  eleventyPluginOptions: {
    unique: true
  },
  configFunction: (eleventyConfig, options) => {
    // Plugin configuration
  }
};

// Async plugin
async function myAsyncPlugin(eleventyConfig, options) {
  const data = await fetch("https://api.example.com/config");
  const config = await data.json();
  
  eleventyConfig.addGlobalData("apiConfig", config);
}

// Usage
eleventyConfig.addPlugin(myCustomPlugin, { prefix: "awesome" });
eleventyConfig.addPlugin(myPluginObject);
eleventyConfig.addPlugin(myAsyncPlugin);

Types

interface PluginDefinition {
  configFunction?: (eleventyConfig: UserConfig, options?: any) => void | Promise<void>;
  eleventyPackage?: string;
  eleventyPluginOptions?: {
    unique?: boolean;
  };
}

interface RenderPluginOptions {
  tagName?: string;
  tagNameFile?: string;
  filterName?: string;
  templateConfig?: TemplateConfig;
  accessGlobalData?: boolean;
}

interface I18nPluginOptions {
  defaultLanguage: string;
  filters?: {
    url?: string;
    links?: string;
  };
  errorMode?: 'strict' | 'allow-fallback' | 'never';
}

interface HtmlBasePluginOptions {
  baseHref?: string;
  extensions?: string;
}

interface InputPathToUrlOptions {
  extensions?: string;
}

interface IdAttributePluginOptions {
  slugify?: (text: string) => string;
  selector?: string;
  decodeEntities?: boolean;
  checkDuplicates?: 'error' | boolean;
  filter?: (element: any) => boolean;
}

type PluginFunction = (eleventyConfig: UserConfig, options?: any) => void | Promise<void>;

interface PluginObject {
  configFunction: PluginFunction;
  eleventyPackage?: string;
  initArguments?: any;
  eleventyPluginOptions?: {
    unique?: boolean;
  };
}