Skip to content

Commit

Permalink
Fixes #188 #3345
Browse files Browse the repository at this point in the history
  • Loading branch information
zachleat committed Jul 11, 2024
1 parent 47a3252 commit f19ef55
Show file tree
Hide file tree
Showing 4 changed files with 109 additions and 1 deletion.
71 changes: 70 additions & 1 deletion src/Template.js
Original file line number Diff line number Diff line change
Expand Up @@ -637,8 +637,77 @@ class Template extends TemplateContent {
});
}

static async runPreprocessors(inputPath, content, data, preprocessors) {
let skippedVia = false;
for (let [name, preprocessor] of Object.entries(preprocessors)) {
let { filter, callback } = preprocessor;

let filters;
if (Array.isArray(filter)) {
filters = filter;
} else if (typeof filter === "string") {
filters = filter.split(",");
} else {
throw new Error(
`Expected file extensions passed to "${name}" content preprocessor to be a string or array. Received: ${filter}`,
);
}

if (!filters.some((extension) => extension === "*" || inputPath.endsWith(extension))) {
// skip
continue;
}

try {
let ret = await callback.call(
{
inputPath,
},
data,
content,
);

// Returning explicit false is the same as ignoring the template
if (ret === false) {
skippedVia = name;
continue;
}

// Different from transforms: returning falsy (not false) here does nothing (skips the preprocessor)
if (ret) {
content = ret;
}
} catch (e) {
throw new EleventyBaseError(
`Preprocessor \`${name}\` encountered an error when transforming ${inputPath}.`,
e,
);
}
}

return {
skippedVia,
content,
};
}

async getTemplates(data) {
let rawInput = await this.getPreRender();
let content = await this.getPreRender();
let { skippedVia, content: rawInput } = await Template.runPreprocessors(
this.inputPath,
content,
data,
this.config.preprocessors,
);

if (skippedVia) {
debug(
"Skipping %o, the %o preprocessor returned an explicit `false`",
this.inputPath,
skippedVia,
);
return [];
}

// https://github.com/11ty/eleventy/issues/1206
data.page.rawInput = rawInput;
Expand Down
2 changes: 2 additions & 0 deletions src/TemplateConfig.js
Original file line number Diff line number Diff line change
Expand Up @@ -333,6 +333,8 @@ class TemplateConfig {
}

this.userConfig.activeNamespace = storedActiveNamespace;

this.userConfig._disablePluginExecution();
}

/**
Expand Down
17 changes: 17 additions & 0 deletions src/UserConfig.js
Original file line number Diff line number Diff line change
Expand Up @@ -102,6 +102,8 @@ class UserConfig {

this.linters = {};
this.transforms = {};
this.preprocessors = {};

this.activeNamespace = "";
this.DateTime = DateTime;
this.dynamicPermalinks = true;
Expand Down Expand Up @@ -544,6 +546,11 @@ class UserConfig {
this.#pluginExecution = true;
}

// Internal method
_disablePluginExecution() {
this.#pluginExecution = false;
}

/* Config is executed in two stages and plugins are the second stage—are we in the plugins stage? */
isPluginExecution() {
return this.#pluginExecution;
Expand Down Expand Up @@ -999,6 +1006,15 @@ class UserConfig {
this.transforms[name] = this.#decorateCallback(`"${name}" Transform`, callback);
}

addPreprocessor(name, fileExtensions, callback) {
name = this.getNamespacedName(name);

this.preprocessors[name] = {
filter: fileExtensions,
callback: this.#decorateCallback(`"${name}" Preprocessor`, callback),
};
}

addLinter(name, callback) {
name = this.getNamespacedName(name);

Expand Down Expand Up @@ -1055,6 +1071,7 @@ class UserConfig {
// filters removed in 1.0 (use addTransform instead)
transforms: this.transforms,
linters: this.linters,
preprocessors: this.preprocessors,
globalData: this.globalData,
layoutAliases: this.layoutAliases,
layoutResolution: this.layoutResolution,
Expand Down
20 changes: 20 additions & 0 deletions test/EleventyTest.js
Original file line number Diff line number Diff line change
Expand Up @@ -1527,3 +1527,23 @@ test("#1419: Shortcode in a permalink", async (t) => {
t.is(results.length, 1);
t.is(results[0].url, `/url-slug/`);
});

test("#188: Content preprocessing", async (t) => {
let elev = new Eleventy("./test/stubs-virtual/", undefined, {
config: eleventyConfig => {
eleventyConfig.addPreprocessor("drafts", ".njk", (data, content) => {
if(data.draft) {
return false;
}
return `Hello ${content}`;
});

eleventyConfig.addTemplate("index.njk", "Before");
eleventyConfig.addTemplate("draft.njk", "Before", { draft: true });
}
});

let results = await elev.toJSON();
t.is(results.length, 1);
t.is(results[0].content, `Hello Before`);
});

0 comments on commit f19ef55

Please sign in to comment.