mongodb/node-mongodb-native · error · MongoGCPError
Status code returned from the GCP endpoint. Response body
Error message
Status code ${response.status} returned from the GCP endpoint. Response body: ${response.body} What it means
Thrown by getGcpTokenData (gcp_machine_workflow.ts:41) when the GCP instance metadata service returns any status other than 200 while fetching an OIDC token. The driver calls the metadata endpoint with a Metadata-Flavor: Google header and expects the token body; a non-200 status means the metadata service rejected the request. The thrown MongoGCPError includes the status code and response body to aid diagnosis.
Solutions
- Confirm the process runs on a real GCP compute instance with access to the metadata service
- Read the response body embedded in the error message for the GCP-specific failure reason
- Verify TOKEN_RESOURCE matches the audience configured in Atlas OIDC exactly
- Ensure the instance service account has token-creator / iam.serviceAccounts.actAs on the target
- Check that no HTTP proxy rewrites http://metadata to a different host
Defensive patterns
Strategy: try-catch
Validate before calling
import { get } from 'http';
// Best-effort reachability check before connecting on GCP:
function checkGcpMetadata(): Promise<boolean> {
return new Promise((resolve) => {
const req = get(
'http://metadata/computeMetadata/v1/instance/service-accounts/default/identity?audience=test',
{ headers: { 'Metadata-Flavor': 'Google' }, timeout: 1000 },
(res) => resolve(res.statusCode !== undefined)
);
req.on('error', () => resolve(false));
req.on('timeout', () => { req.destroy(); resolve(false); });
});
} Try / catch
try {
await client.connect();
} catch (err) {
if (err instanceof MongoGCPError && /GCP endpoint/.test(err.message)) {
// err.message includes the status and body; surface to ops, verify instance/service account
logger.error('GCP metadata call failed', { message: err.message });
}
throw err;
} Prevention
- Run a startup probe against the GCP metadata service before opening MongoClient connections
- Keep the instance service account and audience whitelisting in Terraform/IaC so they stay in sync with TOKEN_RESOURCE
- Surface the embedded response body from the error in alerts for faster diagnosis
When it happens
Trigger: Running with ENVIRONMENT=gcp and the metadata service returns an error: invalid/unauthorized audience (TOKEN_RESOURCE), the compute instance service account cannot mint tokens, the metadata endpoint is proxied/blocked, or the process is not actually on a GCE/GKE/Cloud Run instance and the metadata host resolves to something that returns a non-200 body.
Common situations: Running the gcp workflow on a developer laptop or on-prem (the http://metadata host is not reachable as the real service). TOKEN_RESOURCE audience not whitelisted on the Atlas workload identity provider. The instance service account lacks the permissions to mint tokens for the requested audience. A corporate proxy intercepting the metadata URL.
Related errors
- Azure endpoint did not return a value with only…
- Status code returned from the Azure endpoint. Response body
- TOKEN_RESOURCE must be set in the auth mechanism properties…
- TOKEN_RESOURCE must be set in the auth mechanism properties…
- Auth mechanism property ALLOWED_HOSTS must be an array of…
AI-assisted analysis of mongodb/node-mongodb-native@dce7939f86 (2026-08-11).
Data as JSON: /api/errors/69b67bb264034efd.
Report an issue: GitHub.
Appendix: source
Thrown at src/cmap/auth/mongodb_oidc/gcp_machine_workflow.ts:41
): Promise<OIDCResponse> => {
const tokenAudience = params.tokenAudience;
if (!tokenAudience) {
throw new MongoGCPError(TOKEN_RESOURCE_MISSING_ERROR);
}
return await getGcpTokenData(tokenAudience);
};
/**
* Hit the GCP endpoint to get the token data.
*/
async function getGcpTokenData(tokenAudience: string): Promise<OIDCResponse> {
const url = new URL(GCP_BASE_URL);
url.searchParams.append('audience', tokenAudience);
const response = await get(url, {
headers: GCP_HEADERS
});
if (response.status !== 200) {
throw new MongoGCPError(
`Status code ${response.status} returned from the GCP endpoint. Response body: ${response.body}`
);
}
return { accessToken: response.body };
}
View on GitHub (pinned to dce7939f86)