EUVD-2026-16860

| CVE-2026-33940 HIGH
2026-03-27 https://github.com/handlebars-lang/handlebars.js GHSA-xhpv-hc6g-r9c6
8.1
CVSS 3.1
Share

CVSS Vector

CVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:U/C:H/I:H/A:H
Attack Vector
Network
Attack Complexity
High
Privileges Required
None
User Interaction
None
Scope
Unchanged
Confidentiality
High
Integrity
High
Availability
High

Lifecycle Timeline

4
EUVD ID Assigned
Mar 27, 2026 - 18:30 euvd
EUVD-2026-16860
Analysis Generated
Mar 27, 2026 - 18:30 vuln.today
Patch Released
Mar 27, 2026 - 18:30 nvd
Patch available
CVE Published
Mar 27, 2026 - 18:21 nvd
HIGH 8.1

Description

## Summary A crafted object placed in the template context can bypass all conditional guards in `resolvePartial()` and cause `invokePartial()` to return `undefined`. The Handlebars runtime then treats the unresolved partial as a source that needs to be compiled, passing the crafted object to `env.compile()`. Because the object is a valid Handlebars AST containing injected code, the generated JavaScript executes arbitrary commands on the server. The attack requires the adversary to control a value that can be returned by a dynamic partial lookup. ## Description The vulnerable code path spans two functions in `lib/handlebars/runtime.js`: **`resolvePartial()`:** A crafted object with `call: true` satisfies the first branch condition (`partial.call`) and causes an early return of the original object itself, because none of the remaining conditionals (string check, `options.partials` lookup, etc.) match a plain object. The function returns the crafted object as-is. **`invokePartial()`:** When `resolvePartial` returns a non-function object, `invokePartial` produces `undefined`. The runtime interprets `undefined` as "partial not yet compiled" and calls `env.compile(partial, ...)` where `partial` is the crafted AST object. The JavaScript code generator processes the AST and emits JavaScript containing the injected payload, which is then evaluated. **Minimum prerequisites:** 1. The template uses a dynamic partial lookup: `{{> (lookup . "key")}}` or equivalent. 2. The adversary can set the value of the looked-up context property to a crafted object. In server-side rendering scenarios where templates process user-supplied context data, this enables full Remote Code Execution. ## Proof of Concept ```javascript const Handlebars = require('handlebars'); const vulnerableTemplate = `{{> (lookup . "payload")}}`; const maliciousContext = { payload: { call: true, // bypasses the primary resolvePartial branch type: "Program", body: [ { type: "MustacheStatement", depth: 0, path: { type: "PathExpression", parts: ["pop"], original: "this.pop", // Injected code breaks out of the generated function's argument list depth: "0])),function () {console.error('VULNERABLE: object -> dynamic partial -> RCE');}()));//", }, }, ], }, }; Handlebars.compile(vulnerableTemplate)(maliciousContext); // Prints: VULNERABLE: object -> dynamic partial -> RCE ``` ## Workarounds - **Use the runtime-only build** (`require('handlebars/runtime')`). Without `compile()`, the fallback compilation path in `invokePartial` is unreachable. - **Sanitize context data** before rendering: ensure no value in the context is a non-primitive object that could be passed to a dynamic partial. - **Avoid dynamic partial lookups** (`{{> (lookup ...)}}`) when context data is user-controlled.

Analysis

Remote code execution in Handlebars templating engine (npm package) allows unauthenticated network attackers to execute arbitrary server-side commands by exploiting dynamic partial resolution logic. Affected versions include all releases prior to v4.7.9. …

Sign in for full analysis, threat intelligence, and remediation guidance.

Remediation

Within 24 hours: Identify all instances of Handlebars npm package in use across development, staging, and production environments and determine installed versions. Within 7 days: Upgrade all affected Handlebars instances to version 4.7.9 or later; prioritize production systems first. …

Sign in for detailed remediation steps.

Priority Score

41
Low Medium High Critical
KEV: 0
EPSS: +0.0
CVSS: +40
POC: 0

Share

EUVD-2026-16860 vulnerability details – vuln.today

This site uses cookies essential for authentication and security. No tracking or analytics cookies are used. Privacy Policy