Python requests OAuth2 token 401 with Client Credentials

Trying to get an access token for a backend service using the Genesys Cloud OAuth2 client credentials flow. My requests.post call to /oauth/token keeps returning a 401 Unauthorized. I’m passing the correct client_id and client_secret in the header as Basic Auth, and grant_type in the body. Here’s the snippet:

resp = requests.post(url, headers=headers, data=data)

Logs show the request hits the endpoint but fails auth. Checked credentials twice.

Check your data dictionary structure. The OAuth endpoint is strict about the form-encoded body. If you pass JSON or a wrong key name, it fails silently with 401 sometimes, or just rejects it.

Here is the working pattern I use in my Python scripts for backend integrations. Note the grant_type key must be exact. Also ensure your client secret isn’t URL-encoded if you are building the Basic Auth header manually, though requests handles that if you use auth=.

import requests

url = "https://api.mynice.com/oauth/token"
# Use auth tuple for Basic Auth header
auth = (client_id, client_secret)
data = {
 "grant_type": "client_credentials",
 "scope": "conversation:call:view" # add required scopes
}

# Send as application/x-www-form-urlencoded by default
response = requests.post(url, auth=auth, data=data)

if response.status_code == 200:
 print(response.json().get('access_token'))
else:
 print(f"Error: {response.status_code} - {response.text}")

The 401 usually means the Basic Auth string is malformed. Double check that client_id and client_secret are Base64 encoded correctly in the header if you aren’t using the auth parameter. I’ve seen this trip people up when they manually construct the header.

Be careful with that manual Basic Auth header. If the client secret contains special characters like + or /, standard base64 encoding can trip up the parser. The 401 is often a silent schema validation fail on the payload side too. Always log the exact request body before sending.