TechnitiumSoftware/DnsServer · error · DnsServerException

Failed to initialize Cluster: the zone '{clusterZoneInfo.Nam

Error message

Failed to initialize Cluster: the zone '{clusterZoneInfo.Name}' already exists and is not a Primary zone. Please delete the existing zone or use a different Cluster domain name.

What it means

Thrown by InitializeCluster when the zone matching the requested cluster domain already exists in the AuthZoneManager but its type is not AuthZoneType.Primary (e.g., it is Secondary, Stub, Forwarder, or Catalog). The cluster requires full control over a writable primary zone to store NS/A/AAAA/TLSA records for every node, so a non-primary zone is rejected. The guard is an else-if on the GetAuthZoneInfo lookup result.

Source

Thrown at DnsServerCore/Cluster/ClusterManager.cs:558

                else
                    serverDomain = string.Concat(serverDomain.AsSpan(0, x), ".", clusterDomain);
            }

            Uri primaryNodeUrl = new Uri($"https://{serverDomain}:{_dnsWebService.WebServiceTlsPort}/");

            ClusterNode selfPrimaryNode = new ClusterNode(this, RandomNumberGenerator.GetInt32(int.MaxValue), primaryNodeUrl, primaryNodeIpAddresses, ClusterNodeType.Primary, ClusterNodeState.Self);

            //create cluster primary zone
            AuthZoneInfo clusterZoneInfo = _dnsWebService.DnsServer.AuthZoneManager.GetAuthZoneInfo(clusterDomain);
            if (clusterZoneInfo is null)
            {
                clusterZoneInfo = _dnsWebService.DnsServer.AuthZoneManager.CreatePrimaryZone(clusterDomain);
                if (clusterZoneInfo is null)
                    throw new DnsServerException($"Failed to initialize Cluster: failed to create the Cluster zone '{clusterDomain}'. Please try again.");
            }
            else if (clusterZoneInfo.Type != AuthZoneType.Primary)
            {
                throw new DnsServerException($"Failed to initialize Cluster: the zone '{clusterZoneInfo.Name}' already exists and is not a Primary zone. Please delete the existing zone or use a different Cluster domain name.");
            }

            //create cluster catalog zone
            string clusterCatalogDomain = "cluster-catalog." + clusterDomain;

            AuthZoneInfo clusterCatalogZoneInfo = _dnsWebService.DnsServer.AuthZoneManager.GetAuthZoneInfo(clusterCatalogDomain);
            if (clusterCatalogZoneInfo is null)
            {
                clusterCatalogZoneInfo = _dnsWebService.DnsServer.AuthZoneManager.CreateCatalogZone(clusterCatalogDomain);
                if (clusterCatalogZoneInfo is null)
                    throw new DnsServerException($"Failed to initialize Cluster: failed to create the Cluster Catalog zone '{clusterCatalogDomain}'. Please try again.");
            }
            else if (clusterCatalogZoneInfo.Type != AuthZoneType.Catalog)
            {
                throw new DnsServerException($"Failed to initialize Cluster: the zone '{clusterCatalogZoneInfo.Name}' already exists and is not a Catalog zone. Please delete the existing zone or use a different Cluster domain name.");
            }

            //set cluster primary zone permissions

View on GitHub (pinned to d0484b6c1e)

Solutions

  1. Delete the existing non-primary zone (via the web UI Zones page or AuthZoneManager) so InitializeCluster can create a fresh primary zone, then retry.
  2. Choose a different cluster domain name that does not collide with any existing zone.
  3. If the existing zone should be the cluster zone, convert it to a Primary zone first and retry initialization.

Example fix

// before
_dnsWebService.ClusterManager.InitializeCluster("dns.example.com", ips, session);
// after — remove conflicting zone first
var zone = _dnsWebService.DnsServer.AuthZoneManager.GetAuthZoneInfo("dns.example.com");
if (zone is not null && zone.Type != AuthZoneType.Primary)
    _dnsWebService.DnsServer.AuthZoneManager.DeleteZone(zone.Name);
_dnsWebService.ClusterManager.InitializeCluster("dns.example.com", ips, session);
Defensive patterns

Strategy: validation

Validate before calling

// Check for a conflicting non-primary zone before initializing
string clusterDomain = "dns.example.com";
var zone = _dnsWebService.DnsServer.AuthZoneManager.GetAuthZoneInfo(clusterDomain);
if (zone is not null && zone.Type != AuthZoneType.Primary)
    throw new InvalidOperationException($"Zone '{zone.Name}' exists as {zone.Type}; delete it or pick another domain before InitializeCluster.");
_dnsWebService.ClusterManager.InitializeCluster(clusterDomain, ips, session);

Type guard

static bool IsZoneSafeForClusterInit(AuthZoneInfo zone, string clusterDomain)
    => zone is null || (zone.Name.Equals(clusterDomain, StringComparison.OrdinalIgnoreCase) && zone.Type == AuthZoneType.Primary);

Try / catch

try
{
    _dnsWebService.ClusterManager.InitializeCluster(clusterDomain, ips, session);
}
catch (DnsServerException ex) when (ex.Message.Contains("already exists and is not a Primary zone"))
{
    // surface to user: delete the conflicting zone or change the domain
    throw new InvalidOperationException("Cluster domain conflicts with an existing non-primary zone. Delete it or use a different domain.", ex);
}

Prevention

When it happens

Trigger: InitializeCluster(clusterDomain, ...) is called where clusterDomain names a zone that AuthZoneManager.GetAuthZoneInfo resolves to a non-Primary zone. The primary-creation branch is skipped because the zone is non-null, and the else-if at line 556 fires because clusterZoneInfo.Type != AuthZoneType.Primary.

Common situations: Re-using a domain that was previously configured as a secondary or stub zone; leftover zone from a partially torn-down cluster; zone name collision after importing a backup config from another server; manually pre-creating a forwarder zone with the same name.

Related errors


AI-assisted analysis of TechnitiumSoftware/DnsServer@d0484b6c1e (2026-08-13). Data as JSON: /api/errors/a25c844145c643db. Report an issue: GitHub.