grunt-assemble
grunt-assemble copied to clipboard
Escaping a partial
I'm trying out a few tools for creating a style guide and Assemble seems to fit the bill but I'm stumbling when trying to implement a key feature. I want to be able include a partial twice with the second one escaped (rendered as text) - similar to how Twitter bootstrap and other styleguides document code:
// layout.hbs
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>{{title}}</title>
</head>
<body>
<div class="container">
{{> body }}
</div>
</body>
</html>
// page.hbs
{{#markdown}}
Some notes about the pattern.
{{/markdown}}
<h2>Example</h2>
{{> alert modifier="warning" }}
<h2>Code</h2>
// None of these seem to work...
{{{{> alert modifier="warning" }}}}
{{{> alert modifier="warning" }}}
\{{> alert modifier="warning" }}
After scouring Google for Assemble/Handlebars mentions of how to escape a partial, I'm still none the wiser. Any help would be appreciated.
@lawlesscreation Thanks for the issue! If you're reporting a bug, please be sure to include:
- The version of
assemble
you are using. - Your assemblefile.js (This can be in a gist)
- The commandline output. (Screenshot or gist is fine)
- What you expected to happen instead.
The last example should work. Could you post the assemble part of your grunt config and let us know if you're using any other helpers or plugins?
In an older version of grunt-assemble
we used to render the body then render the layout using the body as a partial but we doing do that anymore. There might be something else rendering the page twice causing the escaped partial to render on the second pass.
@doowb, thanks for the reply. For me, the last example simple renders the handlebars expression as text i.e.: \{{> alert modifier="warning" }}
. I'm not using any helpers or plugins so it's fairly minimal config:
// package.json
"devDependencies": {
"grunt": "^1.0.1",
"grunt-assemble": "^0.6.3",
"grunt-browser-sync": "^2.2.0",
"grunt-contrib-clean": "^1.1.0",
"grunt-contrib-watch": "^1.0.0"
},
// Gruntfile.js
module.exports = function(grunt) {
'use strict';
grunt.initConfig({
config: {
src: './src',
dist: './dist'
},
// Builder
assemble: {
options: {
assets: '<%= config.src %>/assets',
data: ['<%= config.src %>/data/*.json'],
partials: ['<%= config.src %>/partials/*.hbs'],
flatten: true
},
docs: {
options: {
layout: '<%= config.src %>/layouts/docs.hbs'
},
files: {'<%= config.dist %>/': ['<%= config.src %>/docs/**/*.md']}
},
patterns: {
options: {
layout: '<%= config.src %>/layouts/patterns.hbs'
},
files: {'<%= config.dist %>/': ['<%= config.src %>/patterns/**/*.hbs']}
}
},
// Clean the dist folder
clean: {
all: ['<%= config.dist %>/']
},
watch: {
docs: {
files: '<%= config.src %>/docs/**/*.md',
tasks: ['assemble:docs']
},
html: {
files: [
'<%= config.src %>/layouts/**/*.hbs',
'<%= config.src %>/patterns/**/*.{html,hbs,json}'
],
tasks: ['assemble:patterns']
}
},
// Static file server
browserSync: {
dev: {
options: {
directory: true,
server: '<%= config.dist %>',
watchTask: true
},
bsFiles: {
src : [
'<%= config.dist %>/**/*'
]
}
}
}
});
grunt.loadNpmTasks('grunt-assemble');
grunt.loadNpmTasks('grunt-browser-sync');
grunt.loadNpmTasks('grunt-contrib-clean');
grunt.loadNpmTasks('grunt-contrib-watch');
// The default task to run with the `grunt` command.
grunt.registerTask('default', ['clean', 'assemble', 'browserSync', 'watch']);
// The build task to run with the `grunt` command.
grunt.registerTask('build', ['clean', 'assemble']);
};
Sadly, I've still not been able to work this one out. I'll try to create a demo repo on GitHub and link to it.
@lawlesscreation I was traveling and missed your first response... I'll take a closer look today. A demo repo will help a lot, thanks!
Here's a demo of the problem:
https://github.com/lawlesscreation/grunt-assemble-demo
Rendered output:
Some notes about the pattern.
Example
Alert
This is an alert
Code
{{> alert modifiers="warning" }}
Running on Node v6.11.3
@lawlesscreation I think I misunderstood what you're trying to accomplish. I thought that you wanted the result to be {{> alert modifiers="warning"}}
.
Now that I've looked over it again, I think that you want the html contents of the rendered partial.
If this is the case, then you can use the {{#markdown}}
helper and wrap the contents in backticks:
{{#markdown}}
```html
{{> alert modifiers="warning" }}
```
{{/markdown}}
This produces the following:
Some notes about the pattern.
Example
Alert
This is an alert
Code
<div class="alert warning" role="alert">
<h2>Alert</h2>
<p>This is an alert</p>
</div>
Thanks @doowb! that works great!
Looking at your solution reminded me that originally I had tried to use markdown for the pages instead of handlebars (it would be a lot easier to write documentation in MD). The problem was that when I included a .hbs
partial inside a .md
page, it seemed to break when there was whitespace between elements in the partial. Here's a quick demo (https://github.com/lawlesscreation/grunt-assemble-demo/tree/markdown-demo) where it stops rendering the partial as HTML after the whitespace.
You don't happen to know if this is possible? Most of the content in the page will be markdown so it seems easier than wrapping every block individually with {{#markdown}}
.
update:
I can actually cheat a little and invert the tags to close/open those from the layout:
{{/markdown}}
{{> alert modifiers="warning" }}
{{#markdown}}
Feels like a hack though :)
I've not found a better way to do this yet but it still feels a little hacky. Is there a better way to use handlebars partials inside a .md
file?
@lawlesscreation I thought I responded to this the other day...
I haven't had a chance to look into it more, but you should be able to do what you were trying in the original markdown-demo
branch. If there is an issue with it breaking on whitespace, it might be indentation related since markdown expects different indentations in specific situations. For example, if something ends up being indented 4 spaces, then it becomes a code block.
I'll try to take a closer look and get back to you.