Greg
Greg

Reputation: 642

How can I pre-process markdown files in VuePress?

VuePress's standard templating, as documented, occurs during the Vue component rendering. This means the markdown compiler, markdown-it, will not see the rendered template results and will not be able to operate on them.

This can cause issues with variable substitution in links, code blocks, and a number of other edge cases. A somewhat common answer to this issue is to drop down to using raw HTML tags. I find this somewhat undesirable as it's tackles the issue at the wrong stage(post-markdown compilation) and requires content creators to juggle markdown with Vue/HTML/framework concerns.

How can I process the markdown files before markdown compilation in a manner that fits in with the dev/build pipeline?

Upvotes: 1

Views: 953

Answers (1)

Greg
Greg

Reputation: 642

VuePress currently processes markdown files in the webpack pipeline. The gist of this process is:

.md -> markdown-loader(VuePress custom) -> vue-loader -> ...

I will show an example of how to render the markdown templates with Nunjucks before it gets passed through to the markdown loader for compilation.

In order to pre-process the markdown we need to slip a loader in before the first VuePress loader. Luckily we can do this through the exposed plugin/config API:

.vuepress/config.js

chainWebpack: config => {
    config.module
      .rule('md')
      .test(/\.md$/)
      .use(path.resolve(__dirname, './nunjucks'))
        .loader(path.resolve(__dirname, './nunjucks'))
        .end()
},

.vuepress/nunjucks.js

const nunjucks = require('nunjucks')

// Change start/end tokens so they don't collide with the Vue syntax
nunjucks.configure({
    autoescape: false,
    tags: {
        blockStart: '{{{%',
        blockEnd: '%}}}',
        variableStart: '{{{',
        variableEnd: '}}}',
        commentStart: '{{{#',
        commentEnd: '#}}}'
      }
})

const config = {
    apiVersion: 32,
}

module.exports = function(source) {
    const rendered = nunjucks.renderString(source, config)
    return rendered
}

Upvotes: 1

Related Questions