How can I exclude drafts from showing up in collections? Liquid/Eleventy

Viewed 321

I'm building a website with Eleventy for the first time, and even though I have worked with Liquid for a while now, I just can't crack this one.

I want to simplify the architecture as much as possible. This is why I have assigned my collections to variables:

{% assign blogposts = collections.posts %}

so later on in the site I can just write a really short and sweet:

{% for post in blogposts %}...{% endfor %} 

instead of assigning the collections just above it in a file.

Now here's my problem:

I would love to filter away posts marked as draft (using draft: true in the frontmatter). I thought I'd be able to do it like one of these (I've tried...)

{% assign blogposts = collections.posts | draft: false %}
{% assign blogposts = collections.posts | where: draft, false %}
{% assign blogposts = collections.posts | where: data.draft, false %}
{% assign blogposts = collections.posts_nl | where: "draft", "false" %}

Does anyone know how I can accomplish this? Unfortunately it feels to me like the version of liquid used in Eleventy is an older one, and the documentation I can find never seems to address how I can do this. I would really appreciate some help! :)

1 Answers

Instead of filtering the collection in your template, you can use the configuration API to create a filtered collection in your .eleventy.js file. This should work:

// .eleventy.js
eleventyConfig.addCollection('posts', collections => {
  // get all posts by tag 'post'
  return collections.getFilteredByTag('post')
    // exclude all drafts
    .filter(post => !Boolean(post.data.draft))
});

If you need both both the filtered list of posts as well as the complete list, you can also use different aliases:

// .eleventy.js
eleventyConfig.addCollection('posts', collections => {
  return collections.getFilteredByTag('post');
});
eleventyConfig.addCollection('published_posts', collections => {
  // get all posts by tag 'post'
  return collections.getFilteredByTag('post')
    // exclude all drafts
    .filter(post => !Boolean(post.data.draft))
});
Related