16
votes

I would like to create another page-based loop, in the same way the _posts folder works for the blog section, but for a small catalogue of magazines. (Hopefully that makes sense)

Maybe i'm misunderstanding something simple, but I just can't work it out. I have this loop, which feels like it should work, but nothing gets returned.

{% for page in site.pressitems %}
<li>
    <a href="{{ post.url }}">{{ page.title }}</a>
</li>
{% endfor %}

Code, links, explanation, anything is greatly appreciated. :)

4

4 Answers

22
votes

You can't add your own collection to site just like that.

site only knows about three collections: pages, posts, and categories. You can get all the posts of a category by doing site.<category>.posts . AFAIK, categories only work for posts, not pages.

This makes sense, since Jekyll is supposed to be mainly a blogging engine, and not a generic static website generator.

So your best solution right now consists on "lying" to jekyll. Make it believe you have posts, when in reality you are making pages.

_posts/
  pressitems/
  blog/

You will be able to loop over the elements inside _posts/pressitems like this:

for item in site.categories.pressitems.posts do
  ... {{ item.title }} ... {{ item.url }}
endfor

Similarly, your "real blog entries" would go this way:

for p in site.categories.blog.posts do
  ... {{ p.title }} ... {{ p.url }}
endfor

The catch is that you will have to respect Jekyll's naming convention regarding filenames; your pressitems have to look like real posts. This means they have to be named starting with a yyyy-mm-dd- string, like posts. Just give them a random date.

_posts/
  pressitems/
    1901-01-01-the-first-press-item.textile
    1902-01-01-the-second-one.textile

EDIT: This was true when this post was originally written, in 2012, but not any more. Modern Jekyll does allow you to create your own collections https://jekyllrb.com/docs/collections/

18
votes

You can iterate through site.pages

{% for page in site.pages %}
  <h3><a href="{{ page.url }}">{{ page.title }}</a></h3>
  <p>{{ page.content }}</p>
{% endfor %}

And limit the list the only pages that use a particular layout.

{% for page in site.pages %}
  {% if page.layout == 'team' %}  
    <h3><a href="{{ page.url }}">{{ page.title }}</a></h3>
    <p>{{ page.content }}</p>
  {% endif %}
{% endfor %}

See this post about generating a sitemap: http://vvv.tobiassjosten.net/jekyll/jekyll-sitemap-without-plugins/

13
votes

As of October 2016:

In Jekyll 2.5.3 you can actually can add your own collection to site.

Add _my_collection folder to root and fill with documents. Add to _config.yml:

collections:
- my_collection

Now call documents using either post, page, or category. e.g. { for post in site.my_collection < do something > }

It is important to note that this feature can be used it has been marked by the Jekyll team as "an experimental feature and the API may change until the feature stabilizes".

5
votes

On jekyll you can also add yaml front-matter to pages. There's nothing wrong with adding custom front-matter, like page-category.

---
layout: plain
title: "My beautiful page"
description: ""
snippet: ""
page-category: "category 1"
---

access them via:

{% for page in site.pages %}
   {% if page.page-category == "category 1" %}
        {{ page.content }}
   {% endif %}
{% endfor %}