Search code examples
jsongulpnunjucksgulp-nunjucks-rendergulp-data

Multiple Nunjucks files with different JSON data using gulp


I would like to use gulp and Nunjucks to generate multiple template files at once with varying content. These templates will all have the exact same layout, but pass in different variables for text/images.

I am able to successfully generate a single index.html file, but am unsure how to set this up for multiple files to be created at once. Here is a simplified version of what I have:

gulpfile.js

var nunjucks = require('gulp-nunjucks-render');
var data     = require('gulp-data');

gulp.task('nunjucks', function () {
    return gulp
        .src('./src/layouts/**/*.+(html|nunjucks)')
        .pipe(data(function () { return require('./src/data.json'); }))
        .pipe(nunjucks({ path: ['./src/templates'] }))
        .pipe(gulp.dest('./dist'));
});

layout.nunjucks

<head>
    {% block title %} {% endblock %}
</head>

index.nunjucks

{% extends "layout.nunjucks" %}

{% block title %}
    <title>{{ title }}</title>
{% endblock %}

data.json

{
    "title": "DEFAULT"
}

What is the best way to alter this workflow to generate multiple files where each has a different title?

I've found that I can create multiple index.nunjucks files, but it looks like they all use the same data.json file. I also wouldn't want to make a separate JSON file for each.

Could I add an array to my data.json file to have Nunjucks loop through and create a separate file for each object found? Such as the following:

data.json

{
    "files": [{
        "title": "DEFAULT",
    }, {
        "title": "DEFAULT #2"
    }]
}

Or is there a way to set variables within the index.nunjucks file without relying on storing them in JSON?


Solution

  • Found the way to do this: in each Nunjucks index file, I set a variable named email to the filename and updated my data.json file with a new object matching the filename with its own content.

    default.nunjucks

    {% set email = default %}
    
    {% include "index.nunjucks" %}
    

    test.nunjucks

    {% set email = test %}
    
    {% include "index.nunjucks" %}
    

    index.nunjucks

    {% extends "layout.nunjucks" %}
    
    {% block title %}
        <title>{{ email.title }}</title>
    {% endblock %}
    

    layout.nunjucks

    <head>
        {% block title %} {% endblock %}
    </head>
    

    data.json

    {
        "default":
        {
            "title": "TITLE"
        },
        "test":
        {
            "title": "TEST TITLE"
        }
    }
    

    When compiled through gulp, two separate emails are created with their own title using the same template.