honojs/hono · error · JwtTokenAudience
expected audience "${Array.isArray(expected) ? expected.join
Error message
expected audience "${Array.isArray(expected) ? expected.join(', ') : expected}", got "${aud}" What it means
Thrown when the token's aud claim does not match the expected audience. Expected can be a string, RegExp, or array; every payload audience value is tested and at least one must match.
Source
Thrown at src/utils/jwt/jwt.ts:172
throw new JwtTokenIssuer(iss, payload.iss)
}
}
if (aud) {
if (!payload.aud) {
throw new JwtPayloadRequiresAud(payload)
}
const audiences = Array.isArray(payload.aud) ? payload.aud : [payload.aud]
const matched = audiences.some((payloadAud): boolean =>
aud instanceof RegExp
? aud.test(payloadAud)
: typeof aud === 'string'
? payloadAud === aud
: Array.isArray(aud) && aud.includes(payloadAud)
)
if (!matched) {
throw new JwtTokenAudience(aud, payload.aud)
}
}
const headerPayload = token.substring(0, token.lastIndexOf('.'))
const verified = await verifying(
publicKey,
alg,
decodeBase64Url(tokenParts[2]),
utf8Encoder.encode(headerPayload)
)
if (!verified) {
throw new JwtTokenSignatureMismatched(token)
}
return payload
}
// Symmetric algorithms that are not allowed for JWK verificationView on GitHub (pinned to e2740d5a1b)
Solutions
- Decode the token and read the actual aud value
- Align the configured audience with what the IdP emits (exact string)
- For multiple valid audiences pass an array: aud: ['api-a', 'api-b']
- Use a RegExp if audiences share a pattern
- Ensure you validate access tokens (not ID tokens) with your API's audience
Example fix
// before
await verify(token, key, { aud: 'my-api' })
// after
await verify(token, key, { aud: ['my-api', 'my-api-v2'] }) Defensive patterns
Strategy: try-catch
Validate before calling
const audiences = Array.isArray(payload.aud) ? payload.aud : [payload.aud]
if (!audiences.includes(expectedAud)) console.warn('aud mismatch:', audiences) Try / catch
try { await verify(token, key, { aud }) } catch (e) { if (e instanceof JwtTokenAudience) return unauthorized(); throw e } Prevention
- Pass an array when multiple audiences are valid
- Match the audience identifier exactly as registered in the IdP
When it happens
Trigger: verify(token, key, { aud }) where aud is a string that differs from every entry in payload.aud, a RegExp that matches none, or an array that contains none of the payload's audience values.
Common situations: Client verified an ID token (aud = client_id) while expecting the API's audience; audience identifier typo; multiple APIs sharing tokens with different aud identifiers; microservice verified a token intended for another service.
Related errors
- required "aud" in jwt payload: ${JSON.stringify(payload)}
- JWK auth middleware requires options for either "keys" or "j
- invalid credentials structure
- no authorization included in request
- Unauthorized
AI-assisted analysis of honojs/hono@e2740d5a1b (2026-08-28).
Data as JSON: /api/errors/7295075b3350687d.
Report an issue: GitHub.