CVEReports
CVEReports

Automated vulnerability intelligence platform. Comprehensive reports for high-severity CVEs generated by AI.

Product

  • Home
  • Sitemap
  • RSS Feed

Company

  • About
  • Contact
  • Privacy Policy
  • Terms of Service

© 2026 CVEReports. All rights reserved.

Made with love by Amit Schendel & Alon Barad



CVE-2026-27126

Table for Two: Serving Stored XSS in Craft CMS Hidden Features

Amit Schendel
Amit Schendel
Senior Security Researcher

Feb 24, 2026·6 min read·42 visits

Executive Summary (TL;DR)

Craft CMS contained a 'ghost' column type called 'html' within its Table Field component. While not visible in the UI, it was supported by the backend. Attackers with field configuration permissions could manually set a column to this type, enabling the rendering of raw, unsanitized HTML (and JavaScript) in the admin panel.

A hidden, semi-internal 'html' column type in Craft CMS's Table Field component allowed authenticated administrators to inject arbitrary JavaScript. By manipulating field configuration requests, an attacker could enable this unexposed column type, bypassing sanitization and achieving Stored XSS against other control panel users.

The Hook: Ghost Features and Zombie Code

We all love a flexible Content Management System. Craft CMS is arguably one of the best, giving developers granular control over data structures. One of its most powerful tools is the 'Table Field,' which allows content editors to manage rows of repeated data—text, numbers, checkboxes, etc. It is the Excel spreadsheet of the CMS world.

But here is the thing about software development: features get deprecated, hidden, or half-built, and sometimes they never really leave the codebase. They just become ghosts. In CVE-2026-27126, researchers found one of these ghosts lurking in the Table Field logic.

It turns out, while the UI only let you pick mundane column types like singleline or number, the backend logic was secretly holding a candle for a type called html. And unlike its siblings, the html type did exactly what it sounds like—it took whatever input you gave it and dumped it directly into the DOM, raw and wriggling. It’s like finding a secret menu item at a restaurant that serves you uncooked chicken.

The Flaw: Trusting the Configuration

The vulnerability stems from a classic disconnect between the User Interface and the Application Logic. The developers correctly assumed that users shouldn't be creating columns that render raw HTML, so they simply didn't include html in the dropdown menu of the Field Settings page. Case closed, right? Wrong.

The backend component responsible for validating the Table Field configuration (src/fields/Table.php) had a blind spot. It accepted the column configuration array and processed it, but it didn't strictly validate that the requested type was one of the publicly supported options.

Simultaneously, the frontend template responsible for rendering the table in the control panel (editableTable.twig) had logic explicitly designed to handle this html type. It was likely a remnant of an internal feature or a deprecated capability. When the renderer encountered a column with type: 'html', it skipped the usual output encoding and treated the cell's content as trusted markup. This created a perfect Stored XSS vector for anyone who could force the configuration to acknowledge this hidden type.

The Code: The Smoking Gun

Let's look at the PHP code. Before the patch, the validateColumns method was a bit too permissible. It iterated through columns to check basic properties but failed to enforce a strict allowlist on the type attribute.

The fix, implemented by Brandon Kelly, introduces a hardcoded list of allowed types and forces anything else to degrade to a harmless singleline text field.

Before (Conceptual Logic):

foreach ($this->columns as &$col) {
    // Checking label, handle, etc.
    // No check if $col['type'] is actually valid!
}

After (Patched Logic):

// src/fields/Table.php
 
private static function typeOptions(): array
{
    return [
        'checkbox' => true,
        'color' => true,
        'date' => true,
        'select' => true,
        // ... (other safe types)
        'url' => true,
    ];
}
 
public function validateColumns(): void
{
    $typeOptions = self::typeOptions();
 
    foreach ($this->columns as &$col) {
        // If the type isn't in our VIP list, you're getting a text box.
        if (!isset($typeOptions[$col['type']])) {
            $col['type'] = 'singleline';
        }
        // ...
    }
}

