Generate a BIND-format domains.conf file alongside catalog zones. New input properties: file= (zone data path) and dnssec (bare flag). When --bind-conf is set, every zone must have file= or it errors. Renames ZoneEntry.File to ZonesFile (input path for error messages) and adds ZoneFile (BIND file path) and DNSSEC (bool) fields.
65 lines
1.8 KiB
Go
65 lines
1.8 KiB
Go
package main
|
|
|
|
import (
|
|
"fmt"
|
|
"os"
|
|
"sort"
|
|
"strings"
|
|
)
|
|
|
|
// generateBindConf produces a BIND domains.conf from all zone entries.
|
|
// Zones are sorted alphabetically. Each zone block uses 8-space indentation.
|
|
// DNSSEC zones get dnssec-policy and inline-signing directives on the file line.
|
|
func generateBindConf(entries []ZoneEntry) string {
|
|
sorted := make([]ZoneEntry, len(entries))
|
|
copy(sorted, entries)
|
|
sort.Slice(sorted, func(i, j int) bool {
|
|
return sorted[i].Zone < sorted[j].Zone
|
|
})
|
|
|
|
var b strings.Builder
|
|
b.WriteString("# THIS FILE IS GENERATED BY catalog-zone-gen\n")
|
|
b.WriteString("#=============================================\n")
|
|
b.WriteString("#\n")
|
|
|
|
for _, entry := range sorted {
|
|
// Strip trailing dot for BIND zone name
|
|
zoneName := strings.TrimSuffix(entry.Zone, ".")
|
|
|
|
fmt.Fprintf(&b, "zone \"%s\" {\n", zoneName)
|
|
b.WriteString(" type master;\n")
|
|
|
|
fileLine := fmt.Sprintf(" file \"%s\";", entry.ZoneFile)
|
|
if entry.DNSSEC {
|
|
fileLine += " dnssec-policy standard; inline-signing yes;"
|
|
}
|
|
b.WriteString(fileLine + "\n")
|
|
b.WriteString("};\n")
|
|
}
|
|
|
|
return b.String()
|
|
}
|
|
|
|
// validateBindConf checks that every zone entry has a non-empty ZoneFile.
|
|
func validateBindConf(entries []ZoneEntry) error {
|
|
for _, entry := range entries {
|
|
if entry.ZoneFile == "" {
|
|
return fmt.Errorf("%s:%d: zone %s missing file= property (required for --bind-conf)",
|
|
entry.ZonesFile, entry.Line, entry.Zone)
|
|
}
|
|
}
|
|
return nil
|
|
}
|
|
|
|
// writeBindConf validates entries and writes the BIND config to path.
|
|
func writeBindConf(path string, entries []ZoneEntry) error {
|
|
if err := validateBindConf(entries); err != nil {
|
|
return err
|
|
}
|
|
content := generateBindConf(entries)
|
|
if err := os.WriteFile(path, []byte(content), 0o644); err != nil {
|
|
return fmt.Errorf("writing bind config %s: %w", path, err)
|
|
}
|
|
return nil
|
|
}
|