Implement inline partials
Allows for partials to be defined within the current template to allow for localized code reuse as well as for conditional behavior within nested partials. Fixes #1018
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
import registerInline from './decorators/inline';
|
||||
|
||||
export function registerDefaultDecorators(instance) {
|
||||
registerInline(instance);
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,22 @@
|
||||
import {extend} from '../utils';
|
||||
|
||||
export default function(instance) {
|
||||
instance.registerDecorator('inline', function(fn, props, container, options) {
|
||||
let ret = fn;
|
||||
if (!props.partials) {
|
||||
props.partials = {};
|
||||
ret = function(context, options) {
|
||||
// Create a new partials stack frame prior to exec.
|
||||
let original = container.partials;
|
||||
container.partials = extend({}, original, props.partials);
|
||||
let ret = fn(context, options);
|
||||
container.partials = original;
|
||||
return ret;
|
||||
};
|
||||
}
|
||||
|
||||
props.partials[options.args[0]] = options.fn;
|
||||
|
||||
return ret;
|
||||
});
|
||||
}
|
||||
@@ -239,6 +239,10 @@ export function invokePartial(partial, context, options) {
|
||||
let partialBlock;
|
||||
if (options.fn && options.fn !== noop) {
|
||||
partialBlock = options.data['partial-block'] = options.fn;
|
||||
|
||||
if (partialBlock.partials) {
|
||||
options.partials = Utils.extend({}, options.partials, partialBlock.partials);
|
||||
}
|
||||
}
|
||||
|
||||
if (partial === undefined && partialBlock) {
|
||||
|
||||
@@ -257,6 +257,45 @@ describe('partials', function() {
|
||||
});
|
||||
});
|
||||
|
||||
describe('inline partials', function() {
|
||||
it('should define inline partials for template', function() {
|
||||
shouldCompileTo('{{#*inline "myPartial"}}success{{/inline}}{{> myPartial}}', {}, 'success');
|
||||
});
|
||||
it('should overwrite multiple partials in the same template', function() {
|
||||
shouldCompileTo('{{#*inline "myPartial"}}fail{{/inline}}{{#*inline "myPartial"}}success{{/inline}}{{> myPartial}}', {}, 'success');
|
||||
});
|
||||
it('should define inline partials for block', function() {
|
||||
shouldCompileTo('{{#with .}}{{#*inline "myPartial"}}success{{/inline}}{{> myPartial}}{{/with}}', {}, 'success');
|
||||
shouldThrow(function() {
|
||||
shouldCompileTo('{{#with .}}{{#*inline "myPartial"}}success{{/inline}}{{/with}}{{> myPartial}}', {}, 'success');
|
||||
}, Error, /myPartial could not/);
|
||||
});
|
||||
it('should override global partials', function() {
|
||||
shouldCompileTo('{{#*inline "myPartial"}}success{{/inline}}{{> myPartial}}', {hash: {}, partials: {myPartial: function() { return 'fail'; }}}, 'success');
|
||||
});
|
||||
it('should override template partials', function() {
|
||||
shouldCompileTo('{{#*inline "myPartial"}}fail{{/inline}}{{#with .}}{{#*inline "myPartial"}}success{{/inline}}{{> myPartial}}{{/with}}', {}, 'success');
|
||||
});
|
||||
it('should override partials down the entire stack', function() {
|
||||
shouldCompileTo('{{#with .}}{{#*inline "myPartial"}}success{{/inline}}{{#with .}}{{#with .}}{{> myPartial}}{{/with}}{{/with}}{{/with}}', {}, 'success');
|
||||
});
|
||||
|
||||
it('should define inline partials for partial call', function() {
|
||||
shouldCompileToWithPartials(
|
||||
'{{#*inline "myPartial"}}success{{/inline}}{{> dude}}',
|
||||
[{}, {}, {dude: '{{> myPartial }}'}],
|
||||
true,
|
||||
'success');
|
||||
});
|
||||
it('should define inline partials in partial block call', function() {
|
||||
shouldCompileToWithPartials(
|
||||
'{{#> dude}}{{#*inline "myPartial"}}success{{/inline}}{{/dude}}',
|
||||
[{}, {}, {dude: '{{> myPartial }}'}],
|
||||
true,
|
||||
'success');
|
||||
});
|
||||
});
|
||||
|
||||
it('should pass compiler flags', function() {
|
||||
if (Handlebars.compile) {
|
||||
var env = Handlebars.create();
|
||||
|
||||
Reference in New Issue
Block a user