quarkusio/quarkus · error · SpiffeConnectionException
SPIFFE ID trust domain contains invalid character '' + c + '
Error message
SPIFFE ID trust domain contains invalid character '' + c + '':
What it means
Per the SPIFFE spec, trust domains may only contain lowercase letters, digits, '.', '-' and '_'. SpiffeValidator.validateSpiffeId throws SpiffeConnectionException for any other character (uppercase letters, ':', spaces, etc.) in the trust domain.
Source
Thrown at extensions/spiffe-client/runtime/src/main/java/io/quarkus/spiffe/client/runtime/internal/SpiffeValidator.java:113
if (uri.getQuery() != null) {
throw new SpiffeConnectionException("SPIFFE ID must not contain a query: " + spiffeId);
}
if (uri.getFragment() != null) {
throw new SpiffeConnectionException("SPIFFE ID must not contain a fragment: " + spiffeId);
}
String trustDomain = uri.getHost();
if (trustDomain == null || trustDomain.isEmpty()) {
throw new SpiffeConnectionException("SPIFFE ID must have a non-empty trust domain: " + spiffeId);
}
if (trustDomain.length() > MAX_TRUST_DOMAIN_LENGTH) {
throw new SpiffeConnectionException("SPIFFE ID trust domain exceeds maximum length of "
+ MAX_TRUST_DOMAIN_LENGTH + " bytes: " + spiffeId);
}
for (int i = 0; i < trustDomain.length(); i++) {
char c = trustDomain.charAt(i);
if (!isValidTrustDomainChar(c)) {
throw new SpiffeConnectionException(
"SPIFFE ID trust domain contains invalid character '" + c + "': " + spiffeId);
}
}
String path = uri.getPath();
if (path == null || path.isEmpty() || "/".equals(path)) {
throw new SpiffeConnectionException("SPIFFE ID must have a non-root path: " + spiffeId);
}
if (path.endsWith("/")) {
throw new SpiffeConnectionException("SPIFFE ID path must not have a trailing slash: " + spiffeId);
}
String[] segments = path.split("/", -1);
for (int i = 1; i < segments.length; i++) {
String segment = segments[i];
if (segment.isEmpty()) {
throw new SpiffeConnectionException(
"SPIFFE ID path must not contain empty segments: " + spiffeId);
}View on GitHub (pinned to e1c734241f)
Solutions
- Lowercase the trust domain and strip characters outside [a-z0-9._-]
- Use a registered SPIRE trust domain name exactly as configured in the server
- Normalize the domain in config (trim whitespace, lowercase) before building IDs
Example fix
// before String spiffeId = "spiffe://Example.Org/ns/default/sa/app"; // after String spiffeId = "spiffe://example.org/ns/default/sa/app";
Defensive patterns
Strategy: validation
Validate before calling
static final Pattern TRUST_DOMAIN = Pattern.compile("^spiffe://[a-z0-9._-]+(/.*)?$");
static boolean trustDomainCharsetValid(String id) { return TRUST_DOMAIN.matcher(id).matches(); } Try / catch
try { validator.validateSpiffeId(id); } catch (SpiffeConnectionException e) { throw new IllegalArgumentException("Trust domain chars must be [a-z0-9._-]", e); } Prevention
- Lowercase and trim trust domain values when loading config
- Match the SPIRE server's registered trust domain exactly
When it happens
Trigger: validateSpiffeId called with an ID whose host contains characters outside [a-z0-9._-], e.g. 'spiffe://Example.org/service' (uppercase) or a domain containing ':'.
Common situations: Uppercase hostnames copied from company intranet domains; trust domains containing spaces or trailing punctuation from config typos; using a full hostname:port as the domain.
Understand the failure class
- Parsing and encoding errors: unexpected token, malformed input — why parsers reject input and how to find the real culprit.
Related errors
- SPIFFE ID must have a non-empty trust domain:
- SPIFFE ID trust domain exceeds maximum length of + MAX_TRUS
- Audiences must not be empty
- SPIFFE ID must not be empty
- SPIFFE ID exceeds maximum length of 2048 bytes: ${length}
AI-assisted analysis of quarkusio/quarkus@e1c734241f (2026-09-05).
Data as JSON: /api/errors/2a59ff0b65c1ceb5.
Report an issue: GitHub.