Skip to content

GQL entry mutation siteId bypasses schema site scope, enabling cross-site content read/write/delete

High
angrybrad published GHSA-3wcr-p33w-528f Aug 18, 2026

Package

composer craftcms/cms (Composer)

Affected versions

>= 5.0.0-RC1, < 5.10.11

Patched versions

5.10.11

Description

Craft CMS GraphQL entry mutation resolvers (saveEntry, deleteEntry) read siteId directly from $arguments without passing through ArgumentManager::prepareArguments(), which is the function that enforces site-scope filtering via array_intersect against the GraphQL schema’s allowed sites. The query path (ElementResolver::prepareElementQuery) correctly calls prepareArguments(), so queries to unauthorized sites return empty. But mutations bypass this entirely — an attacker with a token scoped to Site A can create, modify, or delete entries in Site B by passing siteId in the mutations argument.

Impact

  • Confidentiality: saveEntry loads the element by siteId — attacker can read content from unauthorized sites.
  • Integrity: saveEntry writes to the specified site’s elements_sites record; propagation spreads changes to all sites.
  • Availability: deleteEntry locates the element by siteId then calls deleteElementById without siteId, deleting the element across all sites.

Report ID: 1540

Severity

High

CVE ID

No known CVE

Weaknesses

Authorization Bypass Through User-Controlled Key

The system's authorization functionality does not prevent one user from gaining access to another user's data or record by modifying the key value identifying the data. Learn more on MITRE.