SonarSource/sonarqube · error · NotFoundException
Email configuration with id
Error message
Email configuration with id %s not found
What it means
EmailConfigurationService supports exactly one email configuration, stored under a fixed internal property key UNIQUE_EMAIL_CONFIGURATION_ID. throwIfNotUniqueConfigurationId throws NotFoundException for any id other than that fixed value. Since the ID is fixed by the platform, any caller-supplied id that differs is reported as 'not found'.
Solutions
- Call the list/get endpoint without an id first to discover the actual supported configuration id and use exactly that
- Delete with the same id returned by getConfiguration
- If migrating, recreate settings under the supported id rather than reusing legacy ids
Example fix
// before
deleteConfiguration("my-smtp-1")
// after
EmailConfiguration cfg = getConfiguration(UNIQUE_EMAIL_CONFIGURATION_ID);
deleteConfiguration(cfg.getId()); // the single supported id Defensive patterns
Strategy: validation
Validate before calling
// discover the supported id before read/delete
List<EmailConfiguration> configs = client.getEmailConfigurations();
if (configs.isEmpty()) throw new IllegalStateException("no email configuration exists");
String id = configs.get(0).getId(); // use this id, never a custom one Type guard
boolean isKnownEmailConfigId(String id, Set<String> knownIds) {
return id != null && knownIds.contains(id);
} Try / catch
try {
service.deleteConfiguration(id);
} catch (NotFoundException e) {
log.warn("Email configuration id '{}' not found; listing valid ids", id);
// fall back to listing and re-resolving the id
} Prevention
- Never invent email configuration ids — always read them from the get/list endpoint
- Remember the product supports a single email configuration
- Write 404 handling for id-based config APIs (email, github, gitlab) uniformly
When it happens
Trigger: GET/DELETE email configuration endpoints with an arbitrary id (e.g. copied from an old doc, a UUID, or 'default') instead of the single supported id; stale client code that cached a different id.
Common situations: API consumers assume multiple email configs exist and pass their own ids; integrations migrated from other products that allowed multiple SMTP configurations; typo in the reserved id.
Understand the failure class
Background: 'Could not be found', 'does not exist', 'not found in database': the resource-not-found family when an ID, slug, key, or URI lookup comes back empty — this error's family across 20 libraries.
Related errors
- Email configuration doesn't exist.
- Unknown type of SMTP secure connection:
- Unknown type of SMTP secure connection:
- Fail to decrypt the property
- Failed to send quality gate change email notification for…
AI-assisted analysis of SonarSource/sonarqube@184c821202 (2026-09-09).
Data as JSON: /api/errors/6598c586b4177907.
Report an issue: GitHub.
Appendix: source
Thrown at server/sonar-webserver-common/src/main/java/org/sonar/server/common/email/config/EmailConfigurationService.java:165
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_SMTP_PORT),
EmailConfigurationSecurityProtocol.valueOf(getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_SMTP_SECURE_CONNECTION)),
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_FROM),
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_FROM_NAME),
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_PREFIX),
EmailConfigurationAuthMethod.valueOf(getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_SMTP_AUTH_METHOD)),
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_SMTP_USERNAME),
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_SMTP_PASSWORD),
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_SMTP_OAUTH_HOST),
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_SMTP_OAUTH_CLIENTID),
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_SMTP_OAUTH_CLIENTSECRET),
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_SMTP_OAUTH_TENANT),
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_SMTP_OAUTH_SCOPE),
getStringInternalPropertyOrEmpty(dbSession, EMAIL_CONFIG_SMTP_OAUTH_GRANT));
}
private static void throwIfNotUniqueConfigurationId(String id) {
if (!UNIQUE_EMAIL_CONFIGURATION_ID.equals(id)) {
throw new NotFoundException(format("Email configuration with id %s not found", id));
}
}
private String getStringInternalPropertyOrEmpty(DbSession dbSession, String property) {
return dbClient.internalPropertiesDao().selectByKey(dbSession, property).orElse("");
}
public Optional<EmailConfiguration> findConfigurations() {
try (DbSession dbSession = dbClient.openSession(false)) {
if (configurationExists(dbSession)) {
return Optional.of(getConfiguration(UNIQUE_EMAIL_CONFIGURATION_ID, dbSession));
}
return Optional.empty();
}
}
public EmailConfiguration updateConfiguration(UpdateEmailConfigurationRequest updateRequest) {
try (DbSession dbSession = dbClient.openSession(true)) {View on GitHub (pinned to 184c821202)