usebruno/bruno · error · Error
Access Token URL is required for OAuth2 client credentials…
Error message
Access Token URL is required for OAuth2 client credentials flow
What it means
Thrown by fetchTokenClientCredentials when the OAuth2Config.accessTokenUrl field is empty/undefined. The client-credentials grant needs a token endpoint to POST credentials to, so the helper refuses to build a request without one. It is a pre-flight validation guard, not a network error.
Solutions
- Set oauth2Config.accessTokenUrl to the full token endpoint URL (e.g. https://auth.example.com/oauth/token) before invoking the flow.
- If the URL comes from an env var, verify the variable is defined and non-empty at call time (console.log it in dev).
- Add a pre-call validation check (see validationCode) so the error surfaces in your code, not inside the helper.
Example fix
// before
const config = { grantType: 'client_credentials', clientId: 'abc', clientSecret: 'xyz' };
await getOAuth2AccessToken(config, tokenStore);
// after
const config = {
grantType: 'client_credentials',
accessTokenUrl: process.env.OAUTH_TOKEN_URL,
clientId: 'abc',
clientSecret: 'xyz'
};
await getOAuth2AccessToken(config, tokenStore); Defensive patterns
Strategy: validation
Validate before calling
function validateClientCredentialsConfig(c) {
if (!c.accessTokenUrl) throw new Error('accessTokenUrl missing for client_credentials flow');
if (!c.clientId) throw new Error('clientId missing for client_credentials flow');
}
validateClientCredentialsConfig(config); Type guard
function isClientCredentialsReady(c) {
return c.grantType === 'client_credentials'
&& typeof c.accessTokenUrl === 'string' && c.accessTokenUrl.length > 0
&& typeof c.clientId === 'string' && c.clientId.length > 0;
} Try / catch
try { await getOAuth2AccessToken(config, tokenStore); }
catch (e) { if (e.message.includes('Access Token URL is required')) { /* fill config */ } else throw e; } Prevention
- Build OAuth2Config through a factory that asserts required fields per grant type.
- Resolve env-var substitutions for URLs before passing the config to the helper.
- Run a config-shape unit test that exercises both grant types.
When it happens
Trigger: Calling getOAuth2AccessToken (or the Bruno auth pipeline) with grantType='client_credentials' but accessTokenUrl set to '', null, undefined, or omitted. This includes configs loaded from a collection where the token URL field was left blank by the user.
Common situations: User created an OAuth2 collection item but never filled the 'Access Token URL' field; env variable referencing the URL resolved to empty; config object assembled programmatically and the accessTokenUrl key was misspelled or destructured away.
Related errors
- Client ID is required for OAuth2 client credentials flow
- Access token URL is required for OAuth2
- Access Token URL is required for OAuth2 password…
- Client ID is required for OAuth2 password credentials flow
- Grant type is required for OAuth2
AI-assisted analysis of usebruno/bruno@9bdd81c7bd (2026-08-13).
Data as JSON: /api/errors/f86455f18f370a8f.
Report an issue: GitHub.
Appendix: source
Thrown at packages/bruno-requests/src/auth/oauth2-helper.ts:122
return data;
}
};
/**
* Fetches an OAuth2 token using client credentials grant
*/
const fetchTokenClientCredentials = async (oauth2Config: OAuth2Config, axiosInstance?: AxiosInstance) => {
const {
accessTokenUrl,
clientId,
clientSecret,
scope,
credentialsPlacement = 'basic_auth_header',
additionalParameters
} = oauth2Config;
if (!accessTokenUrl) {
throw new Error('Access Token URL is required for OAuth2 client credentials flow');
}
if (!clientId) {
throw new Error('Client ID is required for OAuth2 client credentials flow');
}
const requestConfig: RequestConfig = {
method: 'POST',
url: accessTokenUrl,
headers: {
'Content-Type': 'application/x-www-form-urlencoded',
'Accept': 'application/json'
},
data: '',
responseType: 'arraybuffer'
};
const data: ClientCredentialsData = {View on GitHub (pinned to 9bdd81c7bd)