dotCMS / dotCMS/core

[Task] v1 publishing destructive ops: enforce publishing-queue portlet gate

Open
#36,045 0 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Team : Modernization
Dominant language
Java
Stars
970
Forks
486
Avg merge
3d 33m
Merged PRs (30d)
170

Description

Context

Surfaced by the Publishing Queue migration spike (#36039) as a security finding.

The destructive v1 publishing endpoints — DELETE /v1/publishing/{bundleId} (PublishingResource:437) and DELETE /v1/publishing/purge (PublishingResource:894) — currently require only requiredBackendUser(true) + rejectWhenNoUser(true) and do not gate on the publishing-queue portlet.

Equivalent destructive ops on adjacent resources do enforce the portlet gate:

  • DELETE /bundle/ids (BundleResource:369) — has requiredPortlet("publishing-queue")
  • GET /bundle/_download/{bundleId} (BundleResource:754) — same
  • POST /bundle/_generate (BundleResource:795) — same
  • DELETE /v1/publishqueue (PublishQueueResource:40) — same

The inconsistency means a backend user without portlet access can delete bundles via the v1 endpoints even though the UI is hidden from them — they could exploit this via direct REST calls (e.g. an integration / SDK client).

Proposed change

Add requiredPortlet("publishing-queue") to both WebResource.InitBuilder calls in PublishingResource:

  • deletePublishingJob at PublishingResource:437
  • purgePublishingJobs at PublishingResource:894

Verify whether the read-side endpoints (listPublishingJobs, getPublishingJobDetails, retryBundles, pushBundle) should also be gated — likely yes for retryBundles and pushBundle since they are write operations.

Acceptance criteria

  • Calling DELETE /v1/publishing/{bundleId} as a backend user without publishing-queue portlet access returns 403
  • Same for DELETE /v1/publishing/purge
  • Integration test (com.dotcms.rest.api.v1.publishing.PublishingResourceTest or equivalent) covers a non-portlet user being rejected
  • Review the four other v1 publishing endpoints and gate where appropriate

Source links

  • Spike audit: #36039 (Security findings section in the UI mapping comment)
  • Epic: #34734

Labels

Type : Bug (security/permission gap)

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start in PublishingResource at deletePublishingJob (line 437) and purgePublishingJobs (line 894), then compare the portlet checks in BundleResource and PublishQueueResource. Review the other four v1 publishing endpoints named in the issue and use PublishingResourceTest, or its equivalent, to verify that a backend user without publishing-queue access receives 403 for the destructive operations and any other gated writes.

Written by the indexing model from the issue text.

Assessment

Tech stack
java
Domain
api, backend, security
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Quiet
Clarity
Mostly clear
Newbie friendliness
68/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.