handlebars-lang/handlebars.js · error · Exception
Missing helper: "${name}"
Error message
Missing helper: "${name}" What it means
This is thrown by Handlebars' built-in 'helperMissing' helper. When a template references an identifier as a function call (e.g. {{foo bar}}) and no helper named 'foo' is registered, Handlebars calls helperMissing; if there is more than just the options argument (meaning it looked like a helper invocation with args), it throws 'Missing helper: "foo"'. A plain {{foo}} with a missing field returns undefined instead.
Source
Thrown at lib/handlebars/helpers/helper-missing.js:10
import { Exception } from '@handlebars/parser';
export default function (instance) {
instance.registerHelper('helperMissing', function (/* [args, ]options */) {
if (arguments.length === 1) {
// A missing field in a {{foo}} construct.
return undefined;
} else {
// Someone is actually trying to call something, blow up.
throw new Exception(
'Missing helper: "' + arguments[arguments.length - 1].name + '"'
);
}
});
}
View on GitHub (pinned to 13a7a67991)
Solutions
- Register the missing helper before compiling: instance.registerHelper('name', fn), or use the global Handlebars.registerHelper if using the default instance.
- Fix the typo in the template so it matches a registered helper or an existing data field.
- Ensure the same Handlebars instance is used for registerHelper and for compile/template execution.
- Check the changelog when upgrading: built-in helpers (each, if, with, log, lookup, helperMissing) must not be shadowed or removed.
- Temporarily register a catch-all helperMissing override to log which helpers templates request.
Example fix
// before: template uses {{formatDate date}} but helper not registered
// after
import Handlebars from 'handlebars';
Handlebars.registerHelper('formatDate', (date) => new Date(date).toISOString()); Defensive patterns
Strategy: validation
Validate before calling
const usedHelpers = extractHelperNamesFromTemplates(source);
const missing = usedHelpers.filter((n) => !instance.helpers[n]);
if (missing.length) console.warn('Unregistered helpers:', missing); Type guard
function helperIsRegistered(instance, name) {
return typeof instance.helpers?.[name] === 'function';
} Try / catch
try {
return template(data);
} catch (e) {
const m = /Missing helper: "(.+)"/.exec(e.message || '');
if (m) {
console.error(`Helper '${m[1]}' is not registered on this Handlebars instance`);
return fallbackRender(data);
}
throw e;
} Prevention
- Register all helpers before compiling templates
- Use one shared Handlebars instance for registration and compilation
- Add a build-time check that extracts helper names from templates and verifies registration
- Grep templates for helper names after upgrading Handlebars
- Provide a debug helperMissing override in dev that logs missing names
When it happens
Trigger: Template contains {{someHelper arg}} or {{#someHelper}} but no helper named 'someHelper' is registered; typo in a helper name; helper registered on a different Handlebars instance than the one compiling the template; helper removed/renamed after a version upgrade; invoking a block helper without block params after strict-mode-ish misuse.
Common situations: Upgrading Handlebars where a built-in helper moved (e.g. after splitting packages); forgetting instance.registerHelper when using multiple instances; typos like {{#ech}} instead of {{#each}}; partials compiled with a different instance than the one holding the helpers.
Related errors
- Invalid stack pop
- Must pass iterator to #each
- #if requires exactly one argument
- #unless requires exactly one argument
- #with requires exactly one argument
AI-assisted analysis of handlebars-lang/handlebars.js@13a7a67991 (2026-09-02).
Data as JSON: /api/errors/d66e8f0af4767fc1.
Report an issue: GitHub.