Skip to main content
May 5, 2026
Question

App Builder | AEM Cloud Service — Sling POST Servlet returns 403 "The access token is missing required scopes" with OAuth Server-to-Server credential

  • May 5, 2026
  • 4 replies
  • 88 views

 Environment
  - AEM as a Cloud Service (Author) - RDE
  - Adobe App Builder / Adobe I/O Runtime (Server-to-Server OAuth credential)
  - Node.js action using Axios to call AEM APIs

What I'm trying to do

I'm building an App Builder action that creates AEM Sites pages programmatically using the Sling POST Servlet. I have created another action already that creates and updates Content Fragments via the CF Management API(/adobe/sites/cf/fragments) which is working fine.

For page creation, I'm POSTing to the page path with application/x-www-form-urlencoded:

  POST /content/… (content path under which the PDP pages must be created)
  Content-Type: application/x-www-form-urlencoded
  Authorization: Bearer <IMS token>

  _charset_=UTF-8&jcr%3AprimaryType=cq%3APage&jcr%…......

The error

  Every request to the Sling POST Servlet returns:
    "type": "https://api.adobeaemcloud.com/adobe/meta/errors/forbidden",
    "title": "Forbidden",
    "status": 403,
    "detail": "The access token is missing required scopes."
 

  Current credential scopes

  The Developer Console project has these APIs added:
  - Content Fragment Management API → scope: aem.fragments.management
  - AEM Folders API → scope: aem.folders

Product Profiles : AEM Sites Content Managers - author

Full scope string in use: openid,AdobeID,aem.fragments.management,aem.folders

My Questions:

1. What is the correct IMS scope required to call the Sling POST Servlet on /content/... paths with a Server-to-Server credential?

2. Is there an alternative OpenAPI endpoint for programmatic page creation that works with Server-to-Server credentials and the scopes currently available?

Thanks in advance!

4 replies

VeenaVikraman
Community Advisor
Community Advisor
May 7, 2026

Hi Meghana,

The issue does not appear to be with your token generation or the scopes you've configured. Those scopes are valid for the APIs you've enabled. The main issue is that the Sling POST Servlet on /content/... is not part of AEM Cloud’s officially exposed OpenAPI surface for Server-to-Server OAuth in the same way as APIs like Content Fragment Management.

That’s why your CF Management API calls work correctly with aem.fragments.management, while POST requests to /content/... through Sling POST return a 403. The Sling POST Servlet is essentially a repository-level operation and does not behave like the newer IMS-scoped OpenAPI endpoints.

For programmatic page creation in AEM Cloud with App Builder, the approach that typically works best is:

  1. Build a custom AEM servlet or endpoint (for example /bin/yourapp/createpage) deployed inside AEM

  2. Have the App Builder action call that endpoint using the IMS token

  3. Validate the token in AEM and internally create pages using PageManager#create() with a service user that has the required permissions

This approach gives you much better control over:

  • permissions

  • validation

  • business rules

  • auditing

  • scalability

I have worked on a similar use case and I have followed the above approach which worked well for me. 

At the moment, Content Fragment APIs are much more mature from an OpenAPI perspective than generic Sites page creation APIs, so the custom endpoint approach is generally the safest and most flexible option for this use case.

Hope this helps!

 

Thanks

Veena

Meghana_NAuthor
May 8, 2026

Hi ​@VeenaVikraman  Thanks for the detailed response. 

I followed the suggested architecture and ran into the below issue:

  What I implemented:
  - Deployed a custom AEM servlet  (GET for existence check, POST for create/delete)
  - Created a JCR service user via repoinit with jcr:read and rep:write on the content path
  - Mapped the service user to the OSGi bundle via ServiceUserMapperImpl.amended
  - App Builder action calls the servlet with an IMS Bearer token

  The problem:
  The IMS token is being rejected at the CDN layer before the request reaches AEM, with this response:

  {
    "status": 403,
    "detail": "The access token is missing required scopes."
  }

So the service user never gets invoked — the CDN blocks the request first.

Is there anything that I am missing here? Please let me know!

Thanks in advance!

lavishvasuja
Level 4
May 10, 2026

@Meghana_N 

The custom servlet + service user approach is valid from an AEM perspective, but in AEM Cloud the App Builder request must first pass Adobe IMS/AEM authorization before reaching your servlet.