By adding this check, the 'ghost' html type is effectively exorcised. Even if an attacker tries to inject it, the system forces it into a singleline type, which escapes all output.

The Exploit: Editing the Uneditable

Since the UI won't let us select the html type, we have to get our hands dirty with a proxy. This is an 'Authenticated Admin' exploit, meaning the attacker needs permissions to configure fields (specifically allowAdminChanges must be on).

Here is the attack chain:

  1. Intercept: The attacker configures a Table Field in the settings. They set up a standard column (e.g., a Single Line Text column) and hit 'Save'.
  2. Modify: Using Burp Suite or Caido, they catch the POST request. In the JSON payload defining the columns, they hunt for "type": "singleline".
  3. Inject: They change the value to "type": "html". The backend, lacking the validation we saw earlier, saves this configuration to the database.
  4. Weaponize: The attacker (or an unwitting editor) goes to an Entry that uses this field. The column looks normal, but it's a trap. The attacker types <img src=x onerror=alert(document.cookie)> into the cell.
  5. Trigger: The next time an administrator views this entry in the control panel, the payload fires. The editableTable.twig sees the html type and renders the script tag immediately.

The Impact: Why Admin XSS Matters

You might be thinking, "If I already have Admin access to change settings, why do I need XSS?" That is a fair question, but it misses the nuance of modern access control.

First, Privilege Escalation. In many organizations, there are tiers of administrators. A 'Site Builder' might have permission to configure fields but not to install plugins or execute PHP. By using this XSS, the lower-tier admin can hijack the session of a Super Admin. Once they have that session, they can install a malicious plugin or edit templates to achieve full Remote Code Execution (RCE) on the server.

Second, Persistence. An attacker who briefly compromises an admin account can plant this 'time bomb' in the database. Even if their original access is revoked, the XSS payload remains in the content, waiting for a high-value target to view the table. It is a backdoor that lives in the legitimate data structure of the site.

The Fix: Cleaning Up

The remediation is straightforward: upgrade. The patch exists in Craft CMS 4.16.19 and 5.8.23. These versions introduce the strict type checking we analyzed above.

If you cannot upgrade immediately, there is a configuration-level mitigation. Craft CMS has a setting called allowAdminChanges. In a properly secured production environment, this should be set to false.

// config/general.php
'allowAdminChanges' => false,

Disabling admin changes prevents anyone from modifying field configurations via the control panel, effectively neutralizing the attack vector (unless the attacker has direct database access, in which case you have bigger problems). This is a best practice for Craft CMS deployment pipelines anyway—treat your production schema as immutable.

Official Patches

Craft CMSGitHub Commit fixing the issue
Craft CMSOfficial Security Advisory

Fix Analysis (1)

Technical Appendix

CVSS Score
5.9/ 10
CVSS:4.0/AV:N/AC:L/AT:P/PR:L/UI:P/VC:N/VI:H/VA:N/SC:N/SI:N/SA:N

Affected Systems

Craft CMS 4.x (>= 4.5.0-RC1, < 4.16.19)Craft CMS 5.x (>= 5.0.0-RC1, < 5.8.23)

Affected Versions Detail

Product
Affected Versions
Fixed Version
Craft CMS
Pixel & Tonic
>= 4.5.0-RC1, < 4.16.194.16.19
Craft CMS
Pixel & Tonic
>= 5.0.0-RC1, < 5.8.235.8.23
AttributeDetail
CWE IDCWE-79
Attack VectorNetwork (Authenticated)
CVSS v4.05.9 (Medium)
ImpactStored XSS / Session Hijacking
Privileges RequiredLow (Admin with Settings Access)
Exploit StatusPoC Available

MITRE ATT&CK Mapping

T1189Drive-by Compromise
Initial Access
T1185Browser Session Hijacking
Collection
CWE-79
Cross-site Scripting

Improper Neutralization of Input During Web Page Generation ('Cross-site Scripting')

Known Exploits & Detection

Manual AnalysisManual modification of POST request parameters to set column type to 'html'.

Vulnerability Timeline

