handlebars-lang/handlebars.js · error · Exception

You specified knownHelpersOnly, but used the unknown helper

Error message

You specified knownHelpersOnly, but used the unknown helper ${name}

What it means

With the compiler option knownHelpersOnly:true, any subexpression/ Mustache referencing a helper not listed in options.knownHelpers is rejected at compile time. This enables optimized codegen but requires a complete helper whitelist.

Source

Thrown at lib/handlebars/compiler/compiler.js:268

    this.opcode('invokeAmbiguous', name, isBlock);
  },

  simpleSexpr: function (sexpr) {
    let path = sexpr.path;
    path.strict = true;
    this.accept(path);
    this.opcode('resolvePossibleLambda');
  },

  helperSexpr: function (sexpr, program, inverse) {
    let params = this.setupFullMustacheParams(sexpr, program, inverse),
      path = sexpr.path,
      name = path.parts[0];

    if (this.options.knownHelpers[name]) {
      this.opcode('invokeKnownHelper', params.length, name);
    } else if (this.options.knownHelpersOnly) {
      throw new Exception(
        'You specified knownHelpersOnly, but used the unknown helper ' + name,
        sexpr
      );
    } else {
      path.strict = true;
      path.falsy = true;

      this.accept(path);
      this.opcode(
        'invokeHelper',
        params.length,
        path.original,
        AST.helpers.simpleId(path)
      );
    }
  },

  PathExpression: function (path) {

View on GitHub (pinned to 13a7a67991)

Solutions

  1. Add the missing helper to options.knownHelpers (e.g. knownHelpers: {bar: true}).
  2. Remove knownHelpersOnly to allow runtime helper resolution.
  3. Register the helper and include it in the knownHelpers map used by both runtime and compiler.

Example fix

// before
Handlebars.compile(tpl, {knownHelpersOnly: true, knownHelpers: {upper: true}});
// after
Handlebars.compile(tpl, {knownHelpersOnly: true, knownHelpers: {upper: true, lower: true}});
Defensive patterns

Strategy: validation

Validate before calling

function compileStrict(src, helpers) {
  const used = collectHelperNames(Handlebars.parse(src)); // walk MustacheStatement/SubExpression
  const missing = used.filter(h => !(h in helpers));
  if (missing.length) throw new Error('Helpers not in knownHelpers: ' + missing.join(', '));
  return Handlebars.compile(src, { knownHelpersOnly: true, knownHelpers: fromEntries(Object.keys(helpers).map(h => [h, true])) });
}

Try / catch

try { return compileFn(data); } catch (e) { if (/knownHelpersOnly/.test(e.message)) { /* add helper to knownHelpers or disable strict mode */ } throw e; }

Prevention

When it happens

Trigger: Handlebars.compile(tpl, {knownHelpersOnly: true, knownHelpers: {foo: true}}) on a template using a helper (e.g. {{bar}}) absent from knownHelpers.

Common situations: Enabling knownHelpersOnly for performance/strictness and later adding template features with new helpers; built-in helpers like #each/#if also need listing unless using block params defaults.

Related errors


AI-assisted analysis of handlebars-lang/handlebars.js@13a7a67991 (2026-09-02). Data as JSON: /api/errors/555a261c973cd554. Report an issue: GitHub.