So even if the servlet internally uses PageManager#create() with a service user, the external call still needs an IMS token with scopes allowed for that endpoint/path.

The 403 - access token is missing required scopes indicates the request is being blocked at the platform auth layer, before servlet/service-user logic is invoked.

Also, aem.fragments.management and aem.folders are API-specific scopes and don’t provide generic authoring access on /content/*.

So this looks more like an OAuth/API exposure limitation in AEM Cloud rather than a servlet or permission issue.

Level 4
May 10, 2026

Hi Meghana,

Good question and I’ve run into this exact issue before. Here’s what’s going on.
The root cause is that the Sling POST Servlet on /content paths is not covered by the Content Fragment Management or Folders API scopes you currently have. Those scopes only authorize the OpenAPI endpoints under /adobe/sites/. The Sling POST Servlet is a different beast entirely and requires a different authorization mechanism.
To answer your two questions directly:
On the scope question — there is no IMS scope currently available in Developer Console that grants access to the Sling POST Servlet for arbitrary /content paths via Server-to-Server credentials. This is a known limitation Adobe has acknowledged. The Sling POST Servlet was designed around user-based authentication and the OAuth Server-to-Server flow doesn’t map cleanly to it, which is why you keep getting the missing required scopes 403 even with a valid token.
On the alternative endpoint question yes and this is actually the path Adobe wants you to take going forward. For programmatic page creation from App Builder with Server-to-Server credentials, the recommended approach is to use the AEM Sites Pages API if it’s available in your environment, or to go through a custom OSGi servlet on the AEM side that handles the token exchange and creates the page server-side. The App Builder action calls your custom servlet with the IMS token, the servlet validates it using the AEM service user context, and the actual page creation happens within AEM where Sling permissions apply normally.
The practical workaround most teams use right now is a lightweight proxy servlet approach. You deploy a simple Sling servlet to your AEM Cloud instance that accepts the IMS bearer token, validates it against IMS, maps it to an appropriate service user, and then does the jcr:primaryType=cq:Page node creation internally. This way your App Builder action keeps using Server-to-Server OAuth, the token is valid for calling your custom endpoint, and the page creation happens inside AEM where it has full repository access.
It’s a bit more setup than a direct Sling POST call but it’s stable, it works in RDE and production, and it doesn’t depend on Adobe exposing a scope that doesn’t exist yet.

Meghana_NAuthor
May 10, 2026

Hi ​@akhil_merupula 

Thank you for the detailed explanation. Even with the servlet working on RDE via a developer token, the automated App Builder action kept getting 403 with missing required scopes. The CDN is checking for every token for an AEM product context claim and rejects tokens that don't carry it (P.S - I had logs to check if the request is hitting CDN before reaching AEM and it is ). 

However , the AEM CS Sites Content Management (that i have added for the app builder project) has the following scope : openid,AdobeID,aem.fragments.management,aem.folders. I am not sure this will allow the AEM Sites Page API / custom servlet’s to access “/content”.  

 

P.S: I did try earlier with the Page Management API (accessed via /pages) but that too is giving an “access token is missing reqquired scope “ error.

Level 4
May 10, 2026

Hey ​@Meghana_N ,

That CDN product context claim piece is the key insight here and it explains why even the custom servlet approach hits a wall. The CDN is doing a pre-flight check on the token before the request even reaches AEM, so it doesn’t matter what your servlet does internally the token gets rejected at the edge.
The scopes you have right now aem.fragments.management and aem.folders are tied specifically to the Content Fragment and Folders OpenAPIs. They carry the right product context claim for those endpoints but not for arbitrary /content path access or the Sites Page API, which is why you’re seeing the same 403 across both approaches.
What you actually need is the AEM Sites Content Management API scope added to your Developer Console project. This is a separate API from the CF Management one and it’s what carries the product context claim the CDN expects for page-level operations. If it’s not showing up as an available API in your project, it may not be enabled for your program yet worth raising with your AEM CS admin or Adobe support to get it added to your environment’s API allowlist.
The other thing worth trying in the meantime is switching to a Local Development Access Token instead of the Server-to-Server credential for your RDE testing specifically. Local dev tokens bypass the CDN product context check and hit AEM directly, so you can at least validate that your page creation logic works end to end before solving the credential scoping problem for production.
Let me know if the Sites Content Management API shows up in your Developer Console after checking that should unblock both the Page API and custom servlet routes.