-
-
Notifications
You must be signed in to change notification settings - Fork 475
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Async nunjucks filters cause template not to render #2088
Comments
I don't have a ton of time to respond but there is an async friendly for loop in Nunjucks. I don't think the standard for loop is async safe |
The async filter works for me if I use it directly: const axios = require("axios");
module.exports = (eleventyConfig) => {
eleventyConfig.addNunjucksAsyncFilter('scrape', async (uri, cb) => {
const res = await axios.get(uri);
cb(null, `${uri} [status=${res.status}/${res.statusText}]`);
});
return {
dir: {
input: "src",
output: "www"
}
};
}; ---
title: 11ty is fun
link: "https://11ty.dev/"
---
result="{{ link | scrape }}" OUTPUTresult="https://11ty.dev/ [status=200/OK]" But yeah, things get trickier when using loops and partials. |
Here's a rough example using ---
title: 11ty is fun
links:
- https://11ty.dev/
- https://github.com/11ty/eleventy/
- https://opencollective.com/11ty
- https://11ty.dev/uh-oh-404-city/
---
{% asyncEach link in links %}
result="{{ link | scrape }}"
{% endeach %} I had to tweak the async filter to handle errors: eleventyConfig.addNunjucksAsyncFilter('scrape', async (uri, cb) => {
try {
const res = await axios.get(uri);
cb(null, `${uri} [status=${res.status}/${res.statusText}]`);
} catch (err) {
cb(null, `${uri} [error=${err.message}]`);
}
}); OUTPUTresult="https://11ty.dev/ [status=200/OK]"
result="https://github.com/11ty/eleventy/ [status=200/OK]"
result="https://opencollective.com/11ty [status=200/OK]"
result="https://11ty.dev/uh-oh-404-city/ [error=Request failed with status code 404]" The error handling bit is pretty important. I think when I was returning the error directly in the async callback function ( |
Oh, and another tip is depending on what your async filter is doing, you may want to look into some caching solutions. I quite like https://www.11ty.dev/docs/plugins/cache/. I did notice that my build times did increase quite a bit using the basic |
Aha! Yep, the asyncEach did the trick! Thanks muchly. And yeah, I'm using the caching plugin in conjunction with all this. As you may have guessed from the name of the filter, I'm trying to scrape a bunch of URLs for their metadata in order to display unfurling information in my templates. |
|
Describe the bug
Async nunjucks filters cause template not to render
To Reproduce
Steps to reproduce the behavior:
I have a nunjucks filter that looks like this:
eleventyConfig.addNunjucksAsyncFilter('scrape', async (stuff, cb) => {
const data = await Promise.resolve(stuff);
cb(null, data);
});
And in a nunjucks template I have this:
{{ link | scrape }}
As you can see, the filter isn't doing anything, really - it's just returning the value passed in, but via a Promise, then awating it before calling the callback. And I know that the link variable has a value (though even if it didn't, I would still expect this to work).
The above nunjucks snippet is in a partial template which is included (via {% include %}) in a for loop inside of a larger template. The larger template renders, but the partial does not. I'm not seeing any errors emitted from the build process.
I feel like I may have a deep misunderstanding of how async filters work here. Any help is appreciated.
Expected behavior
Given that the async filter isn't doing anything special (right now at least), I'm expecting this to render without a hitch. I'm expecting to see my partial template render in the for loop.
Environment:
The text was updated successfully, but these errors were encountered: