Skip to content

Instantly share code, notes, and snippets.

@monochromer
Last active June 28, 2023 19:05

Revisions

  1. monochromer revised this gist Jun 28, 2023. 1 changed file with 2 additions and 3 deletions.
    5 changes: 2 additions & 3 deletions index.md
    Original file line number Diff line number Diff line change
    @@ -55,10 +55,9 @@ it produces files output:
    ```
    /developer/
    /developer/1
    /developer/2
    /manager/
    /manager/1/
    /manager/2/
    /manager/3/
    /designer/
    /designer/1
    .etc
    ```
  2. monochromer created this gist Jun 28, 2023.
    126 changes: 126 additions & 0 deletions index.11tydata.js
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,126 @@
    function createPagination(paginationOptions) {
    return {
    data: typeof paginationOptions.data === 'string'
    ? paginationOptions.data
    : 'collections.all',

    size: 1,

    alias: paginationOptions.alias ?? 'paginationChunk',

    before: function(paginationData, data) {
    const chunks = [];
    const pageSize = paginationOptions.pageSize;

    const allItems = typeof paginationOptions.data === 'function'
    ? paginationOptions.data(data)
    : data[paginationOptions.data];

    const getKey = typeof paginationOptions.key === 'function'
    ? paginationOptions.key
    : (item) => item[paginationOptions.key];

    const itemsByKey = allItems.reduce((map, item) => {
    const key = getKey(item);
    map[key] = map[key] || [];
    map[key].push(item);
    return map;
    }, {});

    for (const [key, group] of Object.entries(itemsByKey)) {
    const pageNumbers = Math.ceil(group.length / pageSize);
    const groupChunks = [];
    for (let page = 0; page < pageNumbers; page++) {
    const items = group.slice(pageSize * page, pageSize * (page + 1));
    const item = {
    key,
    items,
    pageSize,
    page,
    };
    Object.defineProperty(item, 'next', {
    enumerable: false,
    get() {
    return groupChunks[page + 1]
    }
    });
    Object.defineProperty(item, 'previous', {
    enumerable: false,
    get() {
    return groupChunks[page - 1]
    }
    });
    groupChunks.push(item);
    }
    chunks.push(...groupChunks);
    }

    return chunks;
    }
    }
    }

    module.exports = {
    users: [
    {
    id: 1,
    name: 'User 1',
    role: 'developer'
    },
    {
    id: 2,
    name: 'User 2',
    role: 'manager'
    },
    {
    id: 3,
    name: 'User 3',
    role: 'designer'
    },
    {
    id: 4,
    name: 'User 4',
    role: 'developer'
    },
    {
    id: 5,
    name: 'User 5',
    role: 'manager'
    },
    {
    id: 6,
    name: 'User 6',
    role: 'designer'
    },
    {
    id: 7,
    name: 'User 7',
    role: 'developer'
    },
    {
    id: 8,
    name: 'User 8',
    role: 'manager'
    },
    {
    id: 9,
    name: 'User 9',
    role: 'designer'
    },
    ],

    pagination: createPagination({
    alias: 'paginationChunk',
    pageSize: 2,
    data: data => data.users,
    key: (item) => item.role,
    }),

    eleventyComputed: {
    permalink: function(data) {
    const { paginationChunk } = data;
    const pageNumber = paginationChunk.page === 0 ? '' : `${paginationChunk.page}/`;
    return `/${paginationChunk.key}/${pageNumber}`
    },
    }
    }
    64 changes: 64 additions & 0 deletions index.md
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,64 @@
    # Eleventy double pagination

    For example, for users collection:
    ```javascript
    const users = [
    {
    id: 1,
    name: 'User 1',
    role: 'developer'
    },
    {
    id: 2,
    name: 'User 2',
    role: 'manager'
    },
    {
    id: 3,
    name: 'User 3',
    role: 'designer'
    },
    {
    id: 4,
    name: 'User 4',
    role: 'developer'
    },
    {
    id: 5,
    name: 'User 5',
    role: 'manager'
    },
    {
    id: 6,
    name: 'User 6',
    role: 'designer'
    },
    {
    id: 7,
    name: 'User 7',
    role: 'developer'
    },
    {
    id: 8,
    name: 'User 8',
    role: 'manager'
    },
    {
    id: 9,
    name: 'User 9',
    role: 'designer'
    },
    ]
    ```

    it produces files output:
    ```
    /developer/
    /developer/1
    /developer/2
    /manager/
    /manager/1/
    /manager/2/
    /manager/3/
    .etc
    ```
    12 changes: 12 additions & 0 deletions index.njk
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,12 @@
    ---
    permalink: /
    ---

    <h2>Chunk</h2>
    <pre>{{ paginationChunk | dump(2) | safe }}</pre>

    <h2>Next</h2>
    <pre>{{ paginationChunk.next | dump(2) | safe }}</pre>

    <h2>Prev</h2>
    <pre>{{ paginationChunk.previous | dump(2) | safe }}</pre>