Appearance
Errors
Failures answer with an HTTP status and one JSON shape:
json
{
"error": {
"code": "invalid_request",
"message": "limit must be between 1 and 50",
"param": "limit"
}
}Branch on error.code. message is written for your logs and is free to change wording; code that parses it will break on a release that fixes a typo.
| Status | Code | Meaning | What to do |
|---|---|---|---|
400 | invalid_request | A parameter is missing or out of range. param names it | Fix the call. Retrying is pointless |
401 | invalid_key | Key missing, unknown or disabled | Check the header, then the key |
403 | forbidden | The key is valid but the plan does not include this endpoint | Change plan or drop the call |
404 | not_found | No such clip, or no clips for that word | Show the empty state. Read didYouMean |
429 | rate_limited | Minute window spent | Back off, retry. See rate limits |
429 | quota_exceeded | Period quota spent | Stop retrying until the period resets |
5xx | internal | Our fault | Retry once with backoff, then surface a soft failure |
A miss is not an error state for your user
404 from a word lookup usually means the corpus has not covered that word yet, not that the word is wrong. The response carries didYouMean when close words exist:
json
{
"error": {
"code": "not_found",
"message": "No clips indexed for this word",
"didYouMean": ["receive"]
}
}Offering that suggestion is a better experience than an error banner. See Word matching for how close a match has to be.
Timeouts
Set a client timeout of a few seconds and treat a timeout like internal: one retry, then degrade. Clip playback should never block on us; the embed URL is derivable from a videoId you already stored.