calcom/cal.diy · error · BadRequestException
Something is wrong with Zoom API
Error message
Something is wrong with Zoom API
What it means
Default error message used in connectZoomApp when the POST to https://zoom.us/oauth/token returns a non-200 status AND extracting a JSON body with responseBody.error fails. errorMessage stays as the literal 'Something is wrong with Zoom API' and is thrown via BadRequestException (HTTP 400). It is the fallback when Zoom returns an error with no parseable JSON error field.
Source
Thrown at apps/api/v2/src/modules/conferencing/services/zoom-video.service.ts:83
const result = await fetch(
`https://zoom.us/oauth/token?grant_type=authorization_code&code=${code}&redirect_uri=${redirectUri}`,
{
method: "POST",
headers: {
Authorization: authHeader,
},
}
);
if (result.status !== 200) {
let errorMessage = "Something is wrong with Zoom API";
try {
const responseBody = await result.json();
errorMessage = responseBody.error;
} catch (e) {
errorMessage = await result.clone().text();
}
throw new BadRequestException(errorMessage);
}
const responseBody = await result.json();
if (responseBody.error) {
throw new BadRequestException(responseBody.error);
}
responseBody.expiry_date = Math.round(Date.now() + responseBody.expires_in * 1000);
delete responseBody.expires_in;
if (!userId) {
throw new UnauthorizedException("Invalid Access token.");
}
const existingCredentialZoomVideo = teamId
? await this.credentialsRepository.findAllCredentialsByTypeAndTeamId(ZOOM_TYPE, teamId)
: await this.credentialsRepository.findAllCredentialsByTypeAndUserId(ZOOM_TYPE, userId);View on GitHub (pinned to 176037d0af)
Solutions
- Retry the connect flow once after a short delay — transient Zoom 5xx often clear.
- Verify the Zoom app client_id and client_secret in app keys are current and that the Authorization: Basic header is being built from the correct pair.
- Check Zoom status page and inspect server logs for the actual status code/body returned by Zoom when this fires.
Defensive patterns
Strategy: retry
Try / catch
let lastErr;
for (let attempt = 0; attempt < 3; attempt++) {
try {
return await zoomService.connectZoomApp(state, code, userId, teamId);
} catch (e) {
lastErr = e;
if (e instanceof BadRequestException && /Something is wrong with Zoom API/.test(e.message)) {
await delay(500 * Math.pow(2, attempt));
continue;
}
throw e;
}
}
throw lastErr; Prevention
- Retry transient Zoom 5xx with exponential backoff.
- Alert ops when the literal fallback message recurs frequently (signals outage).
- Keep Zoom app credentials current to avoid persistent failures.
When it happens
Trigger: Zoom token endpoint returns 4xx/5xx with an HTML or empty body (rate-limit page, outage, network proxy intercept), so the try block's `responseBody.error` access throws and the catch falls back to text() — but the original literal is used only if the catch itself is bypassed; in practice the literal surfaces when the JSON parse yields no `.error`. Typical for transient Zoom outages or auth header issues.
Common situations: Zoom API temporary outage/maintenance; client_id:client_secret base64 auth header malformed (expired app credentials); IP rate-limited by Zoom; corporate proxy returning an HTML challenge page instead of JSON.
Related errors
- ${responseBody.error}
- Missing `state` query param
- {error_description}
- Invalid conferencing app, available apps are:
- {responseBody.error}
AI-assisted analysis of calcom/cal.diy@176037d0af (2026-08-12).
Data as JSON: /api/errors/08202e97f2370bce.
Report an issue: GitHub.