Patch committed by vendor
2026-01-14
GHSA Advisory Published
2026-02-24
CVE Published
2026-02-24

References & Sources

  • [1]GHSA-3jh3-prx3-w6wc
  • [2]Patch Commit

Attack Flow Diagram

Press enter or space to select a node. You can then use the arrow keys to move the node around. Press delete to remove it and escape to cancel.
Press enter or space to select an edge. You can then press delete to remove it or escape to cancel.

More Reports

•about 9 hours ago•CVE-2026-14669
8.8

CVE-2026-14669: PostgreSQL to_char() Timezone Abbreviation Heap-Based Buffer Overflow

CVE-2026-14669 is a critical heap-based buffer overflow vulnerability in PostgreSQL's date/time formatting function to_char(timestamptz). The flaw arises from unsafe copying of user-controlled timezone abbreviations into a fixed-size internal buffer. An authenticated database user can trigger this issue by setting a long POSIX timezone abbreviation containing custom formatting, allowing them to overwrite adjacent heap structures and hijack execution control to achieve remote code execution (RCE) with the privileges of the 'postgres' operating system user.

Alon Barad
Alon Barad
7 views•6 min read
•2 days ago•CVE-2026-63462
7.5

CVE-2026-63462: Unauthenticated Stack Overflow Denial of Service in Unleash Server

An unauthenticated remote denial of service vulnerability exists in the Unleash feature management platform. By submitting a crafted JSON payload containing deeply nested structures to an OpenAPI-validated endpoint, an attacker can trigger uncontrolled recursion within the error formatting module. This leads to a call-stack exhaustion (RangeError: Maximum call stack size exceeded) inside the Node.js runtime, causing the service to crash immediately without recovery.

Alon Barad
Alon Barad
11 views•6 min read
•2 days ago•CVE-2026-63004
5.5

CVE-2026-63004: Server-Side Request Forgery in Unleash Addon and Integration Subsystem

CVE-2026-63004 is a server-side request forgery (SSRF) vulnerability in the Unleash feature management platform. Authenticated administrators with CREATE_ADDON or UPDATE_ADDON privileges can exploit this vulnerability to initiate requests to loopback addresses, private networks, and cloud metadata endpoints, potentially leading to information disclosure and credential extraction.

Amit Schendel
Amit Schendel
9 views•8 min read
•2 days ago•CVE-2026-63466
4.1

CVE-2026-63466: Process-Wide Security Degradation via Global Module Mutation in Unleash

Prior to version 8.0.3, Unleash's Markdown event formatter directly mutated the global template-escaping function of the shared mustache Node.js module, resulting in a process-wide security degradation where HTML/Markdown escaping was permanently disabled for the application lifetime.

Alon Barad
Alon Barad
3 views•6 min read
•2 days ago•CVE-2026-76904
9.8

CVE-2026-76904: Unauthenticated SQL Injection in GeoTools PostGIS DataStore Component

A critical SQL injection vulnerability exists in the GeoTools open-source Java library. This vulnerability is situated within the post-processing phase of OGC Filter conversion inside the PostGIS DataStore module. Specifically, the `jsonArrayContains` function does not validate or sanitize its arguments before constructing PostgreSQL SQL/JSON path evaluation queries. An unauthenticated remote attacker can exploit this weakness by submitting crafted filters via standard OGC services like WFS or WMS to execute arbitrary SQL commands on the underlying database system.

Alon Barad
Alon Barad
15 views•5 min read
•2 days ago•CVE-2026-61824
8.2

CVE-2026-61824: High-Severity Cross-Site Scripting (XSS) via Unsanitized Site Extractors in Defuddle

CVE-2026-61824 is a high-severity Cross-Site Scripting (XSS) vulnerability in kepano/defuddle before version 0.19.1. Custom site extractors for platforms such as X/Twitter, Substack, and YouTube constructed HTML representations via template string interpolation without output escaping. This allowed malicious pages to bypass standard parser sanitization routines and execute arbitrary JavaScript.

Amit Schendel
Amit Schendel
7 views•7 min read