Long-lived token generation in CI/CD pipeline returns 403 despite valid client credentials

Running into a wall with our build pipeline again. We need a long-lived API token to deploy s via REST API during the nightly build. The standard OAuth flow works fine when I test it manually in Postman or a local Python script, but the automated Jenkins job keeps getting rejected with a 403 Forbidden.

The endpoint is /api/v2/oauth/token. The payload looks correct based on the docs.

{
 "grant_type": "client_credentials",
 "client_id": "my-app-id",
 "client_secret": "my-secret-key"
}

The error response is vague. It just says “Access denied”. No specific reason about the scope or the client. I’ve checked the permissions on the API application in the admin portal. It has admin:application:read and admin:application:write. I also added webmessaging:guest just in case, but that didn’t help.

I tried adding the Authorization: Basic base64(client_id:client_secret) header to the request body, but that didn’t change anything. The pipeline logs show the request is being sent correctly. The timestamp is synced. The client ID and secret are pulled from Jenkins credentials and are definitely correct since they work in Postman.

Is there a specific permission needed on the application itself to generate long-lived tokens? Or is there a limit on how many tokens can be generated per hour? The docs don’t mention a rate limit for this specific endpoint.

I’ve tried regenerating the client secret. I’ve tried creating a new API application with a different name. Same result. The 403 persists.

Any ideas? I’m stuck. The build is failing because of this.