Skip to content

[security] GHSA-7xjx-hc6h-48v4: Missing authorization on FieldCollection get/layout endpoints - #2156

Draft
pimcore-deployments wants to merge 1 commit into
2026.3from
security/ghsa-7xjx-hc6h-48v4-field-collection-auth-19627eb0a75259d9
Draft

pimcore-deployments wants to merge 1 commit into
2026.3from
security/ghsa-7xjx-hc6h-48v4-field-collection-auth-19627eb0a75259d9

Conversation

@pimcore-deployments

Copy link
Copy Markdown
Contributor

Advisory: GHSA-7xjx-hc6h-48v4

Security-Advisory: pimcore/platform-version/GHSA-7xjx-hc6h-48v4

Vulnerability and root cause

GET /pimcore-studio/api/class/field-collection/{key} (GetController) and
GET /pimcore-studio/api/class/field-collection/{key}/layout (LayoutDefinitionController)
were both created with an #[IsGranted(UserPermissions::CLASS_DEFINITION->value)] guard
(78b5e6f0, #1669). One PR later (8852a482, #1671), the same commit that introduced the
dedicated FIELD_COLLECTIONS permission constant and applied it to six new sibling controllers
(and migrated TreeController to it) deleted the #[IsGranted] attribute from exactly these two
files without reapplying anything. Nothing downstream — the service layer, the repository, or an
event subscriber — re-imposes the check, and the bundle has no EventListener directory at all.
Result: any authenticated user (ROLE_PIMCORE_USER) can read any field-collection definition and
its layout by key, while the list/tree/create/update/delete/export/import endpoints of the same
family correctly require the fieldcollections permission.

Fix

Re-applied the same guard the rest of the FieldCollection controller family uses
(TreeController.php:53 and six siblings), on both affected files:

#[IsGranted(UserPermissions::FIELD_COLLECTIONS->value)]

added directly above the existing #[Route] attribute, with the matching use imports for
UserPermissions and IsGranted. This is a one-line, additive guard per file — no other behavior
changes.

Backward compatibility

Both GetController and LayoutDefinitionController are marked @internal, so they are outside
the BC promise per pimcore-backward-compatibility. Independent of that: the change only
restores authorization that existed on both routes from the day they were introduced and that
every sibling endpoint in the same family already enforces today. A legitimate caller already has
the fieldcollections permission (required to reach the list/tree/CRUD endpoints of the same
resource), so no intended workflow is broken — only the gap that let a caller without that
permission bypass it is closed.

Testing

Added tests/Unit/Class/Controller/FieldCollection/FieldCollectionControllerPermissionTest.php, a
reflection-based regression test that asserts both controllers' route-bearing method carries an
#[IsGranted] attribute with the FIELD_COLLECTIONS permission value, following the existing
precedent tests/Unit/Class/Controller/CustomLayout/CustomLayoutControllerPermissionTest.php
(written for a prior, analogous advisory). Against the vulnerable code this test fails
(assertNotEmpty on an empty attributes array); against the fix it passes, and it does not rely on
booting the kernel or a real request, so it exercises exactly the regressed condition
(the missing attribute) without needing a running instance.

Tests added: tests/Unit/Class/Controller/FieldCollection/FieldCollectionControllerPermissionTest.php

Verification performed: php -l on both changed controllers and the new test file (no syntax
errors). The bundle has no local vendor/ in this sandbox (no Composer/network access), so the
Codeception suite itself was not run locally — CI is the source of truth for that.

Warning

Firewall blocked 1 domain

The following domain was blocked by the firewall during workflow execution:

  • api.anthropic.com

To allow these domains, add them to the network.allowed list in your workflow frontmatter:

network:
  allowed:
    - defaults
    - "api.anthropic.com"

See Network Configuration for more information.

Generated by Draft a security-advisory fix · claude · sonnet50 · 103 AIC · ⌖ 25.4 AIC · ⊞ 7.7K · ◷

…t endpoints

GetController and LayoutDefinitionController lost their #[IsGranted] attribute
in #1671, the same commit that introduced the FIELD_COLLECTIONS permission
constant and applied it to their six sibling controllers. Re-apply the guard
so both routes require the fieldcollections permission, matching
TreeController and the rest of the family.

Fixes GHSA-7xjx-hc6h-48v4.

Co-Authored-By: Claude <noreply@anthropic.com>
@pimcore-deployments pimcore-deployments added ai-generated This content was generated using AI. Security labels Oct 27, 2026
@sonarqubecloud

Copy link
Copy Markdown

@mcop1 mcop1 added this to the 2026.3.4 milestone Oct 27, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

ai-generated This content was generated using AI. Security

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants