Writing a partial name in the DOM with Handlebars/assemble

1k Views Asked by At

I want to write an HTML comment before and after each partial, with the path or name of the partial, to the guys who shall implement it.

I can get the path and filename of the page, but not the partial. Do you know how?

1

There are 1 best solutions below

0
On BEST ANSWER

I think I do know what you mean now.

I put this helper together, let me know if it helps.

Currently the helper only adds a comment before the partial with a path to the original partial - which includes the name of the partial. it seems superfluous to also include the name of the partial since it's already in the path, but if you want that please add a feature request on that repo and I'll get it added. We can easily have it append a comment as well.

You can install the helper with:

npm i handlebars-helper-partial

To have the helper generate the HTML comments with the path to the partial, you will need to define following in the assemble options (I did it this way to make the helper usable for others as well):

assemble: {
  options: {
    include: {
      origin: true
    }
  },
  site: {
    files: {}
  }
}

Alternatively you can just add a file named include.json with:

{
  "include": {
    "origin": true
  }
}

And then specify the path to that file in the Assemble options:

assemble: {
  options: {
    data: ['include.json', 'other/files/*.json']
  },
  site: {
    files: {}
  }
}

Here is the full code for the helper:

/**
 * Handlebars Helpers: {{include}}
 * Copyright (c) 2013 Jon Schlinkert
 * Licensed under the MIT License (MIT).
 */

var path = require('path');
var _ = require('lodash');
var yfm = require('assemble-yaml');



// Export helpers
module.exports.register = function (Handlebars, options, params) {

  'use strict';

  var assemble = params.assemble;
  var grunt = params.grunt;
  var opts = options || {};

  /**
   * {{partial}}
   * Alternative to {{> partial }}
   *
   * @param  {String} name    The name of the partial to use
   * @param  {Object} context The context to pass to the partial
   * @return {String}         Returns compiled HTML
   * @xample: {{partial 'foo' bar}}
   */
  Handlebars.registerHelper('include', function(name, context) {
    if(!Array.isArray(assemble.partials)) {
      assemble.partials = [assemble.partials];
    }

    var filepath = _.first(_.filter(assemble.partials, function(fp) {
      return path.basename(fp, path.extname(fp)) === name;
    }));

    // Process context, using YAML front-matter,
    // grunt config and Assemble options.data
    var pageObj = yfm.extract(filepath) || {};
    var metadata = pageObj.context || {};

    // `context`           = the given context (second parameter)
    // `metadata`          = YAML front matter of the partial
    // `opts.data[name]`   = JSON/YAML data file defined in Assemble options.data with a basename
    //                       matching the name of the partial, e.g {{partial 'foo'}} => foo.json
    // `this`              = YAML front matter of _either_ the "inheriting" page, or a block
    //                       expression wrapping the helper
    // `opts`              = Custom properties defined in Assemble options
    // `grunt.config.data` = Data from grunt.config.data (e.g. pkg: grunt.file.readJSON('package.json'))

    context = _.extend({}, grunt.config.data, opts, this, opts.data[name], metadata, context);
    context = grunt.config.process(context);

    var template = Handlebars.partials[name];
    var fn = Handlebars.compile(template);

    var output = fn(context).replace(/^\s+/, '');

    // Prepend output with the filepath to the original partial
    opts.data.include = opts.data.include || {};
    if(opts.data.include.origin === true) {
      output = '<!-- ' + filepath + ' -->\n' + output;
    }

    return new Handlebars.SafeString(output);
  });
};