CVE-2026-63669
## Summary ApostropheCMS enforces per-type authorization on pages: a page type may declare `editRole` / `publishRole` (and the core `@apostrophecms/archive-page` does), so a project can have page-type subtrees that only higher-privileged roles are allowed to create or edit within. The `move()` operation is supposed to enforce that a page may only be moved *into* a parent the actor has **create** rights over — this is the same boundary the page-insert route enforces (the insert target is fetched with `.permission('create')`). A regression in the move authorization guard silently disabled that destination check for every normal move. The guard now reads `(oldParent._id !== parent._id) && (parent.type !== '@apostrophecms/archive-page') && (!parent._create) && (oldParent.type === '@apostrophecms/archive-page' && !parent._edit)`. Because the final `&&` clause requires `oldParent.type === '@apostrophecms/archive-page'`, the whole conjunction can only be true while restoring a page *out of the archive*. For any ordinary move (the source page's old parent is a normal page), that clause is `false`, the entire condition is `false`, and `!parent._create` is never evaluated. The only surviving gate in the whole path is `moved._edit` — i.e. "can the actor edit the page being moved", which a low-privileged editor legitimately holds for their own ordinary pages. The result is that any authenticated user who can edit at least one page can relocate that page **under a parent of a restricted type they have no create/edit rights over**, and in doing so trigger an unauthenticated, unchecked `updateMany` that re-ranks the restricted parent's existing children (documents the actor cannot edit). This is reachable directly from the documented `PATCH`/`PUT /api/v1/@apostrophecms/page/:_id` REST routes via the attacker-controlled `_targetId` / `_position` body fields. ## Affected code (4.31.0) The broken guard in `move()` — `packages/apostrophe/modules/@apostrophecms/page/index.js`: ```
Properties
- severity
- medium
- summary
- ApostropheCMS: Missing destination-parent authorization in page `move()` allows a low-privileged editor to move and re-rank pages inside a restricted subtree
- epss_score
- 0.00221
- cvss_score
- 6.5
- ghsa_published
- 2026-09-03T20:05:08Z
- source_url
- https://github.com/advisories/GHSA-wr5r-wqp2-x4fh
- ghsa_updated
- 2026-09-03T20:05:10Z
- ghsa_id
- GHSA-wr5r-wqp2-x4fh
- cve_id
- CVE-2026-63669
- cvss_vector
- CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:U/C:N/I:H/A:N
- is_ghsa_only
- false
- epss_percentile
- 0.12461
Related Entities (6)
ENRICHED_BY (1)
VULNERABLE_TO (1)
AFFECTS (1)
HAS_WEAKNESS (2)
REPORTED_BY (1)
Explore deeper with Ninja Signal's threat intelligence graph