source: pro-violet-viettel/www/deploy/20150304/assets/js/handlebars-v2.0.0.js @ 804

Last change on this file since 804 was 780, checked in by dungnv, 10 years ago
File size: 98.5 KB
Line 
1/*!
2
3 handlebars v2.0.0
4
5Copyright (C) 2011-2014 by Yehuda Katz
6
7Permission is hereby granted, free of charge, to any person obtaining a copy
8of this software and associated documentation files (the "Software"), to deal
9in the Software without restriction, including without limitation the rights
10to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11copies of the Software, and to permit persons to whom the Software is
12furnished to do so, subject to the following conditions:
13
14The above copyright notice and this permission notice shall be included in
15all copies or substantial portions of the Software.
16
17THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
20AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
23THE SOFTWARE.
24
25@license
26*/
27/* exported Handlebars */
28(function (root, factory) {
29  if (typeof define === 'function' && define.amd) {
30    define([], factory);
31  } else if (typeof exports === 'object') {
32    module.exports = factory();
33  } else {
34    root.Handlebars = root.Handlebars || factory();
35  }
36}(this, function () {
37// handlebars/safe-string.js
38var __module4__ = (function() {
39  "use strict";
40  var __exports__;
41  // Build out our basic SafeString type
42  function SafeString(string) {
43    this.string = string;
44  }
45
46  SafeString.prototype.toString = function() {
47    return "" + this.string;
48  };
49
50  __exports__ = SafeString;
51  return __exports__;
52})();
53
54// handlebars/utils.js
55var __module3__ = (function(__dependency1__) {
56  "use strict";
57  var __exports__ = {};
58  /*jshint -W004 */
59  var SafeString = __dependency1__;
60
61  var escape = {
62    "&": "&",
63    "<": "&lt;",
64    ">": "&gt;",
65    '"': "&quot;",
66    "'": "&#x27;",
67    "`": "&#x60;"
68  };
69
70  var badChars = /[&<>"'`]/g;
71  var possible = /[&<>"'`]/;
72
73  function escapeChar(chr) {
74    return escape[chr];
75  }
76
77  function extend(obj /* , ...source */) {
78    for (var i = 1; i < arguments.length; i++) {
79      for (var key in arguments[i]) {
80        if (Object.prototype.hasOwnProperty.call(arguments[i], key)) {
81          obj[key] = arguments[i][key];
82        }
83      }
84    }
85
86    return obj;
87  }
88
89  __exports__.extend = extend;var toString = Object.prototype.toString;
90  __exports__.toString = toString;
91  // Sourced from lodash
92  // https://github.com/bestiejs/lodash/blob/master/LICENSE.txt
93  var isFunction = function(value) {
94    return typeof value === 'function';
95  };
96  // fallback for older versions of Chrome and Safari
97  /* istanbul ignore next */
98  if (isFunction(/x/)) {
99    isFunction = function(value) {
100      return typeof value === 'function' && toString.call(value) === '[object Function]';
101    };
102  }
103  var isFunction;
104  __exports__.isFunction = isFunction;
105  /* istanbul ignore next */
106  var isArray = Array.isArray || function(value) {
107    return (value && typeof value === 'object') ? toString.call(value) === '[object Array]' : false;
108  };
109  __exports__.isArray = isArray;
110
111  function escapeExpression(string) {
112    // don't escape SafeStrings, since they're already safe
113    if (string instanceof SafeString) {
114      return string.toString();
115    } else if (string == null) {
116      return "";
117    } else if (!string) {
118      return string + '';
119    }
120
121    // Force a string conversion as this will be done by the append regardless and
122    // the regex test will do this transparently behind the scenes, causing issues if
123    // an object's to string has escaped characters in it.
124    string = "" + string;
125
126    if(!possible.test(string)) { return string; }
127    return string.replace(badChars, escapeChar);
128  }
129
130  __exports__.escapeExpression = escapeExpression;function isEmpty(value) {
131    if (!value && value !== 0) {
132      return true;
133    } else if (isArray(value) && value.length === 0) {
134      return true;
135    } else {
136      return false;
137    }
138  }
139
140  __exports__.isEmpty = isEmpty;function appendContextPath(contextPath, id) {
141    return (contextPath ? contextPath + '.' : '') + id;
142  }
143
144  __exports__.appendContextPath = appendContextPath;
145  return __exports__;
146})(__module4__);
147
148// handlebars/exception.js
149var __module5__ = (function() {
150  "use strict";
151  var __exports__;
152
153  var errorProps = ['description', 'fileName', 'lineNumber', 'message', 'name', 'number', 'stack'];
154
155  function Exception(message, node) {
156    var line;
157    if (node && node.firstLine) {
158      line = node.firstLine;
159
160      message += ' - ' + line + ':' + node.firstColumn;
161    }
162
163    var tmp = Error.prototype.constructor.call(this, message);
164
165    // Unfortunately errors are not enumerable in Chrome (at least), so `for prop in tmp` doesn't work.
166    for (var idx = 0; idx < errorProps.length; idx++) {
167      this[errorProps[idx]] = tmp[errorProps[idx]];
168    }
169
170    if (line) {
171      this.lineNumber = line;
172      this.column = node.firstColumn;
173    }
174  }
175
176  Exception.prototype = new Error();
177
178  __exports__ = Exception;
179  return __exports__;
180})();
181
182// handlebars/base.js
183var __module2__ = (function(__dependency1__, __dependency2__) {
184  "use strict";
185  var __exports__ = {};
186  var Utils = __dependency1__;
187  var Exception = __dependency2__;
188
189  var VERSION = "2.0.0";
190  __exports__.VERSION = VERSION;var COMPILER_REVISION = 6;
191  __exports__.COMPILER_REVISION = COMPILER_REVISION;
192  var REVISION_CHANGES = {
193    1: '<= 1.0.rc.2', // 1.0.rc.2 is actually rev2 but doesn't report it
194    2: '== 1.0.0-rc.3',
195    3: '== 1.0.0-rc.4',
196    4: '== 1.x.x',
197    5: '== 2.0.0-alpha.x',
198    6: '>= 2.0.0-beta.1'
199  };
200  __exports__.REVISION_CHANGES = REVISION_CHANGES;
201  var isArray = Utils.isArray,
202      isFunction = Utils.isFunction,
203      toString = Utils.toString,
204      objectType = '[object Object]';
205
206  function HandlebarsEnvironment(helpers, partials) {
207    this.helpers = helpers || {};
208    this.partials = partials || {};
209
210    registerDefaultHelpers(this);
211  }
212
213  __exports__.HandlebarsEnvironment = HandlebarsEnvironment;HandlebarsEnvironment.prototype = {
214    constructor: HandlebarsEnvironment,
215
216    logger: logger,
217    log: log,
218
219    registerHelper: function(name, fn) {
220      if (toString.call(name) === objectType) {
221        if (fn) { throw new Exception('Arg not supported with multiple helpers'); }
222        Utils.extend(this.helpers, name);
223      } else {
224        this.helpers[name] = fn;
225      }
226    },
227    unregisterHelper: function(name) {
228      delete this.helpers[name];
229    },
230
231    registerPartial: function(name, partial) {
232      if (toString.call(name) === objectType) {
233        Utils.extend(this.partials,  name);
234      } else {
235        this.partials[name] = partial;
236      }
237    },
238    unregisterPartial: function(name) {
239      delete this.partials[name];
240    }
241  };
242
243  function registerDefaultHelpers(instance) {
244    instance.registerHelper('helperMissing', function(/* [args, ]options */) {
245      if(arguments.length === 1) {
246        // A missing field in a {{foo}} constuct.
247        return undefined;
248      } else {
249        // Someone is actually trying to call something, blow up.
250        throw new Exception("Missing helper: '" + arguments[arguments.length-1].name + "'");
251      }
252    });
253
254    instance.registerHelper('blockHelperMissing', function(context, options) {
255      var inverse = options.inverse,
256          fn = options.fn;
257
258      if(context === true) {
259        return fn(this);
260      } else if(context === false || context == null) {
261        return inverse(this);
262      } else if (isArray(context)) {
263        if(context.length > 0) {
264          if (options.ids) {
265            options.ids = [options.name];
266          }
267
268          return instance.helpers.each(context, options);
269        } else {
270          return inverse(this);
271        }
272      } else {
273        if (options.data && options.ids) {
274          var data = createFrame(options.data);
275          data.contextPath = Utils.appendContextPath(options.data.contextPath, options.name);
276          options = {data: data};
277        }
278
279        return fn(context, options);
280      }
281    });
282
283    instance.registerHelper('each', function(context, options) {
284      if (!options) {
285        throw new Exception('Must pass iterator to #each');
286      }
287
288      var fn = options.fn, inverse = options.inverse;
289      var i = 0, ret = "", data;
290
291      var contextPath;
292      if (options.data && options.ids) {
293        contextPath = Utils.appendContextPath(options.data.contextPath, options.ids[0]) + '.';
294      }
295
296      if (isFunction(context)) { context = context.call(this); }
297
298      if (options.data) {
299        data = createFrame(options.data);
300      }
301
302      if(context && typeof context === 'object') {
303        if (isArray(context)) {
304          for(var j = context.length; i<j; i++) {
305            if (data) {
306              data.index = i;
307              data.first = (i === 0);
308              data.last  = (i === (context.length-1));
309
310              if (contextPath) {
311                data.contextPath = contextPath + i;
312              }
313            }
314            ret = ret + fn(context[i], { data: data });
315          }
316        } else {
317          for(var key in context) {
318            if(context.hasOwnProperty(key)) {
319              if(data) {
320                data.key = key;
321                data.index = i;
322                data.first = (i === 0);
323
324                if (contextPath) {
325                  data.contextPath = contextPath + key;
326                }
327              }
328              ret = ret + fn(context[key], {data: data});
329              i++;
330            }
331          }
332        }
333      }
334
335      if(i === 0){
336        ret = inverse(this);
337      }
338
339      return ret;
340    });
341
342    instance.registerHelper('if', function(conditional, options) {
343      if (isFunction(conditional)) { conditional = conditional.call(this); }
344
345      // Default behavior is to render the positive path if the value is truthy and not empty.
346      // The `includeZero` option may be set to treat the condtional as purely not empty based on the
347      // behavior of isEmpty. Effectively this determines if 0 is handled by the positive path or negative.
348      if ((!options.hash.includeZero && !conditional) || Utils.isEmpty(conditional)) {
349        return options.inverse(this);
350      } else {
351        return options.fn(this);
352      }
353    });
354
355    instance.registerHelper('unless', function(conditional, options) {
356      return instance.helpers['if'].call(this, conditional, {fn: options.inverse, inverse: options.fn, hash: options.hash});
357    });
358
359    instance.registerHelper('with', function(context, options) {
360      if (isFunction(context)) { context = context.call(this); }
361
362      var fn = options.fn;
363
364      if (!Utils.isEmpty(context)) {
365        if (options.data && options.ids) {
366          var data = createFrame(options.data);
367          data.contextPath = Utils.appendContextPath(options.data.contextPath, options.ids[0]);
368          options = {data:data};
369        }
370
371        return fn(context, options);
372      } else {
373        return options.inverse(this);
374      }
375    });
376
377    instance.registerHelper('log', function(message, options) {
378      var level = options.data && options.data.level != null ? parseInt(options.data.level, 10) : 1;
379      instance.log(level, message);
380    });
381
382    instance.registerHelper('lookup', function(obj, field) {
383      return obj && obj[field];
384    });
385  }
386
387  var logger = {
388    methodMap: { 0: 'debug', 1: 'info', 2: 'warn', 3: 'error' },
389
390    // State enum
391    DEBUG: 0,
392    INFO: 1,
393    WARN: 2,
394    ERROR: 3,
395    level: 3,
396
397    // can be overridden in the host environment
398    log: function(level, message) {
399      if (logger.level <= level) {
400        var method = logger.methodMap[level];
401        if (typeof console !== 'undefined' && console[method]) {
402          console[method].call(console, message);
403        }
404      }
405    }
406  };
407  __exports__.logger = logger;
408  var log = logger.log;
409  __exports__.log = log;
410  var createFrame = function(object) {
411    var frame = Utils.extend({}, object);
412    frame._parent = object;
413    return frame;
414  };
415  __exports__.createFrame = createFrame;
416  return __exports__;
417})(__module3__, __module5__);
418
419// handlebars/runtime.js
420var __module6__ = (function(__dependency1__, __dependency2__, __dependency3__) {
421  "use strict";
422  var __exports__ = {};
423  var Utils = __dependency1__;
424  var Exception = __dependency2__;
425  var COMPILER_REVISION = __dependency3__.COMPILER_REVISION;
426  var REVISION_CHANGES = __dependency3__.REVISION_CHANGES;
427  var createFrame = __dependency3__.createFrame;
428
429  function checkRevision(compilerInfo) {
430    var compilerRevision = compilerInfo && compilerInfo[0] || 1,
431        currentRevision = COMPILER_REVISION;
432
433    if (compilerRevision !== currentRevision) {
434      if (compilerRevision < currentRevision) {
435        var runtimeVersions = REVISION_CHANGES[currentRevision],
436            compilerVersions = REVISION_CHANGES[compilerRevision];
437        throw new Exception("Template was precompiled with an older version of Handlebars than the current runtime. "+
438              "Please update your precompiler to a newer version ("+runtimeVersions+") or downgrade your runtime to an older version ("+compilerVersions+").");
439      } else {
440        // Use the embedded version info since the runtime doesn't know about this revision yet
441        throw new Exception("Template was precompiled with a newer version of Handlebars than the current runtime. "+
442              "Please update your runtime to a newer version ("+compilerInfo[1]+").");
443      }
444    }
445  }
446
447  __exports__.checkRevision = checkRevision;// TODO: Remove this line and break up compilePartial
448
449  function template(templateSpec, env) {
450    /* istanbul ignore next */
451    if (!env) {
452      throw new Exception("No environment passed to template");
453    }
454    if (!templateSpec || !templateSpec.main) {
455      throw new Exception('Unknown template object: ' + typeof templateSpec);
456    }
457
458    // Note: Using env.VM references rather than local var references throughout this section to allow
459    // for external users to override these as psuedo-supported APIs.
460    env.VM.checkRevision(templateSpec.compiler);
461
462    var invokePartialWrapper = function(partial, indent, name, context, hash, helpers, partials, data, depths) {
463      if (hash) {
464        context = Utils.extend({}, context, hash);
465      }
466
467      var result = env.VM.invokePartial.call(this, partial, name, context, helpers, partials, data, depths);
468
469      if (result == null && env.compile) {
470        var options = { helpers: helpers, partials: partials, data: data, depths: depths };
471        partials[name] = env.compile(partial, { data: data !== undefined, compat: templateSpec.compat }, env);
472        result = partials[name](context, options);
473      }
474      if (result != null) {
475        if (indent) {
476          var lines = result.split('\n');
477          for (var i = 0, l = lines.length; i < l; i++) {
478            if (!lines[i] && i + 1 === l) {
479              break;
480            }
481
482            lines[i] = indent + lines[i];
483          }
484          result = lines.join('\n');
485        }
486        return result;
487      } else {
488        throw new Exception("The partial " + name + " could not be compiled when running in runtime-only mode");
489      }
490    };
491
492    // Just add water
493    var container = {
494      lookup: function(depths, name) {
495        var len = depths.length;
496        for (var i = 0; i < len; i++) {
497          if (depths[i] && depths[i][name] != null) {
498            return depths[i][name];
499          }
500        }
501      },
502      lambda: function(current, context) {
503        return typeof current === 'function' ? current.call(context) : current;
504      },
505
506      escapeExpression: Utils.escapeExpression,
507      invokePartial: invokePartialWrapper,
508
509      fn: function(i) {
510        return templateSpec[i];
511      },
512
513      programs: [],
514      program: function(i, data, depths) {
515        var programWrapper = this.programs[i],
516            fn = this.fn(i);
517        if (data || depths) {
518          programWrapper = program(this, i, fn, data, depths);
519        } else if (!programWrapper) {
520          programWrapper = this.programs[i] = program(this, i, fn);
521        }
522        return programWrapper;
523      },
524
525      data: function(data, depth) {
526        while (data && depth--) {
527          data = data._parent;
528        }
529        return data;
530      },
531      merge: function(param, common) {
532        var ret = param || common;
533
534        if (param && common && (param !== common)) {
535          ret = Utils.extend({}, common, param);
536        }
537
538        return ret;
539      },
540
541      noop: env.VM.noop,
542      compilerInfo: templateSpec.compiler
543    };
544
545    var ret = function(context, options) {
546      options = options || {};
547      var data = options.data;
548
549      ret._setup(options);
550      if (!options.partial && templateSpec.useData) {
551        data = initData(context, data);
552      }
553      var depths;
554      if (templateSpec.useDepths) {
555        depths = options.depths ? [context].concat(options.depths) : [context];
556      }
557
558      return templateSpec.main.call(container, context, container.helpers, container.partials, data, depths);
559    };
560    ret.isTop = true;
561
562    ret._setup = function(options) {
563      if (!options.partial) {
564        container.helpers = container.merge(options.helpers, env.helpers);
565
566        if (templateSpec.usePartial) {
567          container.partials = container.merge(options.partials, env.partials);
568        }
569      } else {
570        container.helpers = options.helpers;
571        container.partials = options.partials;
572      }
573    };
574
575    ret._child = function(i, data, depths) {
576      if (templateSpec.useDepths && !depths) {
577        throw new Exception('must pass parent depths');
578      }
579
580      return program(container, i, templateSpec[i], data, depths);
581    };
582    return ret;
583  }
584
585  __exports__.template = template;function program(container, i, fn, data, depths) {
586    var prog = function(context, options) {
587      options = options || {};
588
589      return fn.call(container, context, container.helpers, container.partials, options.data || data, depths && [context].concat(depths));
590    };
591    prog.program = i;
592    prog.depth = depths ? depths.length : 0;
593    return prog;
594  }
595
596  __exports__.program = program;function invokePartial(partial, name, context, helpers, partials, data, depths) {
597    var options = { partial: true, helpers: helpers, partials: partials, data: data, depths: depths };
598
599    if(partial === undefined) {
600      throw new Exception("The partial " + name + " could not be found");
601    } else if(partial instanceof Function) {
602      return partial(context, options);
603    }
604  }
605
606  __exports__.invokePartial = invokePartial;function noop() { return ""; }
607
608  __exports__.noop = noop;function initData(context, data) {
609    if (!data || !('root' in data)) {
610      data = data ? createFrame(data) : {};
611      data.root = context;
612    }
613    return data;
614  }
615  return __exports__;
616})(__module3__, __module5__, __module2__);
617
618// handlebars.runtime.js
619var __module1__ = (function(__dependency1__, __dependency2__, __dependency3__, __dependency4__, __dependency5__) {
620  "use strict";
621  var __exports__;
622  /*globals Handlebars: true */
623  var base = __dependency1__;
624
625  // Each of these augment the Handlebars object. No need to setup here.
626  // (This is done to easily share code between commonjs and browse envs)
627  var SafeString = __dependency2__;
628  var Exception = __dependency3__;
629  var Utils = __dependency4__;
630  var runtime = __dependency5__;
631
632  // For compatibility and usage outside of module systems, make the Handlebars object a namespace
633  var create = function() {
634    var hb = new base.HandlebarsEnvironment();
635
636    Utils.extend(hb, base);
637    hb.SafeString = SafeString;
638    hb.Exception = Exception;
639    hb.Utils = Utils;
640    hb.escapeExpression = Utils.escapeExpression;
641
642    hb.VM = runtime;
643    hb.template = function(spec) {
644      return runtime.template(spec, hb);
645    };
646
647    return hb;
648  };
649
650  var Handlebars = create();
651  Handlebars.create = create;
652
653  Handlebars['default'] = Handlebars;
654
655  __exports__ = Handlebars;
656  return __exports__;
657})(__module2__, __module4__, __module5__, __module3__, __module6__);
658
659// handlebars/compiler/ast.js
660var __module7__ = (function(__dependency1__) {
661  "use strict";
662  var __exports__;
663  var Exception = __dependency1__;
664
665  function LocationInfo(locInfo) {
666    locInfo = locInfo || {};
667    this.firstLine   = locInfo.first_line;
668    this.firstColumn = locInfo.first_column;
669    this.lastColumn  = locInfo.last_column;
670    this.lastLine    = locInfo.last_line;
671  }
672
673  var AST = {
674    ProgramNode: function(statements, strip, locInfo) {
675      LocationInfo.call(this, locInfo);
676      this.type = "program";
677      this.statements = statements;
678      this.strip = strip;
679    },
680
681    MustacheNode: function(rawParams, hash, open, strip, locInfo) {
682      LocationInfo.call(this, locInfo);
683      this.type = "mustache";
684      this.strip = strip;
685
686      // Open may be a string parsed from the parser or a passed boolean flag
687      if (open != null && open.charAt) {
688        // Must use charAt to support IE pre-10
689        var escapeFlag = open.charAt(3) || open.charAt(2);
690        this.escaped = escapeFlag !== '{' && escapeFlag !== '&';
691      } else {
692        this.escaped = !!open;
693      }
694
695      if (rawParams instanceof AST.SexprNode) {
696        this.sexpr = rawParams;
697      } else {
698        // Support old AST API
699        this.sexpr = new AST.SexprNode(rawParams, hash);
700      }
701
702      // Support old AST API that stored this info in MustacheNode
703      this.id = this.sexpr.id;
704      this.params = this.sexpr.params;
705      this.hash = this.sexpr.hash;
706      this.eligibleHelper = this.sexpr.eligibleHelper;
707      this.isHelper = this.sexpr.isHelper;
708    },
709
710    SexprNode: function(rawParams, hash, locInfo) {
711      LocationInfo.call(this, locInfo);
712
713      this.type = "sexpr";
714      this.hash = hash;
715
716      var id = this.id = rawParams[0];
717      var params = this.params = rawParams.slice(1);
718
719      // a mustache is definitely a helper if:
720      // * it is an eligible helper, and
721      // * it has at least one parameter or hash segment
722      this.isHelper = !!(params.length || hash);
723
724      // a mustache is an eligible helper if:
725      // * its id is simple (a single part, not `this` or `..`)
726      this.eligibleHelper = this.isHelper || id.isSimple;
727
728      // if a mustache is an eligible helper but not a definite
729      // helper, it is ambiguous, and will be resolved in a later
730      // pass or at runtime.
731    },
732
733    PartialNode: function(partialName, context, hash, strip, locInfo) {
734      LocationInfo.call(this, locInfo);
735      this.type         = "partial";
736      this.partialName  = partialName;
737      this.context      = context;
738      this.hash = hash;
739      this.strip = strip;
740
741      this.strip.inlineStandalone = true;
742    },
743
744    BlockNode: function(mustache, program, inverse, strip, locInfo) {
745      LocationInfo.call(this, locInfo);
746
747      this.type = 'block';
748      this.mustache = mustache;
749      this.program  = program;
750      this.inverse  = inverse;
751      this.strip = strip;
752
753      if (inverse && !program) {
754        this.isInverse = true;
755      }
756    },
757
758    RawBlockNode: function(mustache, content, close, locInfo) {
759      LocationInfo.call(this, locInfo);
760
761      if (mustache.sexpr.id.original !== close) {
762        throw new Exception(mustache.sexpr.id.original + " doesn't match " + close, this);
763      }
764
765      content = new AST.ContentNode(content, locInfo);
766
767      this.type = 'block';
768      this.mustache = mustache;
769      this.program = new AST.ProgramNode([content], {}, locInfo);
770    },
771
772    ContentNode: function(string, locInfo) {
773      LocationInfo.call(this, locInfo);
774      this.type = "content";
775      this.original = this.string = string;
776    },
777
778    HashNode: function(pairs, locInfo) {
779      LocationInfo.call(this, locInfo);
780      this.type = "hash";
781      this.pairs = pairs;
782    },
783
784    IdNode: function(parts, locInfo) {
785      LocationInfo.call(this, locInfo);
786      this.type = "ID";
787
788      var original = "",
789          dig = [],
790          depth = 0,
791          depthString = '';
792
793      for(var i=0,l=parts.length; i<l; i++) {
794        var part = parts[i].part;
795        original += (parts[i].separator || '') + part;
796
797        if (part === ".." || part === "." || part === "this") {
798          if (dig.length > 0) {
799            throw new Exception("Invalid path: " + original, this);
800          } else if (part === "..") {
801            depth++;
802            depthString += '../';
803          } else {
804            this.isScoped = true;
805          }
806        } else {
807          dig.push(part);
808        }
809      }
810
811      this.original = original;
812      this.parts    = dig;
813      this.string   = dig.join('.');
814      this.depth    = depth;
815      this.idName   = depthString + this.string;
816
817      // an ID is simple if it only has one part, and that part is not
818      // `..` or `this`.
819      this.isSimple = parts.length === 1 && !this.isScoped && depth === 0;
820
821      this.stringModeValue = this.string;
822    },
823
824    PartialNameNode: function(name, locInfo) {
825      LocationInfo.call(this, locInfo);
826      this.type = "PARTIAL_NAME";
827      this.name = name.original;
828    },
829
830    DataNode: function(id, locInfo) {
831      LocationInfo.call(this, locInfo);
832      this.type = "DATA";
833      this.id = id;
834      this.stringModeValue = id.stringModeValue;
835      this.idName = '@' + id.stringModeValue;
836    },
837
838    StringNode: function(string, locInfo) {
839      LocationInfo.call(this, locInfo);
840      this.type = "STRING";
841      this.original =
842        this.string =
843        this.stringModeValue = string;
844    },
845
846    NumberNode: function(number, locInfo) {
847      LocationInfo.call(this, locInfo);
848      this.type = "NUMBER";
849      this.original =
850        this.number = number;
851      this.stringModeValue = Number(number);
852    },
853
854    BooleanNode: function(bool, locInfo) {
855      LocationInfo.call(this, locInfo);
856      this.type = "BOOLEAN";
857      this.bool = bool;
858      this.stringModeValue = bool === "true";
859    },
860
861    CommentNode: function(comment, locInfo) {
862      LocationInfo.call(this, locInfo);
863      this.type = "comment";
864      this.comment = comment;
865
866      this.strip = {
867        inlineStandalone: true
868      };
869    }
870  };
871
872
873  // Must be exported as an object rather than the root of the module as the jison lexer
874  // most modify the object to operate properly.
875  __exports__ = AST;
876  return __exports__;
877})(__module5__);
878
879// handlebars/compiler/parser.js
880var __module9__ = (function() {
881  "use strict";
882  var __exports__;
883  /* jshint ignore:start */
884  /* istanbul ignore next */
885  /* Jison generated parser */
886  var handlebars = (function(){
887  var parser = {trace: function trace() { },
888  yy: {},
889  symbols_: {"error":2,"root":3,"program":4,"EOF":5,"program_repetition0":6,"statement":7,"mustache":8,"block":9,"rawBlock":10,"partial":11,"CONTENT":12,"COMMENT":13,"openRawBlock":14,"END_RAW_BLOCK":15,"OPEN_RAW_BLOCK":16,"sexpr":17,"CLOSE_RAW_BLOCK":18,"openBlock":19,"block_option0":20,"closeBlock":21,"openInverse":22,"block_option1":23,"OPEN_BLOCK":24,"CLOSE":25,"OPEN_INVERSE":26,"inverseAndProgram":27,"INVERSE":28,"OPEN_ENDBLOCK":29,"path":30,"OPEN":31,"OPEN_UNESCAPED":32,"CLOSE_UNESCAPED":33,"OPEN_PARTIAL":34,"partialName":35,"param":36,"partial_option0":37,"partial_option1":38,"sexpr_repetition0":39,"sexpr_option0":40,"dataName":41,"STRING":42,"NUMBER":43,"BOOLEAN":44,"OPEN_SEXPR":45,"CLOSE_SEXPR":46,"hash":47,"hash_repetition_plus0":48,"hashSegment":49,"ID":50,"EQUALS":51,"DATA":52,"pathSegments":53,"SEP":54,"$accept":0,"$end":1},
890  terminals_: {2:"error",5:"EOF",12:"CONTENT",13:"COMMENT",15:"END_RAW_BLOCK",16:"OPEN_RAW_BLOCK",18:"CLOSE_RAW_BLOCK",24:"OPEN_BLOCK",25:"CLOSE",26:"OPEN_INVERSE",28:"INVERSE",29:"OPEN_ENDBLOCK",31:"OPEN",32:"OPEN_UNESCAPED",33:"CLOSE_UNESCAPED",34:"OPEN_PARTIAL",42:"STRING",43:"NUMBER",44:"BOOLEAN",45:"OPEN_SEXPR",46:"CLOSE_SEXPR",50:"ID",51:"EQUALS",52:"DATA",54:"SEP"},
891  productions_: [0,[3,2],[4,1],[7,1],[7,1],[7,1],[7,1],[7,1],[7,1],[10,3],[14,3],[9,4],[9,4],[19,3],[22,3],[27,2],[21,3],[8,3],[8,3],[11,5],[11,4],[17,3],[17,1],[36,1],[36,1],[36,1],[36,1],[36,1],[36,3],[47,1],[49,3],[35,1],[35,1],[35,1],[41,2],[30,1],[53,3],[53,1],[6,0],[6,2],[20,0],[20,1],[23,0],[23,1],[37,0],[37,1],[38,0],[38,1],[39,0],[39,2],[40,0],[40,1],[48,1],[48,2]],
892  performAction: function anonymous(yytext,yyleng,yylineno,yy,yystate,$$,_$) {
893
894  var $0 = $$.length - 1;
895  switch (yystate) {
896  case 1: yy.prepareProgram($$[$0-1].statements, true); return $$[$0-1];
897  break;
898  case 2:this.$ = new yy.ProgramNode(yy.prepareProgram($$[$0]), {}, this._$);
899  break;
900  case 3:this.$ = $$[$0];
901  break;
902  case 4:this.$ = $$[$0];
903  break;
904  case 5:this.$ = $$[$0];
905  break;
906  case 6:this.$ = $$[$0];
907  break;
908  case 7:this.$ = new yy.ContentNode($$[$0], this._$);
909  break;
910  case 8:this.$ = new yy.CommentNode($$[$0], this._$);
911  break;
912  case 9:this.$ = new yy.RawBlockNode($$[$0-2], $$[$0-1], $$[$0], this._$);
913  break;
914  case 10:this.$ = new yy.MustacheNode($$[$0-1], null, '', '', this._$);
915  break;
916  case 11:this.$ = yy.prepareBlock($$[$0-3], $$[$0-2], $$[$0-1], $$[$0], false, this._$);
917  break;
918  case 12:this.$ = yy.prepareBlock($$[$0-3], $$[$0-2], $$[$0-1], $$[$0], true, this._$);
919  break;
920  case 13:this.$ = new yy.MustacheNode($$[$0-1], null, $$[$0-2], yy.stripFlags($$[$0-2], $$[$0]), this._$);
921  break;
922  case 14:this.$ = new yy.MustacheNode($$[$0-1], null, $$[$0-2], yy.stripFlags($$[$0-2], $$[$0]), this._$);
923  break;
924  case 15:this.$ = { strip: yy.stripFlags($$[$0-1], $$[$0-1]), program: $$[$0] };
925  break;
926  case 16:this.$ = {path: $$[$0-1], strip: yy.stripFlags($$[$0-2], $$[$0])};
927  break;
928  case 17:this.$ = new yy.MustacheNode($$[$0-1], null, $$[$0-2], yy.stripFlags($$[$0-2], $$[$0]), this._$);
929  break;
930  case 18:this.$ = new yy.MustacheNode($$[$0-1], null, $$[$0-2], yy.stripFlags($$[$0-2], $$[$0]), this._$);
931  break;
932  case 19:this.$ = new yy.PartialNode($$[$0-3], $$[$0-2], $$[$0-1], yy.stripFlags($$[$0-4], $$[$0]), this._$);
933  break;
934  case 20:this.$ = new yy.PartialNode($$[$0-2], undefined, $$[$0-1], yy.stripFlags($$[$0-3], $$[$0]), this._$);
935  break;
936  case 21:this.$ = new yy.SexprNode([$$[$0-2]].concat($$[$0-1]), $$[$0], this._$);
937  break;
938  case 22:this.$ = new yy.SexprNode([$$[$0]], null, this._$);
939  break;
940  case 23:this.$ = $$[$0];
941  break;
942  case 24:this.$ = new yy.StringNode($$[$0], this._$);
943  break;
944  case 25:this.$ = new yy.NumberNode($$[$0], this._$);
945  break;
946  case 26:this.$ = new yy.BooleanNode($$[$0], this._$);
947  break;
948  case 27:this.$ = $$[$0];
949  break;
950  case 28:$$[$0-1].isHelper = true; this.$ = $$[$0-1];
951  break;
952  case 29:this.$ = new yy.HashNode($$[$0], this._$);
953  break;
954  case 30:this.$ = [$$[$0-2], $$[$0]];
955  break;
956  case 31:this.$ = new yy.PartialNameNode($$[$0], this._$);
957  break;
958  case 32:this.$ = new yy.PartialNameNode(new yy.StringNode($$[$0], this._$), this._$);
959  break;
960  case 33:this.$ = new yy.PartialNameNode(new yy.NumberNode($$[$0], this._$));
961  break;
962  case 34:this.$ = new yy.DataNode($$[$0], this._$);
963  break;
964  case 35:this.$ = new yy.IdNode($$[$0], this._$);
965  break;
966  case 36: $$[$0-2].push({part: $$[$0], separator: $$[$0-1]}); this.$ = $$[$0-2];
967  break;
968  case 37:this.$ = [{part: $$[$0]}];
969  break;
970  case 38:this.$ = [];
971  break;
972  case 39:$$[$0-1].push($$[$0]);
973  break;
974  case 48:this.$ = [];
975  break;
976  case 49:$$[$0-1].push($$[$0]);
977  break;
978  case 52:this.$ = [$$[$0]];
979  break;
980  case 53:$$[$0-1].push($$[$0]);
981  break;
982  }
983  },
984  table: [{3:1,4:2,5:[2,38],6:3,12:[2,38],13:[2,38],16:[2,38],24:[2,38],26:[2,38],31:[2,38],32:[2,38],34:[2,38]},{1:[3]},{5:[1,4]},{5:[2,2],7:5,8:6,9:7,10:8,11:9,12:[1,10],13:[1,11],14:16,16:[1,20],19:14,22:15,24:[1,18],26:[1,19],28:[2,2],29:[2,2],31:[1,12],32:[1,13],34:[1,17]},{1:[2,1]},{5:[2,39],12:[2,39],13:[2,39],16:[2,39],24:[2,39],26:[2,39],28:[2,39],29:[2,39],31:[2,39],32:[2,39],34:[2,39]},{5:[2,3],12:[2,3],13:[2,3],16:[2,3],24:[2,3],26:[2,3],28:[2,3],29:[2,3],31:[2,3],32:[2,3],34:[2,3]},{5:[2,4],12:[2,4],13:[2,4],16:[2,4],24:[2,4],26:[2,4],28:[2,4],29:[2,4],31:[2,4],32:[2,4],34:[2,4]},{5:[2,5],12:[2,5],13:[2,5],16:[2,5],24:[2,5],26:[2,5],28:[2,5],29:[2,5],31:[2,5],32:[2,5],34:[2,5]},{5:[2,6],12:[2,6],13:[2,6],16:[2,6],24:[2,6],26:[2,6],28:[2,6],29:[2,6],31:[2,6],32:[2,6],34:[2,6]},{5:[2,7],12:[2,7],13:[2,7],16:[2,7],24:[2,7],26:[2,7],28:[2,7],29:[2,7],31:[2,7],32:[2,7],34:[2,7]},{5:[2,8],12:[2,8],13:[2,8],16:[2,8],24:[2,8],26:[2,8],28:[2,8],29:[2,8],31:[2,8],32:[2,8],34:[2,8]},{17:21,30:22,41:23,50:[1,26],52:[1,25],53:24},{17:27,30:22,41:23,50:[1,26],52:[1,25],53:24},{4:28,6:3,12:[2,38],13:[2,38],16:[2,38],24:[2,38],26:[2,38],28:[2,38],29:[2,38],31:[2,38],32:[2,38],34:[2,38]},{4:29,6:3,12:[2,38],13:[2,38],16:[2,38],24:[2,38],26:[2,38],28:[2,38],29:[2,38],31:[2,38],32:[2,38],34:[2,38]},{12:[1,30]},{30:32,35:31,42:[1,33],43:[1,34],50:[1,26],53:24},{17:35,30:22,41:23,50:[1,26],52:[1,25],53:24},{17:36,30:22,41:23,50:[1,26],52:[1,25],53:24},{17:37,30:22,41:23,50:[1,26],52:[1,25],53:24},{25:[1,38]},{18:[2,48],25:[2,48],33:[2,48],39:39,42:[2,48],43:[2,48],44:[2,48],45:[2,48],46:[2,48],50:[2,48],52:[2,48]},{18:[2,22],25:[2,22],33:[2,22],46:[2,22]},{18:[2,35],25:[2,35],33:[2,35],42:[2,35],43:[2,35],44:[2,35],45:[2,35],46:[2,35],50:[2,35],52:[2,35],54:[1,40]},{30:41,50:[1,26],53:24},{18:[2,37],25:[2,37],33:[2,37],42:[2,37],43:[2,37],44:[2,37],45:[2,37],46:[2,37],50:[2,37],52:[2,37],54:[2,37]},{33:[1,42]},{20:43,27:44,28:[1,45],29:[2,40]},{23:46,27:47,28:[1,45],29:[2,42]},{15:[1,48]},{25:[2,46],30:51,36:49,38:50,41:55,42:[1,52],43:[1,53],44:[1,54],45:[1,56],47:57,48:58,49:60,50:[1,59],52:[1,25],53:24},{25:[2,31],42:[2,31],43:[2,31],44:[2,31],45:[2,31],50:[2,31],52:[2,31]},{25:[2,32],42:[2,32],43:[2,32],44:[2,32],45:[2,32],50:[2,32],52:[2,32]},{25:[2,33],42:[2,33],43:[2,33],44:[2,33],45:[2,33],50:[2,33],52:[2,33]},{25:[1,61]},{25:[1,62]},{18:[1,63]},{5:[2,17],12:[2,17],13:[2,17],16:[2,17],24:[2,17],26:[2,17],28:[2,17],29:[2,17],31:[2,17],32:[2,17],34:[2,17]},{18:[2,50],25:[2,50],30:51,33:[2,50],36:65,40:64,41:55,42:[1,52],43:[1,53],44:[1,54],45:[1,56],46:[2,50],47:66,48:58,49:60,50:[1,59],52:[1,25],53:24},{50:[1,67]},{18:[2,34],25:[2,34],33:[2,34],42:[2,34],43:[2,34],44:[2,34],45:[2,34],46:[2,34],50:[2,34],52:[2,34]},{5:[2,18],12:[2,18],13:[2,18],16:[2,18],24:[2,18],26:[2,18],28:[2,18],29:[2,18],31:[2,18],32:[2,18],34:[2,18]},{21:68,29:[1,69]},{29:[2,41]},{4:70,6:3,12:[2,38],13:[2,38],16:[2,38],24:[2,38],26:[2,38],29:[2,38],31:[2,38],32:[2,38],34:[2,38]},{21:71,29:[1,69]},{29:[2,43]},{5:[2,9],12:[2,9],13:[2,9],16:[2,9],24:[2,9],26:[2,9],28:[2,9],29:[2,9],31:[2,9],32:[2,9],34:[2,9]},{25:[2,44],37:72,47:73,48:58,49:60,50:[1,74]},{25:[1,75]},{18:[2,23],25:[2,23],33:[2,23],42:[2,23],43:[2,23],44:[2,23],45:[2,23],46:[2,23],50:[2,23],52:[2,23]},{18:[2,24],25:[2,24],33:[2,24],42:[2,24],43:[2,24],44:[2,24],45:[2,24],46:[2,24],50:[2,24],52:[2,24]},{18:[2,25],25:[2,25],33:[2,25],42:[2,25],43:[2,25],44:[2,25],45:[2,25],46:[2,25],50:[2,25],52:[2,25]},{18:[2,26],25:[2,26],33:[2,26],42:[2,26],43:[2,26],44:[2,26],45:[2,26],46:[2,26],50:[2,26],52:[2,26]},{18:[2,27],25:[2,27],33:[2,27],42:[2,27],43:[2,27],44:[2,27],45:[2,27],46:[2,27],50:[2,27],52:[2,27]},{17:76,30:22,41:23,50:[1,26],52:[1,25],53:24},{25:[2,47]},{18:[2,29],25:[2,29],33:[2,29],46:[2,29],49:77,50:[1,74]},{18:[2,37],25:[2,37],33:[2,37],42:[2,37],43:[2,37],44:[2,37],45:[2,37],46:[2,37],50:[2,37],51:[1,78],52:[2,37],54:[2,37]},{18:[2,52],25:[2,52],33:[2,52],46:[2,52],50:[2,52]},{12:[2,13],13:[2,13],16:[2,13],24:[2,13],26:[2,13],28:[2,13],29:[2,13],31:[2,13],32:[2,13],34:[2,13]},{12:[2,14],13:[2,14],16:[2,14],24:[2,14],26:[2,14],28:[2,14],29:[2,14],31:[2,14],32:[2,14],34:[2,14]},{12:[2,10]},{18:[2,21],25:[2,21],33:[2,21],46:[2,21]},{18:[2,49],25:[2,49],33:[2,49],42:[2,49],43:[2,49],44:[2,49],45:[2,49],46:[2,49],50:[2,49],52:[2,49]},{18:[2,51],25:[2,51],33:[2,51],46:[2,51]},{18:[2,36],25:[2,36],33:[2,36],42:[2,36],43:[2,36],44:[2,36],45:[2,36],46:[2,36],50:[2,36],52:[2,36],54:[2,36]},{5:[2,11],12:[2,11],13:[2,11],16:[2,11],24:[2,11],26:[2,11],28:[2,11],29:[2,11],31:[2,11],32:[2,11],34:[2,11]},{30:79,50:[1,26],53:24},{29:[2,15]},{5:[2,12],12:[2,12],13:[2,12],16:[2,12],24:[2,12],26:[2,12],28:[2,12],29:[2,12],31:[2,12],32:[2,12],34:[2,12]},{25:[1,80]},{25:[2,45]},{51:[1,78]},{5:[2,20],12:[2,20],13:[2,20],16:[2,20],24:[2,20],26:[2,20],28:[2,20],29:[2,20],31:[2,20],32:[2,20],34:[2,20]},{46:[1,81]},{18:[2,53],25:[2,53],33:[2,53],46:[2,53],50:[2,53]},{30:51,36:82,41:55,42:[1,52],43:[1,53],44:[1,54],45:[1,56],50:[1,26],52:[1,25],53:24},{25:[1,83]},{5:[2,19],12:[2,19],13:[2,19],16:[2,19],24:[2,19],26:[2,19],28:[2,19],29:[2,19],31:[2,19],32:[2,19],34:[2,19]},{18:[2,28],25:[2,28],33:[2,28],42:[2,28],43:[2,28],44:[2,28],45:[2,28],46:[2,28],50:[2,28],52:[2,28]},{18:[2,30],25:[2,30],33:[2,30],46:[2,30],50:[2,30]},{5:[2,16],12:[2,16],13:[2,16],16:[2,16],24:[2,16],26:[2,16],28:[2,16],29:[2,16],31:[2,16],32:[2,16],34:[2,16]}],
985  defaultActions: {4:[2,1],44:[2,41],47:[2,43],57:[2,47],63:[2,10],70:[2,15],73:[2,45]},
986  parseError: function parseError(str, hash) {
987      throw new Error(str);
988  },
989  parse: function parse(input) {
990      var self = this, stack = [0], vstack = [null], lstack = [], table = this.table, yytext = "", yylineno = 0, yyleng = 0, recovering = 0, TERROR = 2, EOF = 1;
991      this.lexer.setInput(input);
992      this.lexer.yy = this.yy;
993      this.yy.lexer = this.lexer;
994      this.yy.parser = this;
995      if (typeof this.lexer.yylloc == "undefined")
996          this.lexer.yylloc = {};
997      var yyloc = this.lexer.yylloc;
998      lstack.push(yyloc);
999      var ranges = this.lexer.options && this.lexer.options.ranges;
1000      if (typeof this.yy.parseError === "function")
1001          this.parseError = this.yy.parseError;
1002      function popStack(n) {
1003          stack.length = stack.length - 2 * n;
1004          vstack.length = vstack.length - n;
1005          lstack.length = lstack.length - n;
1006      }
1007      function lex() {
1008          var token;
1009          token = self.lexer.lex() || 1;
1010          if (typeof token !== "number") {
1011              token = self.symbols_[token] || token;
1012          }
1013          return token;
1014      }
1015      var symbol, preErrorSymbol, state, action, a, r, yyval = {}, p, len, newState, expected;
1016      while (true) {
1017          state = stack[stack.length - 1];
1018          if (this.defaultActions[state]) {
1019              action = this.defaultActions[state];
1020          } else {
1021              if (symbol === null || typeof symbol == "undefined") {
1022                  symbol = lex();
1023              }
1024              action = table[state] && table[state][symbol];
1025          }
1026          if (typeof action === "undefined" || !action.length || !action[0]) {
1027              var errStr = "";
1028              if (!recovering) {
1029                  expected = [];
1030                  for (p in table[state])
1031                      if (this.terminals_[p] && p > 2) {
1032                          expected.push("'" + this.terminals_[p] + "'");
1033                      }
1034                  if (this.lexer.showPosition) {
1035                      errStr = "Parse error on line " + (yylineno + 1) + ":\n" + this.lexer.showPosition() + "\nExpecting " + expected.join(", ") + ", got '" + (this.terminals_[symbol] || symbol) + "'";
1036                  } else {
1037                      errStr = "Parse error on line " + (yylineno + 1) + ": Unexpected " + (symbol == 1?"end of input":"'" + (this.terminals_[symbol] || symbol) + "'");
1038                  }
1039                  this.parseError(errStr, {text: this.lexer.match, token: this.terminals_[symbol] || symbol, line: this.lexer.yylineno, loc: yyloc, expected: expected});
1040              }
1041          }
1042          if (action[0] instanceof Array && action.length > 1) {
1043              throw new Error("Parse Error: multiple actions possible at state: " + state + ", token: " + symbol);
1044          }
1045          switch (action[0]) {
1046          case 1:
1047              stack.push(symbol);
1048              vstack.push(this.lexer.yytext);
1049              lstack.push(this.lexer.yylloc);
1050              stack.push(action[1]);
1051              symbol = null;
1052              if (!preErrorSymbol) {
1053                  yyleng = this.lexer.yyleng;
1054                  yytext = this.lexer.yytext;
1055                  yylineno = this.lexer.yylineno;
1056                  yyloc = this.lexer.yylloc;
1057                  if (recovering > 0)
1058                      recovering--;
1059              } else {
1060                  symbol = preErrorSymbol;
1061                  preErrorSymbol = null;
1062              }
1063              break;
1064          case 2:
1065              len = this.productions_[action[1]][1];
1066              yyval.$ = vstack[vstack.length - len];
1067              yyval._$ = {first_line: lstack[lstack.length - (len || 1)].first_line, last_line: lstack[lstack.length - 1].last_line, first_column: lstack[lstack.length - (len || 1)].first_column, last_column: lstack[lstack.length - 1].last_column};
1068              if (ranges) {
1069                  yyval._$.range = [lstack[lstack.length - (len || 1)].range[0], lstack[lstack.length - 1].range[1]];
1070              }
1071              r = this.performAction.call(yyval, yytext, yyleng, yylineno, this.yy, action[1], vstack, lstack);
1072              if (typeof r !== "undefined") {
1073                  return r;
1074              }
1075              if (len) {
1076                  stack = stack.slice(0, -1 * len * 2);
1077                  vstack = vstack.slice(0, -1 * len);
1078                  lstack = lstack.slice(0, -1 * len);
1079              }
1080              stack.push(this.productions_[action[1]][0]);
1081              vstack.push(yyval.$);
1082              lstack.push(yyval._$);
1083              newState = table[stack[stack.length - 2]][stack[stack.length - 1]];
1084              stack.push(newState);
1085              break;
1086          case 3:
1087              return true;
1088          }
1089      }
1090      return true;
1091  }
1092  };
1093  /* Jison generated lexer */
1094  var lexer = (function(){
1095  var lexer = ({EOF:1,
1096  parseError:function parseError(str, hash) {
1097          if (this.yy.parser) {
1098              this.yy.parser.parseError(str, hash);
1099          } else {
1100              throw new Error(str);
1101          }
1102      },
1103  setInput:function (input) {
1104          this._input = input;
1105          this._more = this._less = this.done = false;
1106          this.yylineno = this.yyleng = 0;
1107          this.yytext = this.matched = this.match = '';
1108          this.conditionStack = ['INITIAL'];
1109          this.yylloc = {first_line:1,first_column:0,last_line:1,last_column:0};
1110          if (this.options.ranges) this.yylloc.range = [0,0];
1111          this.offset = 0;
1112          return this;
1113      },
1114  input:function () {
1115          var ch = this._input[0];
1116          this.yytext += ch;
1117          this.yyleng++;
1118          this.offset++;
1119          this.match += ch;
1120          this.matched += ch;
1121          var lines = ch.match(/(?:\r\n?|\n).*/g);
1122          if (lines) {
1123              this.yylineno++;
1124              this.yylloc.last_line++;
1125          } else {
1126              this.yylloc.last_column++;
1127          }
1128          if (this.options.ranges) this.yylloc.range[1]++;
1129
1130          this._input = this._input.slice(1);
1131          return ch;
1132      },
1133  unput:function (ch) {
1134          var len = ch.length;
1135          var lines = ch.split(/(?:\r\n?|\n)/g);
1136
1137          this._input = ch + this._input;
1138          this.yytext = this.yytext.substr(0, this.yytext.length-len-1);
1139          //this.yyleng -= len;
1140          this.offset -= len;
1141          var oldLines = this.match.split(/(?:\r\n?|\n)/g);
1142          this.match = this.match.substr(0, this.match.length-1);
1143          this.matched = this.matched.substr(0, this.matched.length-1);
1144
1145          if (lines.length-1) this.yylineno -= lines.length-1;
1146          var r = this.yylloc.range;
1147
1148          this.yylloc = {first_line: this.yylloc.first_line,
1149            last_line: this.yylineno+1,
1150            first_column: this.yylloc.first_column,
1151            last_column: lines ?
1152                (lines.length === oldLines.length ? this.yylloc.first_column : 0) + oldLines[oldLines.length - lines.length].length - lines[0].length:
1153                this.yylloc.first_column - len
1154            };
1155
1156          if (this.options.ranges) {
1157              this.yylloc.range = [r[0], r[0] + this.yyleng - len];
1158          }
1159          return this;
1160      },
1161  more:function () {
1162          this._more = true;
1163          return this;
1164      },
1165  less:function (n) {
1166          this.unput(this.match.slice(n));
1167      },
1168  pastInput:function () {
1169          var past = this.matched.substr(0, this.matched.length - this.match.length);
1170          return (past.length > 20 ? '...':'') + past.substr(-20).replace(/\n/g, "");
1171      },
1172  upcomingInput:function () {
1173          var next = this.match;
1174          if (next.length < 20) {
1175              next += this._input.substr(0, 20-next.length);
1176          }
1177          return (next.substr(0,20)+(next.length > 20 ? '...':'')).replace(/\n/g, "");
1178      },
1179  showPosition:function () {
1180          var pre = this.pastInput();
1181          var c = new Array(pre.length + 1).join("-");
1182          return pre + this.upcomingInput() + "\n" + c+"^";
1183      },
1184  next:function () {
1185          if (this.done) {
1186              return this.EOF;
1187          }
1188          if (!this._input) this.done = true;
1189
1190          var token,
1191              match,
1192              tempMatch,
1193              index,
1194              col,
1195              lines;
1196          if (!this._more) {
1197              this.yytext = '';
1198              this.match = '';
1199          }
1200          var rules = this._currentRules();
1201          for (var i=0;i < rules.length; i++) {
1202              tempMatch = this._input.match(this.rules[rules[i]]);
1203              if (tempMatch && (!match || tempMatch[0].length > match[0].length)) {
1204                  match = tempMatch;
1205                  index = i;
1206                  if (!this.options.flex) break;
1207              }
1208          }
1209          if (match) {
1210              lines = match[0].match(/(?:\r\n?|\n).*/g);
1211              if (lines) this.yylineno += lines.length;
1212              this.yylloc = {first_line: this.yylloc.last_line,
1213                             last_line: this.yylineno+1,
1214                             first_column: this.yylloc.last_column,
1215                             last_column: lines ? lines[lines.length-1].length-lines[lines.length-1].match(/\r?\n?/)[0].length : this.yylloc.last_column + match[0].length};
1216              this.yytext += match[0];
1217              this.match += match[0];
1218              this.matches = match;
1219              this.yyleng = this.yytext.length;
1220              if (this.options.ranges) {
1221                  this.yylloc.range = [this.offset, this.offset += this.yyleng];
1222              }
1223              this._more = false;
1224              this._input = this._input.slice(match[0].length);
1225              this.matched += match[0];
1226              token = this.performAction.call(this, this.yy, this, rules[index],this.conditionStack[this.conditionStack.length-1]);
1227              if (this.done && this._input) this.done = false;
1228              if (token) return token;
1229              else return;
1230          }
1231          if (this._input === "") {
1232              return this.EOF;
1233          } else {
1234              return this.parseError('Lexical error on line '+(this.yylineno+1)+'. Unrecognized text.\n'+this.showPosition(),
1235                      {text: "", token: null, line: this.yylineno});
1236          }
1237      },
1238  lex:function lex() {
1239          var r = this.next();
1240          if (typeof r !== 'undefined') {
1241              return r;
1242          } else {
1243              return this.lex();
1244          }
1245      },
1246  begin:function begin(condition) {
1247          this.conditionStack.push(condition);
1248      },
1249  popState:function popState() {
1250          return this.conditionStack.pop();
1251      },
1252  _currentRules:function _currentRules() {
1253          return this.conditions[this.conditionStack[this.conditionStack.length-1]].rules;
1254      },
1255  topState:function () {
1256          return this.conditionStack[this.conditionStack.length-2];
1257      },
1258  pushState:function begin(condition) {
1259          this.begin(condition);
1260      }});
1261  lexer.options = {};
1262  lexer.performAction = function anonymous(yy,yy_,$avoiding_name_collisions,YY_START) {
1263
1264
1265  function strip(start, end) {
1266    return yy_.yytext = yy_.yytext.substr(start, yy_.yyleng-end);
1267  }
1268
1269
1270  var YYSTATE=YY_START
1271  switch($avoiding_name_collisions) {
1272  case 0:
1273                                     if(yy_.yytext.slice(-2) === "\\\\") {
1274                                       strip(0,1);
1275                                       this.begin("mu");
1276                                     } else if(yy_.yytext.slice(-1) === "\\") {
1277                                       strip(0,1);
1278                                       this.begin("emu");
1279                                     } else {
1280                                       this.begin("mu");
1281                                     }
1282                                     if(yy_.yytext) return 12;
1283                                   
1284  break;
1285  case 1:return 12;
1286  break;
1287  case 2:
1288                                     this.popState();
1289                                     return 12;
1290                                   
1291  break;
1292  case 3:
1293                                    yy_.yytext = yy_.yytext.substr(5, yy_.yyleng-9);
1294                                    this.popState();
1295                                    return 15;
1296                                   
1297  break;
1298  case 4: return 12;
1299  break;
1300  case 5:strip(0,4); this.popState(); return 13;
1301  break;
1302  case 6:return 45;
1303  break;
1304  case 7:return 46;
1305  break;
1306  case 8: return 16;
1307  break;
1308  case 9:
1309                                    this.popState();
1310                                    this.begin('raw');
1311                                    return 18;
1312                                   
1313  break;
1314  case 10:return 34;
1315  break;
1316  case 11:return 24;
1317  break;
1318  case 12:return 29;
1319  break;
1320  case 13:this.popState(); return 28;
1321  break;
1322  case 14:this.popState(); return 28;
1323  break;
1324  case 15:return 26;
1325  break;
1326  case 16:return 26;
1327  break;
1328  case 17:return 32;
1329  break;
1330  case 18:return 31;
1331  break;
1332  case 19:this.popState(); this.begin('com');
1333  break;
1334  case 20:strip(3,5); this.popState(); return 13;
1335  break;
1336  case 21:return 31;
1337  break;
1338  case 22:return 51;
1339  break;
1340  case 23:return 50;
1341  break;
1342  case 24:return 50;
1343  break;
1344  case 25:return 54;
1345  break;
1346  case 26:// ignore whitespace
1347  break;
1348  case 27:this.popState(); return 33;
1349  break;
1350  case 28:this.popState(); return 25;
1351  break;
1352  case 29:yy_.yytext = strip(1,2).replace(/\\"/g,'"'); return 42;
1353  break;
1354  case 30:yy_.yytext = strip(1,2).replace(/\\'/g,"'"); return 42;
1355  break;
1356  case 31:return 52;
1357  break;
1358  case 32:return 44;
1359  break;
1360  case 33:return 44;
1361  break;
1362  case 34:return 43;
1363  break;
1364  case 35:return 50;
1365  break;
1366  case 36:yy_.yytext = strip(1,2); return 50;
1367  break;
1368  case 37:return 'INVALID';
1369  break;
1370  case 38:return 5;
1371  break;
1372  }
1373  };
1374  lexer.rules = [/^(?:[^\x00]*?(?=(\{\{)))/,/^(?:[^\x00]+)/,/^(?:[^\x00]{2,}?(?=(\{\{|\\\{\{|\\\\\{\{|$)))/,/^(?:\{\{\{\{\/[^\s!"#%-,\.\/;->@\[-\^`\{-~]+(?=[=}\s\/.])\}\}\}\})/,/^(?:[^\x00]*?(?=(\{\{\{\{\/)))/,/^(?:[\s\S]*?--\}\})/,/^(?:\()/,/^(?:\))/,/^(?:\{\{\{\{)/,/^(?:\}\}\}\})/,/^(?:\{\{(~)?>)/,/^(?:\{\{(~)?#)/,/^(?:\{\{(~)?\/)/,/^(?:\{\{(~)?\^\s*(~)?\}\})/,/^(?:\{\{(~)?\s*else\s*(~)?\}\})/,/^(?:\{\{(~)?\^)/,/^(?:\{\{(~)?\s*else\b)/,/^(?:\{\{(~)?\{)/,/^(?:\{\{(~)?&)/,/^(?:\{\{!--)/,/^(?:\{\{![\s\S]*?\}\})/,/^(?:\{\{(~)?)/,/^(?:=)/,/^(?:\.\.)/,/^(?:\.(?=([=~}\s\/.)])))/,/^(?:[\/.])/,/^(?:\s+)/,/^(?:\}(~)?\}\})/,/^(?:(~)?\}\})/,/^(?:"(\\["]|[^"])*")/,/^(?:'(\\[']|[^'])*')/,/^(?:@)/,/^(?:true(?=([~}\s)])))/,/^(?:false(?=([~}\s)])))/,/^(?:-?[0-9]+(?:\.[0-9]+)?(?=([~}\s)])))/,/^(?:([^\s!"#%-,\.\/;->@\[-\^`\{-~]+(?=([=~}\s\/.)]))))/,/^(?:\[[^\]]*\])/,/^(?:.)/,/^(?:$)/];
1375  lexer.conditions = {"mu":{"rules":[6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38],"inclusive":false},"emu":{"rules":[2],"inclusive":false},"com":{"rules":[5],"inclusive":false},"raw":{"rules":[3,4],"inclusive":false},"INITIAL":{"rules":[0,1,38],"inclusive":true}};
1376  return lexer;})()
1377  parser.lexer = lexer;
1378  function Parser () { this.yy = {}; }Parser.prototype = parser;parser.Parser = Parser;
1379  return new Parser;
1380  })();__exports__ = handlebars;
1381  /* jshint ignore:end */
1382  return __exports__;
1383})();
1384
1385// handlebars/compiler/helpers.js
1386var __module10__ = (function(__dependency1__) {
1387  "use strict";
1388  var __exports__ = {};
1389  var Exception = __dependency1__;
1390
1391  function stripFlags(open, close) {
1392    return {
1393      left: open.charAt(2) === '~',
1394      right: close.charAt(close.length-3) === '~'
1395    };
1396  }
1397
1398  __exports__.stripFlags = stripFlags;
1399  function prepareBlock(mustache, program, inverseAndProgram, close, inverted, locInfo) {
1400    /*jshint -W040 */
1401    if (mustache.sexpr.id.original !== close.path.original) {
1402      throw new Exception(mustache.sexpr.id.original + ' doesn\'t match ' + close.path.original, mustache);
1403    }
1404
1405    var inverse = inverseAndProgram && inverseAndProgram.program;
1406
1407    var strip = {
1408      left: mustache.strip.left,
1409      right: close.strip.right,
1410
1411      // Determine the standalone candiacy. Basically flag our content as being possibly standalone
1412      // so our parent can determine if we actually are standalone
1413      openStandalone: isNextWhitespace(program.statements),
1414      closeStandalone: isPrevWhitespace((inverse || program).statements)
1415    };
1416
1417    if (mustache.strip.right) {
1418      omitRight(program.statements, null, true);
1419    }
1420
1421    if (inverse) {
1422      var inverseStrip = inverseAndProgram.strip;
1423
1424      if (inverseStrip.left) {
1425        omitLeft(program.statements, null, true);
1426      }
1427      if (inverseStrip.right) {
1428        omitRight(inverse.statements, null, true);
1429      }
1430      if (close.strip.left) {
1431        omitLeft(inverse.statements, null, true);
1432      }
1433
1434      // Find standalone else statments
1435      if (isPrevWhitespace(program.statements)
1436          && isNextWhitespace(inverse.statements)) {
1437
1438        omitLeft(program.statements);
1439        omitRight(inverse.statements);
1440      }
1441    } else {
1442      if (close.strip.left) {
1443        omitLeft(program.statements, null, true);
1444      }
1445    }
1446
1447    if (inverted) {
1448      return new this.BlockNode(mustache, inverse, program, strip, locInfo);
1449    } else {
1450      return new this.BlockNode(mustache, program, inverse, strip, locInfo);
1451    }
1452  }
1453
1454  __exports__.prepareBlock = prepareBlock;
1455  function prepareProgram(statements, isRoot) {
1456    for (var i = 0, l = statements.length; i < l; i++) {
1457      var current = statements[i],
1458          strip = current.strip;
1459
1460      if (!strip) {
1461        continue;
1462      }
1463
1464      var _isPrevWhitespace = isPrevWhitespace(statements, i, isRoot, current.type === 'partial'),
1465          _isNextWhitespace = isNextWhitespace(statements, i, isRoot),
1466
1467          openStandalone = strip.openStandalone && _isPrevWhitespace,
1468          closeStandalone = strip.closeStandalone && _isNextWhitespace,
1469          inlineStandalone = strip.inlineStandalone && _isPrevWhitespace && _isNextWhitespace;
1470
1471      if (strip.right) {
1472        omitRight(statements, i, true);
1473      }
1474      if (strip.left) {
1475        omitLeft(statements, i, true);
1476      }
1477
1478      if (inlineStandalone) {
1479        omitRight(statements, i);
1480
1481        if (omitLeft(statements, i)) {
1482          // If we are on a standalone node, save the indent info for partials
1483          if (current.type === 'partial') {
1484            current.indent = (/([ \t]+$)/).exec(statements[i-1].original) ? RegExp.$1 : '';
1485          }
1486        }
1487      }
1488      if (openStandalone) {
1489        omitRight((current.program || current.inverse).statements);
1490
1491        // Strip out the previous content node if it's whitespace only
1492        omitLeft(statements, i);
1493      }
1494      if (closeStandalone) {
1495        // Always strip the next node
1496        omitRight(statements, i);
1497
1498        omitLeft((current.inverse || current.program).statements);
1499      }
1500    }
1501
1502    return statements;
1503  }
1504
1505  __exports__.prepareProgram = prepareProgram;function isPrevWhitespace(statements, i, isRoot) {
1506    if (i === undefined) {
1507      i = statements.length;
1508    }
1509
1510    // Nodes that end with newlines are considered whitespace (but are special
1511    // cased for strip operations)
1512    var prev = statements[i-1],
1513        sibling = statements[i-2];
1514    if (!prev) {
1515      return isRoot;
1516    }
1517
1518    if (prev.type === 'content') {
1519      return (sibling || !isRoot ? (/\r?\n\s*?$/) : (/(^|\r?\n)\s*?$/)).test(prev.original);
1520    }
1521  }
1522  function isNextWhitespace(statements, i, isRoot) {
1523    if (i === undefined) {
1524      i = -1;
1525    }
1526
1527    var next = statements[i+1],
1528        sibling = statements[i+2];
1529    if (!next) {
1530      return isRoot;
1531    }
1532
1533    if (next.type === 'content') {
1534      return (sibling || !isRoot ? (/^\s*?\r?\n/) : (/^\s*?(\r?\n|$)/)).test(next.original);
1535    }
1536  }
1537
1538  // Marks the node to the right of the position as omitted.
1539  // I.e. {{foo}}' ' will mark the ' ' node as omitted.
1540  //
1541  // If i is undefined, then the first child will be marked as such.
1542  //
1543  // If mulitple is truthy then all whitespace will be stripped out until non-whitespace
1544  // content is met.
1545  function omitRight(statements, i, multiple) {
1546    var current = statements[i == null ? 0 : i + 1];
1547    if (!current || current.type !== 'content' || (!multiple && current.rightStripped)) {
1548      return;
1549    }
1550
1551    var original = current.string;
1552    current.string = current.string.replace(multiple ? (/^\s+/) : (/^[ \t]*\r?\n?/), '');
1553    current.rightStripped = current.string !== original;
1554  }
1555
1556  // Marks the node to the left of the position as omitted.
1557  // I.e. ' '{{foo}} will mark the ' ' node as omitted.
1558  //
1559  // If i is undefined then the last child will be marked as such.
1560  //
1561  // If mulitple is truthy then all whitespace will be stripped out until non-whitespace
1562  // content is met.
1563  function omitLeft(statements, i, multiple) {
1564    var current = statements[i == null ? statements.length - 1 : i - 1];
1565    if (!current || current.type !== 'content' || (!multiple && current.leftStripped)) {
1566      return;
1567    }
1568
1569    // We omit the last node if it's whitespace only and not preceeded by a non-content node.
1570    var original = current.string;
1571    current.string = current.string.replace(multiple ? (/\s+$/) : (/[ \t]+$/), '');
1572    current.leftStripped = current.string !== original;
1573    return current.leftStripped;
1574  }
1575  return __exports__;
1576})(__module5__);
1577
1578// handlebars/compiler/base.js
1579var __module8__ = (function(__dependency1__, __dependency2__, __dependency3__, __dependency4__) {
1580  "use strict";
1581  var __exports__ = {};
1582  var parser = __dependency1__;
1583  var AST = __dependency2__;
1584  var Helpers = __dependency3__;
1585  var extend = __dependency4__.extend;
1586
1587  __exports__.parser = parser;
1588
1589  var yy = {};
1590  extend(yy, Helpers, AST);
1591
1592  function parse(input) {
1593    // Just return if an already-compile AST was passed in.
1594    if (input.constructor === AST.ProgramNode) { return input; }
1595
1596    parser.yy = yy;
1597
1598    return parser.parse(input);
1599  }
1600
1601  __exports__.parse = parse;
1602  return __exports__;
1603})(__module9__, __module7__, __module10__, __module3__);
1604
1605// handlebars/compiler/compiler.js
1606var __module11__ = (function(__dependency1__, __dependency2__) {
1607  "use strict";
1608  var __exports__ = {};
1609  var Exception = __dependency1__;
1610  var isArray = __dependency2__.isArray;
1611
1612  var slice = [].slice;
1613
1614  function Compiler() {}
1615
1616  __exports__.Compiler = Compiler;// the foundHelper register will disambiguate helper lookup from finding a
1617  // function in a context. This is necessary for mustache compatibility, which
1618  // requires that context functions in blocks are evaluated by blockHelperMissing,
1619  // and then proceed as if the resulting value was provided to blockHelperMissing.
1620
1621  Compiler.prototype = {
1622    compiler: Compiler,
1623
1624    equals: function(other) {
1625      var len = this.opcodes.length;
1626      if (other.opcodes.length !== len) {
1627        return false;
1628      }
1629
1630      for (var i = 0; i < len; i++) {
1631        var opcode = this.opcodes[i],
1632            otherOpcode = other.opcodes[i];
1633        if (opcode.opcode !== otherOpcode.opcode || !argEquals(opcode.args, otherOpcode.args)) {
1634          return false;
1635        }
1636      }
1637
1638      // We know that length is the same between the two arrays because they are directly tied
1639      // to the opcode behavior above.
1640      len = this.children.length;
1641      for (i = 0; i < len; i++) {
1642        if (!this.children[i].equals(other.children[i])) {
1643          return false;
1644        }
1645      }
1646
1647      return true;
1648    },
1649
1650    guid: 0,
1651
1652    compile: function(program, options) {
1653      this.opcodes = [];
1654      this.children = [];
1655      this.depths = {list: []};
1656      this.options = options;
1657      this.stringParams = options.stringParams;
1658      this.trackIds = options.trackIds;
1659
1660      // These changes will propagate to the other compiler components
1661      var knownHelpers = this.options.knownHelpers;
1662      this.options.knownHelpers = {
1663        'helperMissing': true,
1664        'blockHelperMissing': true,
1665        'each': true,
1666        'if': true,
1667        'unless': true,
1668        'with': true,
1669        'log': true,
1670        'lookup': true
1671      };
1672      if (knownHelpers) {
1673        for (var name in knownHelpers) {
1674          this.options.knownHelpers[name] = knownHelpers[name];
1675        }
1676      }
1677
1678      return this.accept(program);
1679    },
1680
1681    accept: function(node) {
1682      return this[node.type](node);
1683    },
1684
1685    program: function(program) {
1686      var statements = program.statements;
1687
1688      for(var i=0, l=statements.length; i<l; i++) {
1689        this.accept(statements[i]);
1690      }
1691      this.isSimple = l === 1;
1692
1693      this.depths.list = this.depths.list.sort(function(a, b) {
1694        return a - b;
1695      });
1696
1697      return this;
1698    },
1699
1700    compileProgram: function(program) {
1701      var result = new this.compiler().compile(program, this.options);
1702      var guid = this.guid++, depth;
1703
1704      this.usePartial = this.usePartial || result.usePartial;
1705
1706      this.children[guid] = result;
1707
1708      for(var i=0, l=result.depths.list.length; i<l; i++) {
1709        depth = result.depths.list[i];
1710
1711        if(depth < 2) { continue; }
1712        else { this.addDepth(depth - 1); }
1713      }
1714
1715      return guid;
1716    },
1717
1718    block: function(block) {
1719      var mustache = block.mustache,
1720          program = block.program,
1721          inverse = block.inverse;
1722
1723      if (program) {
1724        program = this.compileProgram(program);
1725      }
1726
1727      if (inverse) {
1728        inverse = this.compileProgram(inverse);
1729      }
1730
1731      var sexpr = mustache.sexpr;
1732      var type = this.classifySexpr(sexpr);
1733
1734      if (type === "helper") {
1735        this.helperSexpr(sexpr, program, inverse);
1736      } else if (type === "simple") {
1737        this.simpleSexpr(sexpr);
1738
1739        // now that the simple mustache is resolved, we need to
1740        // evaluate it by executing `blockHelperMissing`
1741        this.opcode('pushProgram', program);
1742        this.opcode('pushProgram', inverse);
1743        this.opcode('emptyHash');
1744        this.opcode('blockValue', sexpr.id.original);
1745      } else {
1746        this.ambiguousSexpr(sexpr, program, inverse);
1747
1748        // now that the simple mustache is resolved, we need to
1749        // evaluate it by executing `blockHelperMissing`
1750        this.opcode('pushProgram', program);
1751        this.opcode('pushProgram', inverse);
1752        this.opcode('emptyHash');
1753        this.opcode('ambiguousBlockValue');
1754      }
1755
1756      this.opcode('append');
1757    },
1758
1759    hash: function(hash) {
1760      var pairs = hash.pairs, i, l;
1761
1762      this.opcode('pushHash');
1763
1764      for(i=0, l=pairs.length; i<l; i++) {
1765        this.pushParam(pairs[i][1]);
1766      }
1767      while(i--) {
1768        this.opcode('assignToHash', pairs[i][0]);
1769      }
1770      this.opcode('popHash');
1771    },
1772
1773    partial: function(partial) {
1774      var partialName = partial.partialName;
1775      this.usePartial = true;
1776
1777      if (partial.hash) {
1778        this.accept(partial.hash);
1779      } else {
1780        this.opcode('push', 'undefined');
1781      }
1782
1783      if (partial.context) {
1784        this.accept(partial.context);
1785      } else {
1786        this.opcode('getContext', 0);
1787        this.opcode('pushContext');
1788      }
1789
1790      this.opcode('invokePartial', partialName.name, partial.indent || '');
1791      this.opcode('append');
1792    },
1793
1794    content: function(content) {
1795      if (content.string) {
1796        this.opcode('appendContent', content.string);
1797      }
1798    },
1799
1800    mustache: function(mustache) {
1801      this.sexpr(mustache.sexpr);
1802
1803      if(mustache.escaped && !this.options.noEscape) {
1804        this.opcode('appendEscaped');
1805      } else {
1806        this.opcode('append');
1807      }
1808    },
1809
1810    ambiguousSexpr: function(sexpr, program, inverse) {
1811      var id = sexpr.id,
1812          name = id.parts[0],
1813          isBlock = program != null || inverse != null;
1814
1815      this.opcode('getContext', id.depth);
1816
1817      this.opcode('pushProgram', program);
1818      this.opcode('pushProgram', inverse);
1819
1820      this.ID(id);
1821
1822      this.opcode('invokeAmbiguous', name, isBlock);
1823    },
1824
1825    simpleSexpr: function(sexpr) {
1826      var id = sexpr.id;
1827
1828      if (id.type === 'DATA') {
1829        this.DATA(id);
1830      } else if (id.parts.length) {
1831        this.ID(id);
1832      } else {
1833        // Simplified ID for `this`
1834        this.addDepth(id.depth);
1835        this.opcode('getContext', id.depth);
1836        this.opcode('pushContext');
1837      }
1838
1839      this.opcode('resolvePossibleLambda');
1840    },
1841
1842    helperSexpr: function(sexpr, program, inverse) {
1843      var params = this.setupFullMustacheParams(sexpr, program, inverse),
1844          id = sexpr.id,
1845          name = id.parts[0];
1846
1847      if (this.options.knownHelpers[name]) {
1848        this.opcode('invokeKnownHelper', params.length, name);
1849      } else if (this.options.knownHelpersOnly) {
1850        throw new Exception("You specified knownHelpersOnly, but used the unknown helper " + name, sexpr);
1851      } else {
1852        id.falsy = true;
1853
1854        this.ID(id);
1855        this.opcode('invokeHelper', params.length, id.original, id.isSimple);
1856      }
1857    },
1858
1859    sexpr: function(sexpr) {
1860      var type = this.classifySexpr(sexpr);
1861
1862      if (type === "simple") {
1863        this.simpleSexpr(sexpr);
1864      } else if (type === "helper") {
1865        this.helperSexpr(sexpr);
1866      } else {
1867        this.ambiguousSexpr(sexpr);
1868      }
1869    },
1870
1871    ID: function(id) {
1872      this.addDepth(id.depth);
1873      this.opcode('getContext', id.depth);
1874
1875      var name = id.parts[0];
1876      if (!name) {
1877        // Context reference, i.e. `{{foo .}}` or `{{foo ..}}`
1878        this.opcode('pushContext');
1879      } else {
1880        this.opcode('lookupOnContext', id.parts, id.falsy, id.isScoped);
1881      }
1882    },
1883
1884    DATA: function(data) {
1885      this.options.data = true;
1886      this.opcode('lookupData', data.id.depth, data.id.parts);
1887    },
1888
1889    STRING: function(string) {
1890      this.opcode('pushString', string.string);
1891    },
1892
1893    NUMBER: function(number) {
1894      this.opcode('pushLiteral', number.number);
1895    },
1896
1897    BOOLEAN: function(bool) {
1898      this.opcode('pushLiteral', bool.bool);
1899    },
1900
1901    comment: function() {},
1902
1903    // HELPERS
1904    opcode: function(name) {
1905      this.opcodes.push({ opcode: name, args: slice.call(arguments, 1) });
1906    },
1907
1908    addDepth: function(depth) {
1909      if(depth === 0) { return; }
1910
1911      if(!this.depths[depth]) {
1912        this.depths[depth] = true;
1913        this.depths.list.push(depth);
1914      }
1915    },
1916
1917    classifySexpr: function(sexpr) {
1918      var isHelper   = sexpr.isHelper;
1919      var isEligible = sexpr.eligibleHelper;
1920      var options    = this.options;
1921
1922      // if ambiguous, we can possibly resolve the ambiguity now
1923      // An eligible helper is one that does not have a complex path, i.e. `this.foo`, `../foo` etc.
1924      if (isEligible && !isHelper) {
1925        var name = sexpr.id.parts[0];
1926
1927        if (options.knownHelpers[name]) {
1928          isHelper = true;
1929        } else if (options.knownHelpersOnly) {
1930          isEligible = false;
1931        }
1932      }
1933
1934      if (isHelper) { return "helper"; }
1935      else if (isEligible) { return "ambiguous"; }
1936      else { return "simple"; }
1937    },
1938
1939    pushParams: function(params) {
1940      for(var i=0, l=params.length; i<l; i++) {
1941        this.pushParam(params[i]);
1942      }
1943    },
1944
1945    pushParam: function(val) {
1946      if (this.stringParams) {
1947        if(val.depth) {
1948          this.addDepth(val.depth);
1949        }
1950        this.opcode('getContext', val.depth || 0);
1951        this.opcode('pushStringParam', val.stringModeValue, val.type);
1952
1953        if (val.type === 'sexpr') {
1954          // Subexpressions get evaluated and passed in
1955          // in string params mode.
1956          this.sexpr(val);
1957        }
1958      } else {
1959        if (this.trackIds) {
1960          this.opcode('pushId', val.type, val.idName || val.stringModeValue);
1961        }
1962        this.accept(val);
1963      }
1964    },
1965
1966    setupFullMustacheParams: function(sexpr, program, inverse) {
1967      var params = sexpr.params;
1968      this.pushParams(params);
1969
1970      this.opcode('pushProgram', program);
1971      this.opcode('pushProgram', inverse);
1972
1973      if (sexpr.hash) {
1974        this.hash(sexpr.hash);
1975      } else {
1976        this.opcode('emptyHash');
1977      }
1978
1979      return params;
1980    }
1981  };
1982
1983  function precompile(input, options, env) {
1984    if (input == null || (typeof input !== 'string' && input.constructor !== env.AST.ProgramNode)) {
1985      throw new Exception("You must pass a string or Handlebars AST to Handlebars.precompile. You passed " + input);
1986    }
1987
1988    options = options || {};
1989    if (!('data' in options)) {
1990      options.data = true;
1991    }
1992    if (options.compat) {
1993      options.useDepths = true;
1994    }
1995
1996    var ast = env.parse(input);
1997    var environment = new env.Compiler().compile(ast, options);
1998    return new env.JavaScriptCompiler().compile(environment, options);
1999  }
2000
2001  __exports__.precompile = precompile;function compile(input, options, env) {
2002    if (input == null || (typeof input !== 'string' && input.constructor !== env.AST.ProgramNode)) {
2003      throw new Exception("You must pass a string or Handlebars AST to Handlebars.compile. You passed " + input);
2004    }
2005
2006    options = options || {};
2007
2008    if (!('data' in options)) {
2009      options.data = true;
2010    }
2011    if (options.compat) {
2012      options.useDepths = true;
2013    }
2014
2015    var compiled;
2016
2017    function compileInput() {
2018      var ast = env.parse(input);
2019      var environment = new env.Compiler().compile(ast, options);
2020      var templateSpec = new env.JavaScriptCompiler().compile(environment, options, undefined, true);
2021      return env.template(templateSpec);
2022    }
2023
2024    // Template is only compiled on first use and cached after that point.
2025    var ret = function(context, options) {
2026      if (!compiled) {
2027        compiled = compileInput();
2028      }
2029      return compiled.call(this, context, options);
2030    };
2031    ret._setup = function(options) {
2032      if (!compiled) {
2033        compiled = compileInput();
2034      }
2035      return compiled._setup(options);
2036    };
2037    ret._child = function(i, data, depths) {
2038      if (!compiled) {
2039        compiled = compileInput();
2040      }
2041      return compiled._child(i, data, depths);
2042    };
2043    return ret;
2044  }
2045
2046  __exports__.compile = compile;function argEquals(a, b) {
2047    if (a === b) {
2048      return true;
2049    }
2050
2051    if (isArray(a) && isArray(b) && a.length === b.length) {
2052      for (var i = 0; i < a.length; i++) {
2053        if (!argEquals(a[i], b[i])) {
2054          return false;
2055        }
2056      }
2057      return true;
2058    }
2059  }
2060  return __exports__;
2061})(__module5__, __module3__);
2062
2063// handlebars/compiler/javascript-compiler.js
2064var __module12__ = (function(__dependency1__, __dependency2__) {
2065  "use strict";
2066  var __exports__;
2067  var COMPILER_REVISION = __dependency1__.COMPILER_REVISION;
2068  var REVISION_CHANGES = __dependency1__.REVISION_CHANGES;
2069  var Exception = __dependency2__;
2070
2071  function Literal(value) {
2072    this.value = value;
2073  }
2074
2075  function JavaScriptCompiler() {}
2076
2077  JavaScriptCompiler.prototype = {
2078    // PUBLIC API: You can override these methods in a subclass to provide
2079    // alternative compiled forms for name lookup and buffering semantics
2080    nameLookup: function(parent, name /* , type*/) {
2081      if (JavaScriptCompiler.isValidJavaScriptVariableName(name)) {
2082        return parent + "." + name;
2083      } else {
2084        return parent + "['" + name + "']";
2085      }
2086    },
2087    depthedLookup: function(name) {
2088      this.aliases.lookup = 'this.lookup';
2089
2090      return 'lookup(depths, "' + name + '")';
2091    },
2092
2093    compilerInfo: function() {
2094      var revision = COMPILER_REVISION,
2095          versions = REVISION_CHANGES[revision];
2096      return [revision, versions];
2097    },
2098
2099    appendToBuffer: function(string) {
2100      if (this.environment.isSimple) {
2101        return "return " + string + ";";
2102      } else {
2103        return {
2104          appendToBuffer: true,
2105          content: string,
2106          toString: function() { return "buffer += " + string + ";"; }
2107        };
2108      }
2109    },
2110
2111    initializeBuffer: function() {
2112      return this.quotedString("");
2113    },
2114
2115    namespace: "Handlebars",
2116    // END PUBLIC API
2117
2118    compile: function(environment, options, context, asObject) {
2119      this.environment = environment;
2120      this.options = options;
2121      this.stringParams = this.options.stringParams;
2122      this.trackIds = this.options.trackIds;
2123      this.precompile = !asObject;
2124
2125      this.name = this.environment.name;
2126      this.isChild = !!context;
2127      this.context = context || {
2128        programs: [],
2129        environments: []
2130      };
2131
2132      this.preamble();
2133
2134      this.stackSlot = 0;
2135      this.stackVars = [];
2136      this.aliases = {};
2137      this.registers = { list: [] };
2138      this.hashes = [];
2139      this.compileStack = [];
2140      this.inlineStack = [];
2141
2142      this.compileChildren(environment, options);
2143
2144      this.useDepths = this.useDepths || environment.depths.list.length || this.options.compat;
2145
2146      var opcodes = environment.opcodes,
2147          opcode,
2148          i,
2149          l;
2150
2151      for (i = 0, l = opcodes.length; i < l; i++) {
2152        opcode = opcodes[i];
2153
2154        this[opcode.opcode].apply(this, opcode.args);
2155      }
2156
2157      // Flush any trailing content that might be pending.
2158      this.pushSource('');
2159
2160      /* istanbul ignore next */
2161      if (this.stackSlot || this.inlineStack.length || this.compileStack.length) {
2162        throw new Exception('Compile completed with content left on stack');
2163      }
2164
2165      var fn = this.createFunctionContext(asObject);
2166      if (!this.isChild) {
2167        var ret = {
2168          compiler: this.compilerInfo(),
2169          main: fn
2170        };
2171        var programs = this.context.programs;
2172        for (i = 0, l = programs.length; i < l; i++) {
2173          if (programs[i]) {
2174            ret[i] = programs[i];
2175          }
2176        }
2177
2178        if (this.environment.usePartial) {
2179          ret.usePartial = true;
2180        }
2181        if (this.options.data) {
2182          ret.useData = true;
2183        }
2184        if (this.useDepths) {
2185          ret.useDepths = true;
2186        }
2187        if (this.options.compat) {
2188          ret.compat = true;
2189        }
2190
2191        if (!asObject) {
2192          ret.compiler = JSON.stringify(ret.compiler);
2193          ret = this.objectLiteral(ret);
2194        }
2195
2196        return ret;
2197      } else {
2198        return fn;
2199      }
2200    },
2201
2202    preamble: function() {
2203      // track the last context pushed into place to allow skipping the
2204      // getContext opcode when it would be a noop
2205      this.lastContext = 0;
2206      this.source = [];
2207    },
2208
2209    createFunctionContext: function(asObject) {
2210      var varDeclarations = '';
2211
2212      var locals = this.stackVars.concat(this.registers.list);
2213      if(locals.length > 0) {
2214        varDeclarations += ", " + locals.join(", ");
2215      }
2216
2217      // Generate minimizer alias mappings
2218      for (var alias in this.aliases) {
2219        if (this.aliases.hasOwnProperty(alias)) {
2220          varDeclarations += ', ' + alias + '=' + this.aliases[alias];
2221        }
2222      }
2223
2224      var params = ["depth0", "helpers", "partials", "data"];
2225
2226      if (this.useDepths) {
2227        params.push('depths');
2228      }
2229
2230      // Perform a second pass over the output to merge content when possible
2231      var source = this.mergeSource(varDeclarations);
2232
2233      if (asObject) {
2234        params.push(source);
2235
2236        return Function.apply(this, params);
2237      } else {
2238        return 'function(' + params.join(',') + ') {\n  ' + source + '}';
2239      }
2240    },
2241    mergeSource: function(varDeclarations) {
2242      var source = '',
2243          buffer,
2244          appendOnly = !this.forceBuffer,
2245          appendFirst;
2246
2247      for (var i = 0, len = this.source.length; i < len; i++) {
2248        var line = this.source[i];
2249        if (line.appendToBuffer) {
2250          if (buffer) {
2251            buffer = buffer + '\n    + ' + line.content;
2252          } else {
2253            buffer = line.content;
2254          }
2255        } else {
2256          if (buffer) {
2257            if (!source) {
2258              appendFirst = true;
2259              source = buffer + ';\n  ';
2260            } else {
2261              source += 'buffer += ' + buffer + ';\n  ';
2262            }
2263            buffer = undefined;
2264          }
2265          source += line + '\n  ';
2266
2267          if (!this.environment.isSimple) {
2268            appendOnly = false;
2269          }
2270        }
2271      }
2272
2273      if (appendOnly) {
2274        if (buffer || !source) {
2275          source += 'return ' + (buffer || '""') + ';\n';
2276        }
2277      } else {
2278        varDeclarations += ", buffer = " + (appendFirst ? '' : this.initializeBuffer());
2279        if (buffer) {
2280          source += 'return buffer + ' + buffer + ';\n';
2281        } else {
2282          source += 'return buffer;\n';
2283        }
2284      }
2285
2286      if (varDeclarations) {
2287        source = 'var ' + varDeclarations.substring(2) + (appendFirst ? '' : ';\n  ') + source;
2288      }
2289
2290      return source;
2291    },
2292
2293    // [blockValue]
2294    //
2295    // On stack, before: hash, inverse, program, value
2296    // On stack, after: return value of blockHelperMissing
2297    //
2298    // The purpose of this opcode is to take a block of the form
2299    // `{{#this.foo}}...{{/this.foo}}`, resolve the value of `foo`, and
2300    // replace it on the stack with the result of properly
2301    // invoking blockHelperMissing.
2302    blockValue: function(name) {
2303      this.aliases.blockHelperMissing = 'helpers.blockHelperMissing';
2304
2305      var params = [this.contextName(0)];
2306      this.setupParams(name, 0, params);
2307
2308      var blockName = this.popStack();
2309      params.splice(1, 0, blockName);
2310
2311      this.push('blockHelperMissing.call(' + params.join(', ') + ')');
2312    },
2313
2314    // [ambiguousBlockValue]
2315    //
2316    // On stack, before: hash, inverse, program, value
2317    // Compiler value, before: lastHelper=value of last found helper, if any
2318    // On stack, after, if no lastHelper: same as [blockValue]
2319    // On stack, after, if lastHelper: value
2320    ambiguousBlockValue: function() {
2321      this.aliases.blockHelperMissing = 'helpers.blockHelperMissing';
2322
2323      // We're being a bit cheeky and reusing the options value from the prior exec
2324      var params = [this.contextName(0)];
2325      this.setupParams('', 0, params, true);
2326
2327      this.flushInline();
2328
2329      var current = this.topStack();
2330      params.splice(1, 0, current);
2331
2332      this.pushSource("if (!" + this.lastHelper + ") { " + current + " = blockHelperMissing.call(" + params.join(", ") + "); }");
2333    },
2334
2335    // [appendContent]
2336    //
2337    // On stack, before: ...
2338    // On stack, after: ...
2339    //
2340    // Appends the string value of `content` to the current buffer
2341    appendContent: function(content) {
2342      if (this.pendingContent) {
2343        content = this.pendingContent + content;
2344      }
2345
2346      this.pendingContent = content;
2347    },
2348
2349    // [append]
2350    //
2351    // On stack, before: value, ...
2352    // On stack, after: ...
2353    //
2354    // Coerces `value` to a String and appends it to the current buffer.
2355    //
2356    // If `value` is truthy, or 0, it is coerced into a string and appended
2357    // Otherwise, the empty string is appended
2358    append: function() {
2359      // Force anything that is inlined onto the stack so we don't have duplication
2360      // when we examine local
2361      this.flushInline();
2362      var local = this.popStack();
2363      this.pushSource('if (' + local + ' != null) { ' + this.appendToBuffer(local) + ' }');
2364      if (this.environment.isSimple) {
2365        this.pushSource("else { " + this.appendToBuffer("''") + " }");
2366      }
2367    },
2368
2369    // [appendEscaped]
2370    //
2371    // On stack, before: value, ...
2372    // On stack, after: ...
2373    //
2374    // Escape `value` and append it to the buffer
2375    appendEscaped: function() {
2376      this.aliases.escapeExpression = 'this.escapeExpression';
2377
2378      this.pushSource(this.appendToBuffer("escapeExpression(" + this.popStack() + ")"));
2379    },
2380
2381    // [getContext]
2382    //
2383    // On stack, before: ...
2384    // On stack, after: ...
2385    // Compiler value, after: lastContext=depth
2386    //
2387    // Set the value of the `lastContext` compiler value to the depth
2388    getContext: function(depth) {
2389      this.lastContext = depth;
2390    },
2391
2392    // [pushContext]
2393    //
2394    // On stack, before: ...
2395    // On stack, after: currentContext, ...
2396    //
2397    // Pushes the value of the current context onto the stack.
2398    pushContext: function() {
2399      this.pushStackLiteral(this.contextName(this.lastContext));
2400    },
2401
2402    // [lookupOnContext]
2403    //
2404    // On stack, before: ...
2405    // On stack, after: currentContext[name], ...
2406    //
2407    // Looks up the value of `name` on the current context and pushes
2408    // it onto the stack.
2409    lookupOnContext: function(parts, falsy, scoped) {
2410      /*jshint -W083 */
2411      var i = 0,
2412          len = parts.length;
2413
2414      if (!scoped && this.options.compat && !this.lastContext) {
2415        // The depthed query is expected to handle the undefined logic for the root level that
2416        // is implemented below, so we evaluate that directly in compat mode
2417        this.push(this.depthedLookup(parts[i++]));
2418      } else {
2419        this.pushContext();
2420      }
2421
2422      for (; i < len; i++) {
2423        this.replaceStack(function(current) {
2424          var lookup = this.nameLookup(current, parts[i], 'context');
2425          // We want to ensure that zero and false are handled properly if the context (falsy flag)
2426          // needs to have the special handling for these values.
2427          if (!falsy) {
2428            return ' != null ? ' + lookup + ' : ' + current;
2429          } else {
2430            // Otherwise we can use generic falsy handling
2431            return ' && ' + lookup;
2432          }
2433        });
2434      }
2435    },
2436
2437    // [lookupData]
2438    //
2439    // On stack, before: ...
2440    // On stack, after: data, ...
2441    //
2442    // Push the data lookup operator
2443    lookupData: function(depth, parts) {
2444      /*jshint -W083 */
2445      if (!depth) {
2446        this.pushStackLiteral('data');
2447      } else {
2448        this.pushStackLiteral('this.data(data, ' + depth + ')');
2449      }
2450
2451      var len = parts.length;
2452      for (var i = 0; i < len; i++) {
2453        this.replaceStack(function(current) {
2454          return ' && ' + this.nameLookup(current, parts[i], 'data');
2455        });
2456      }
2457    },
2458
2459    // [resolvePossibleLambda]
2460    //
2461    // On stack, before: value, ...
2462    // On stack, after: resolved value, ...
2463    //
2464    // If the `value` is a lambda, replace it on the stack by
2465    // the return value of the lambda
2466    resolvePossibleLambda: function() {
2467      this.aliases.lambda = 'this.lambda';
2468
2469      this.push('lambda(' + this.popStack() + ', ' + this.contextName(0) + ')');
2470    },
2471
2472    // [pushStringParam]
2473    //
2474    // On stack, before: ...
2475    // On stack, after: string, currentContext, ...
2476    //
2477    // This opcode is designed for use in string mode, which
2478    // provides the string value of a parameter along with its
2479    // depth rather than resolving it immediately.
2480    pushStringParam: function(string, type) {
2481      this.pushContext();
2482      this.pushString(type);
2483
2484      // If it's a subexpression, the string result
2485      // will be pushed after this opcode.
2486      if (type !== 'sexpr') {
2487        if (typeof string === 'string') {
2488          this.pushString(string);
2489        } else {
2490          this.pushStackLiteral(string);
2491        }
2492      }
2493    },
2494
2495    emptyHash: function() {
2496      this.pushStackLiteral('{}');
2497
2498      if (this.trackIds) {
2499        this.push('{}'); // hashIds
2500      }
2501      if (this.stringParams) {
2502        this.push('{}'); // hashContexts
2503        this.push('{}'); // hashTypes
2504      }
2505    },
2506    pushHash: function() {
2507      if (this.hash) {
2508        this.hashes.push(this.hash);
2509      }
2510      this.hash = {values: [], types: [], contexts: [], ids: []};
2511    },
2512    popHash: function() {
2513      var hash = this.hash;
2514      this.hash = this.hashes.pop();
2515
2516      if (this.trackIds) {
2517        this.push('{' + hash.ids.join(',') + '}');
2518      }
2519      if (this.stringParams) {
2520        this.push('{' + hash.contexts.join(',') + '}');
2521        this.push('{' + hash.types.join(',') + '}');
2522      }
2523
2524      this.push('{\n    ' + hash.values.join(',\n    ') + '\n  }');
2525    },
2526
2527    // [pushString]
2528    //
2529    // On stack, before: ...
2530    // On stack, after: quotedString(string), ...
2531    //
2532    // Push a quoted version of `string` onto the stack
2533    pushString: function(string) {
2534      this.pushStackLiteral(this.quotedString(string));
2535    },
2536
2537    // [push]
2538    //
2539    // On stack, before: ...
2540    // On stack, after: expr, ...
2541    //
2542    // Push an expression onto the stack
2543    push: function(expr) {
2544      this.inlineStack.push(expr);
2545      return expr;
2546    },
2547
2548    // [pushLiteral]
2549    //
2550    // On stack, before: ...
2551    // On stack, after: value, ...
2552    //
2553    // Pushes a value onto the stack. This operation prevents
2554    // the compiler from creating a temporary variable to hold
2555    // it.
2556    pushLiteral: function(value) {
2557      this.pushStackLiteral(value);
2558    },
2559
2560    // [pushProgram]
2561    //
2562    // On stack, before: ...
2563    // On stack, after: program(guid), ...
2564    //
2565    // Push a program expression onto the stack. This takes
2566    // a compile-time guid and converts it into a runtime-accessible
2567    // expression.
2568    pushProgram: function(guid) {
2569      if (guid != null) {
2570        this.pushStackLiteral(this.programExpression(guid));
2571      } else {
2572        this.pushStackLiteral(null);
2573      }
2574    },
2575
2576    // [invokeHelper]
2577    //
2578    // On stack, before: hash, inverse, program, params..., ...
2579    // On stack, after: result of helper invocation
2580    //
2581    // Pops off the helper's parameters, invokes the helper,
2582    // and pushes the helper's return value onto the stack.
2583    //
2584    // If the helper is not found, `helperMissing` is called.
2585    invokeHelper: function(paramSize, name, isSimple) {
2586      this.aliases.helperMissing = 'helpers.helperMissing';
2587
2588      var nonHelper = this.popStack();
2589      var helper = this.setupHelper(paramSize, name);
2590
2591      var lookup = (isSimple ? helper.name + ' || ' : '') + nonHelper + ' || helperMissing';
2592      this.push('((' + lookup + ').call(' + helper.callParams + '))');
2593    },
2594
2595    // [invokeKnownHelper]
2596    //
2597    // On stack, before: hash, inverse, program, params..., ...
2598    // On stack, after: result of helper invocation
2599    //
2600    // This operation is used when the helper is known to exist,
2601    // so a `helperMissing` fallback is not required.
2602    invokeKnownHelper: function(paramSize, name) {
2603      var helper = this.setupHelper(paramSize, name);
2604      this.push(helper.name + ".call(" + helper.callParams + ")");
2605    },
2606
2607    // [invokeAmbiguous]
2608    //
2609    // On stack, before: hash, inverse, program, params..., ...
2610    // On stack, after: result of disambiguation
2611    //
2612    // This operation is used when an expression like `{{foo}}`
2613    // is provided, but we don't know at compile-time whether it
2614    // is a helper or a path.
2615    //
2616    // This operation emits more code than the other options,
2617    // and can be avoided by passing the `knownHelpers` and
2618    // `knownHelpersOnly` flags at compile-time.
2619    invokeAmbiguous: function(name, helperCall) {
2620      this.aliases.functionType = '"function"';
2621      this.aliases.helperMissing = 'helpers.helperMissing';
2622      this.useRegister('helper');
2623
2624      var nonHelper = this.popStack();
2625
2626      this.emptyHash();
2627      var helper = this.setupHelper(0, name, helperCall);
2628
2629      var helperName = this.lastHelper = this.nameLookup('helpers', name, 'helper');
2630
2631      this.push(
2632        '((helper = (helper = ' + helperName + ' || ' + nonHelper + ') != null ? helper : helperMissing'
2633          + (helper.paramsInit ? '),(' + helper.paramsInit : '') + '),'
2634        + '(typeof helper === functionType ? helper.call(' + helper.callParams + ') : helper))');
2635    },
2636
2637    // [invokePartial]
2638    //
2639    // On stack, before: context, ...
2640    // On stack after: result of partial invocation
2641    //
2642    // This operation pops off a context, invokes a partial with that context,
2643    // and pushes the result of the invocation back.
2644    invokePartial: function(name, indent) {
2645      var params = [this.nameLookup('partials', name, 'partial'), "'" + indent + "'", "'" + name + "'", this.popStack(), this.popStack(), "helpers", "partials"];
2646
2647      if (this.options.data) {
2648        params.push("data");
2649      } else if (this.options.compat) {
2650        params.push('undefined');
2651      }
2652      if (this.options.compat) {
2653        params.push('depths');
2654      }
2655
2656      this.push("this.invokePartial(" + params.join(", ") + ")");
2657    },
2658
2659    // [assignToHash]
2660    //
2661    // On stack, before: value, ..., hash, ...
2662    // On stack, after: ..., hash, ...
2663    //
2664    // Pops a value off the stack and assigns it to the current hash
2665    assignToHash: function(key) {
2666      var value = this.popStack(),
2667          context,
2668          type,
2669          id;
2670
2671      if (this.trackIds) {
2672        id = this.popStack();
2673      }
2674      if (this.stringParams) {
2675        type = this.popStack();
2676        context = this.popStack();
2677      }
2678
2679      var hash = this.hash;
2680      if (context) {
2681        hash.contexts.push("'" + key + "': " + context);
2682      }
2683      if (type) {
2684        hash.types.push("'" + key + "': " + type);
2685      }
2686      if (id) {
2687        hash.ids.push("'" + key + "': " + id);
2688      }
2689      hash.values.push("'" + key + "': (" + value + ")");
2690    },
2691
2692    pushId: function(type, name) {
2693      if (type === 'ID' || type === 'DATA') {
2694        this.pushString(name);
2695      } else if (type === 'sexpr') {
2696        this.pushStackLiteral('true');
2697      } else {
2698        this.pushStackLiteral('null');
2699      }
2700    },
2701
2702    // HELPERS
2703
2704    compiler: JavaScriptCompiler,
2705
2706    compileChildren: function(environment, options) {
2707      var children = environment.children, child, compiler;
2708
2709      for(var i=0, l=children.length; i<l; i++) {
2710        child = children[i];
2711        compiler = new this.compiler();
2712
2713        var index = this.matchExistingProgram(child);
2714
2715        if (index == null) {
2716          this.context.programs.push('');     // Placeholder to prevent name conflicts for nested children
2717          index = this.context.programs.length;
2718          child.index = index;
2719          child.name = 'program' + index;
2720          this.context.programs[index] = compiler.compile(child, options, this.context, !this.precompile);
2721          this.context.environments[index] = child;
2722
2723          this.useDepths = this.useDepths || compiler.useDepths;
2724        } else {
2725          child.index = index;
2726          child.name = 'program' + index;
2727        }
2728      }
2729    },
2730    matchExistingProgram: function(child) {
2731      for (var i = 0, len = this.context.environments.length; i < len; i++) {
2732        var environment = this.context.environments[i];
2733        if (environment && environment.equals(child)) {
2734          return i;
2735        }
2736      }
2737    },
2738
2739    programExpression: function(guid) {
2740      var child = this.environment.children[guid],
2741          depths = child.depths.list,
2742          useDepths = this.useDepths,
2743          depth;
2744
2745      var programParams = [child.index, 'data'];
2746
2747      if (useDepths) {
2748        programParams.push('depths');
2749      }
2750
2751      return 'this.program(' + programParams.join(', ') + ')';
2752    },
2753
2754    useRegister: function(name) {
2755      if(!this.registers[name]) {
2756        this.registers[name] = true;
2757        this.registers.list.push(name);
2758      }
2759    },
2760
2761    pushStackLiteral: function(item) {
2762      return this.push(new Literal(item));
2763    },
2764
2765    pushSource: function(source) {
2766      if (this.pendingContent) {
2767        this.source.push(this.appendToBuffer(this.quotedString(this.pendingContent)));
2768        this.pendingContent = undefined;
2769      }
2770
2771      if (source) {
2772        this.source.push(source);
2773      }
2774    },
2775
2776    pushStack: function(item) {
2777      this.flushInline();
2778
2779      var stack = this.incrStack();
2780      this.pushSource(stack + " = " + item + ";");
2781      this.compileStack.push(stack);
2782      return stack;
2783    },
2784
2785    replaceStack: function(callback) {
2786      var prefix = '',
2787          inline = this.isInline(),
2788          stack,
2789          createdStack,
2790          usedLiteral;
2791
2792      /* istanbul ignore next */
2793      if (!this.isInline()) {
2794        throw new Exception('replaceStack on non-inline');
2795      }
2796
2797      // We want to merge the inline statement into the replacement statement via ','
2798      var top = this.popStack(true);
2799
2800      if (top instanceof Literal) {
2801        // Literals do not need to be inlined
2802        prefix = stack = top.value;
2803        usedLiteral = true;
2804      } else {
2805        // Get or create the current stack name for use by the inline
2806        createdStack = !this.stackSlot;
2807        var name = !createdStack ? this.topStackName() : this.incrStack();
2808
2809        prefix = '(' + this.push(name) + ' = ' + top + ')';
2810        stack = this.topStack();
2811      }
2812
2813      var item = callback.call(this, stack);
2814
2815      if (!usedLiteral) {
2816        this.popStack();
2817      }
2818      if (createdStack) {
2819        this.stackSlot--;
2820      }
2821      this.push('(' + prefix + item + ')');
2822    },
2823
2824    incrStack: function() {
2825      this.stackSlot++;
2826      if(this.stackSlot > this.stackVars.length) { this.stackVars.push("stack" + this.stackSlot); }
2827      return this.topStackName();
2828    },
2829    topStackName: function() {
2830      return "stack" + this.stackSlot;
2831    },
2832    flushInline: function() {
2833      var inlineStack = this.inlineStack;
2834      if (inlineStack.length) {
2835        this.inlineStack = [];
2836        for (var i = 0, len = inlineStack.length; i < len; i++) {
2837          var entry = inlineStack[i];
2838          if (entry instanceof Literal) {
2839            this.compileStack.push(entry);
2840          } else {
2841            this.pushStack(entry);
2842          }
2843        }
2844      }
2845    },
2846    isInline: function() {
2847      return this.inlineStack.length;
2848    },
2849
2850    popStack: function(wrapped) {
2851      var inline = this.isInline(),
2852          item = (inline ? this.inlineStack : this.compileStack).pop();
2853
2854      if (!wrapped && (item instanceof Literal)) {
2855        return item.value;
2856      } else {
2857        if (!inline) {
2858          /* istanbul ignore next */
2859          if (!this.stackSlot) {
2860            throw new Exception('Invalid stack pop');
2861          }
2862          this.stackSlot--;
2863        }
2864        return item;
2865      }
2866    },
2867
2868    topStack: function() {
2869      var stack = (this.isInline() ? this.inlineStack : this.compileStack),
2870          item = stack[stack.length - 1];
2871
2872      if (item instanceof Literal) {
2873        return item.value;
2874      } else {
2875        return item;
2876      }
2877    },
2878
2879    contextName: function(context) {
2880      if (this.useDepths && context) {
2881        return 'depths[' + context + ']';
2882      } else {
2883        return 'depth' + context;
2884      }
2885    },
2886
2887    quotedString: function(str) {
2888      return '"' + str
2889        .replace(/\\/g, '\\\\')
2890        .replace(/"/g, '\\"')
2891        .replace(/\n/g, '\\n')
2892        .replace(/\r/g, '\\r')
2893        .replace(/\u2028/g, '\\u2028')   // Per Ecma-262 7.3 + 7.8.4
2894        .replace(/\u2029/g, '\\u2029') + '"';
2895    },
2896
2897    objectLiteral: function(obj) {
2898      var pairs = [];
2899
2900      for (var key in obj) {
2901        if (obj.hasOwnProperty(key)) {
2902          pairs.push(this.quotedString(key) + ':' + obj[key]);
2903        }
2904      }
2905
2906      return '{' + pairs.join(',') + '}';
2907    },
2908
2909    setupHelper: function(paramSize, name, blockHelper) {
2910      var params = [],
2911          paramsInit = this.setupParams(name, paramSize, params, blockHelper);
2912      var foundHelper = this.nameLookup('helpers', name, 'helper');
2913
2914      return {
2915        params: params,
2916        paramsInit: paramsInit,
2917        name: foundHelper,
2918        callParams: [this.contextName(0)].concat(params).join(", ")
2919      };
2920    },
2921
2922    setupOptions: function(helper, paramSize, params) {
2923      var options = {}, contexts = [], types = [], ids = [], param, inverse, program;
2924
2925      options.name = this.quotedString(helper);
2926      options.hash = this.popStack();
2927
2928      if (this.trackIds) {
2929        options.hashIds = this.popStack();
2930      }
2931      if (this.stringParams) {
2932        options.hashTypes = this.popStack();
2933        options.hashContexts = this.popStack();
2934      }
2935
2936      inverse = this.popStack();
2937      program = this.popStack();
2938
2939      // Avoid setting fn and inverse if neither are set. This allows
2940      // helpers to do a check for `if (options.fn)`
2941      if (program || inverse) {
2942        if (!program) {
2943          program = 'this.noop';
2944        }
2945
2946        if (!inverse) {
2947          inverse = 'this.noop';
2948        }
2949
2950        options.fn = program;
2951        options.inverse = inverse;
2952      }
2953
2954      // The parameters go on to the stack in order (making sure that they are evaluated in order)
2955      // so we need to pop them off the stack in reverse order
2956      var i = paramSize;
2957      while (i--) {
2958        param = this.popStack();
2959        params[i] = param;
2960
2961        if (this.trackIds) {
2962          ids[i] = this.popStack();
2963        }
2964        if (this.stringParams) {
2965          types[i] = this.popStack();
2966          contexts[i] = this.popStack();
2967        }
2968      }
2969
2970      if (this.trackIds) {
2971        options.ids = "[" + ids.join(",") + "]";
2972      }
2973      if (this.stringParams) {
2974        options.types = "[" + types.join(",") + "]";
2975        options.contexts = "[" + contexts.join(",") + "]";
2976      }
2977
2978      if (this.options.data) {
2979        options.data = "data";
2980      }
2981
2982      return options;
2983    },
2984
2985    // the params and contexts arguments are passed in arrays
2986    // to fill in
2987    setupParams: function(helperName, paramSize, params, useRegister) {
2988      var options = this.objectLiteral(this.setupOptions(helperName, paramSize, params));
2989
2990      if (useRegister) {
2991        this.useRegister('options');
2992        params.push('options');
2993        return 'options=' + options;
2994      } else {
2995        params.push(options);
2996        return '';
2997      }
2998    }
2999  };
3000
3001  var reservedWords = (
3002    "break else new var" +
3003    " case finally return void" +
3004    " catch for switch while" +
3005    " continue function this with" +
3006    " default if throw" +
3007    " delete in try" +
3008    " do instanceof typeof" +
3009    " abstract enum int short" +
3010    " boolean export interface static" +
3011    " byte extends long super" +
3012    " char final native synchronized" +
3013    " class float package throws" +
3014    " const goto private transient" +
3015    " debugger implements protected volatile" +
3016    " double import public let yield"
3017  ).split(" ");
3018
3019  var compilerWords = JavaScriptCompiler.RESERVED_WORDS = {};
3020
3021  for(var i=0, l=reservedWords.length; i<l; i++) {
3022    compilerWords[reservedWords[i]] = true;
3023  }
3024
3025  JavaScriptCompiler.isValidJavaScriptVariableName = function(name) {
3026    return !JavaScriptCompiler.RESERVED_WORDS[name] && /^[a-zA-Z_$][0-9a-zA-Z_$]*$/.test(name);
3027  };
3028
3029  __exports__ = JavaScriptCompiler;
3030  return __exports__;
3031})(__module2__, __module5__);
3032
3033// handlebars.js
3034var __module0__ = (function(__dependency1__, __dependency2__, __dependency3__, __dependency4__, __dependency5__) {
3035  "use strict";
3036  var __exports__;
3037  /*globals Handlebars: true */
3038  var Handlebars = __dependency1__;
3039
3040  // Compiler imports
3041  var AST = __dependency2__;
3042  var Parser = __dependency3__.parser;
3043  var parse = __dependency3__.parse;
3044  var Compiler = __dependency4__.Compiler;
3045  var compile = __dependency4__.compile;
3046  var precompile = __dependency4__.precompile;
3047  var JavaScriptCompiler = __dependency5__;
3048
3049  var _create = Handlebars.create;
3050  var create = function() {
3051    var hb = _create();
3052
3053    hb.compile = function(input, options) {
3054      return compile(input, options, hb);
3055    };
3056    hb.precompile = function (input, options) {
3057      return precompile(input, options, hb);
3058    };
3059
3060    hb.AST = AST;
3061    hb.Compiler = Compiler;
3062    hb.JavaScriptCompiler = JavaScriptCompiler;
3063    hb.Parser = Parser;
3064    hb.parse = parse;
3065
3066    return hb;
3067  };
3068
3069  Handlebars = create();
3070  Handlebars.create = create;
3071
3072  Handlebars['default'] = Handlebars;
3073
3074  __exports__ = Handlebars;
3075  return __exports__;
3076})(__module1__, __module7__, __module8__, __module11__, __module12__);
3077
3078  return __module0__;
3079}));
Note: See TracBrowser for help on using the repository browser.