apache/cassandra · critical · ConfigurationException
The seed provider lists no seeds.
Error message
The seed provider lists no seeds.
What it means
After the seed provider is instantiated, applySeedProvider() validates it returns at least one seed. An empty seed list makes cluster bootstrap impossible (a joining node has no contact points), so startup is aborted with this ConfigurationException.
Solutions
- Set a non-empty seeds list in cassandra.yaml (at least one live node address host:port)
- If seeds come from a template/variable, verify the variable was actually populated in the rendered config before startup
- For dynamic seed providers, fix the underlying discovery source (DNS, cloud metadata) or fall back to static seeds
Example fix
// cassandra.yaml before
seed_provider:
- class_name: org.apache.cassandra.locator.SimpleSeedProvider
parameters:
- seeds: ""
// after
seed_provider:
- class_name: org.apache.cassandra.locator.SimpleSeedProvider
parameters:
- seeds: "10.0.1.1:7000" Defensive patterns
Strategy: validation
Validate before calling
if (conf.seed_provider.parameters.isEmpty() || String.valueOf(conf.seed_provider.parameters.get("seeds")).isBlank())
throw new IllegalStateException("seed_provider seeds parameter must contain at least one address"); Try / catch
try { DatabaseDescriptor.applySeedProvider(); } catch (ConfigurationException e) { /* supply non-empty seeds */ } Prevention
- Fail deploys when template variables for seeds render empty
- Keep at least 2-3 static seeds across DCs in the config
- Ping seed hosts from new nodes as a pre-join check
When it happens
Trigger: applySeedProvider() called when seedProvider.getSeeds().isEmpty() — e.g. seeds parameter is an empty string, contains only whitespace, or a custom provider returns an empty set (e.g. dynamic provider with no resolvable entries).
Common situations: seed_provider parameters with `seeds: ""` produced by a templating engine with unset variables; environment-variable substitution failing at deploy time; custom seed provider (e.g. cloud-auto-discovery) returning nothing because metadata API or DNS lookup failed.
Understand the failure class
Background: "must not be empty", "cannot be empty" — required-field validation errors across open-source libraries — this error's family across 41 libraries.
Related errors
- Error while getting seed node list
- Fatal configuration error; unable to start server. See…
- seeds configuration is missing; a minimum of one seed is…
- Seeds list is now empty!
- A maximum number of tokens per node is supported
AI-assisted analysis of apache/cassandra@88fd0f6a0e (2026-09-10).
Data as JSON: /api/errors/74520ea7cedb8d03.
Report an issue: GitHub.
Appendix: source
Thrown at src/java/org/apache/cassandra/config/DatabaseDescriptor.java:1678
{
// load the seeds for node contact points
if (conf.seed_provider == null)
{
throw new ConfigurationException("seeds configuration is missing; a minimum of one seed is required.", false);
}
try
{
Class<? extends SeedProvider> seedProviderClass =
FBUtilities.classForNameWithoutInitialization(conf.seed_provider.class_name, "seed provider", SeedProvider.class);
seedProvider = (SeedProvider) seedProviderClass.getConstructor(Map.class).newInstance(conf.seed_provider.parameters);
}
// there are about 5 checked exceptions that could be thrown here.
catch (Exception e)
{
throw new ConfigurationException(e.getMessage() + "\nFatal configuration error; unable to start server. See log for stacktrace.", true);
}
if (seedProvider.getSeeds().size() == 0)
throw new ConfigurationException("The seed provider lists no seeds.", false);
}
@VisibleForTesting
static void checkForLowestAcceptedTimeouts(Config conf)
{
if (conf.read_request_timeout.toMilliseconds() < LOWEST_ACCEPTED_TIMEOUT.toMilliseconds())
{
logInfo("read_request_timeout", conf.read_request_timeout, LOWEST_ACCEPTED_TIMEOUT);
conf.read_request_timeout = new DurationSpec.LongMillisecondsBound("10ms");
}
if (conf.range_request_timeout.toMilliseconds() < LOWEST_ACCEPTED_TIMEOUT.toMilliseconds())
{
logInfo("range_request_timeout", conf.range_request_timeout, LOWEST_ACCEPTED_TIMEOUT);
conf.range_request_timeout = new DurationSpec.LongMillisecondsBound("10ms");
}
if (conf.request_timeout.toMilliseconds() < LOWEST_ACCEPTED_TIMEOUT.toMilliseconds())View on GitHub (pinned to 88fd0f6a0e)