mirror of
https://github.com/StackExchange/dnscontrol.git
synced 2024-05-11 05:55:12 +00:00
Seperate create-domains command (#21)
* removing auto-create from gcloud * adding create-domains command * implement DomainCreator for r53
This commit is contained in:
17
main.go
17
main.go
@@ -133,6 +133,23 @@ func main() {
|
||||
fmt.Printf("Initialized %d registrars and %d dns service providers.\n", len(registrars), len(dsps))
|
||||
anyErrors, totalCorrections := false, 0
|
||||
switch command {
|
||||
case "create-domains":
|
||||
for _, domain := range dnsConfig.Domains {
|
||||
fmt.Println("*** ", domain.Name)
|
||||
for prov := range domain.DNSProviders {
|
||||
dsp, ok := dsps[prov]
|
||||
if !ok {
|
||||
log.Fatalf("DSP %s not declared.", prov)
|
||||
}
|
||||
if creator, ok := dsp.(providers.DomainCreator); ok {
|
||||
fmt.Println(" -", prov)
|
||||
err := creator.EnsureDomainExists(domain.Name)
|
||||
if err != nil {
|
||||
fmt.Printf("Error creating domain: %s\n", err)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
case "preview", "push":
|
||||
DomainLoop:
|
||||
for _, domain := range dnsConfig.Domains {
|
||||
|
@@ -4,7 +4,6 @@ import (
|
||||
"context"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"log"
|
||||
"strings"
|
||||
|
||||
"golang.org/x/oauth2"
|
||||
@@ -86,10 +85,6 @@ func (g *gcloud) getZone(domain string) (*dns.ManagedZone, error) {
|
||||
func (g *gcloud) GetNameservers(domain string) ([]*models.Nameserver, error) {
|
||||
zone, err := g.getZone(domain)
|
||||
if err != nil {
|
||||
if _, ok := err.(errNoExist); ok {
|
||||
log.Printf("WARNING: Domain %s is not on your google cloud account. Dnscontrol will add it, but you will need to run a second time to configure nameservers properly.", domain)
|
||||
return nil, nil
|
||||
}
|
||||
return nil, err
|
||||
}
|
||||
return models.StringsToNameservers(zone.NameServers), nil
|
||||
@@ -108,16 +103,10 @@ func keyForRec(r *models.RecordConfig) key {
|
||||
}
|
||||
|
||||
func (g *gcloud) GetDomainCorrections(dc *models.DomainConfig) ([]*models.Correction, error) {
|
||||
corrections := []*models.Correction{}
|
||||
|
||||
rrs, zoneName, err := g.getRecords(dc.Name)
|
||||
if err != nil {
|
||||
if _, ok := err.(errNoExist); ok {
|
||||
c, zn := g.addZone(dc.Name)
|
||||
corrections = append(corrections, c)
|
||||
zoneName = zn
|
||||
} else {
|
||||
return nil, err
|
||||
}
|
||||
return nil, err
|
||||
}
|
||||
//convert to dnscontrol RecordConfig format
|
||||
existingRecords := []diff.Record{}
|
||||
@@ -200,11 +189,10 @@ func (g *gcloud) GetDomainCorrections(dc *models.DomainConfig) ([]*models.Correc
|
||||
_, err := g.client.Changes.Create(g.project, zoneName, chg).Do()
|
||||
return err
|
||||
}
|
||||
corrections = append(corrections, &models.Correction{
|
||||
return []*models.Correction{{
|
||||
Msg: desc,
|
||||
F: runChange,
|
||||
})
|
||||
return corrections, nil
|
||||
}}, nil
|
||||
}
|
||||
|
||||
func (g *gcloud) getRecords(domain string) ([]*dns.ResourceRecordSet, string, error) {
|
||||
@@ -236,19 +224,23 @@ func (g *gcloud) getRecords(domain string) ([]*dns.ResourceRecordSet, string, er
|
||||
return sets, zone.Name, nil
|
||||
}
|
||||
|
||||
func (g *gcloud) addZone(name string) (*models.Correction, string) {
|
||||
mz := &dns.ManagedZone{}
|
||||
mz.DnsName = name + "."
|
||||
mz.Name = strings.Replace(name, ".", "-", -1)
|
||||
mz.Description = "zone added by dnscontrol"
|
||||
return &models.Correction{
|
||||
Msg: fmt.Sprintf("Add zone for %s", name),
|
||||
F: func() error {
|
||||
_, err := g.client.ManagedZones.Create(g.project, mz).Do()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
},
|
||||
}, mz.Name
|
||||
func (g *gcloud) EnsureDomainExists(domain string) error {
|
||||
z, err := g.getZone(domain)
|
||||
if err != nil {
|
||||
if _, ok := err.(errNoExist); !ok {
|
||||
return err
|
||||
}
|
||||
}
|
||||
if z != nil {
|
||||
return nil
|
||||
}
|
||||
fmt.Printf("Adding zone for %s to gcloud account\n", domain)
|
||||
mz := &dns.ManagedZone{
|
||||
DnsName: domain + ".",
|
||||
Name: strings.Replace(domain, ".", "-", -1),
|
||||
Description: "zone added by dnscontrol",
|
||||
}
|
||||
g.zones = nil //reset cache
|
||||
_, err = g.client.ManagedZones.Create(g.project, mz).Do()
|
||||
return err
|
||||
}
|
||||
|
@@ -19,6 +19,12 @@ type DNSServiceProvider interface {
|
||||
GetDomainCorrections(dc *models.DomainConfig) ([]*models.Correction, error)
|
||||
}
|
||||
|
||||
//DomainCreator should be implemented by providers that have the ability to add domains to an account. the create-domains command
|
||||
//can be run to ensure all domains are present before running preview/push
|
||||
type DomainCreator interface {
|
||||
EnsureDomainExists(domain string) error
|
||||
}
|
||||
|
||||
//RegistrarInitializer is a function to create a registrar. Function will be passed the unprocessed json payload from the configuration file for the given provider.
|
||||
type RegistrarInitializer func(map[string]string) (Registrar, error)
|
||||
|
||||
|
@@ -3,7 +3,6 @@ package route53
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"log"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
@@ -78,14 +77,21 @@ func getKey(r diff.Record) key {
|
||||
return key{r.GetName(), r.GetType()}
|
||||
}
|
||||
|
||||
type errNoExist struct {
|
||||
domain string
|
||||
}
|
||||
|
||||
func (e errNoExist) Error() string {
|
||||
return fmt.Sprintf("Domain %s not found in your route 53 account", e.domain)
|
||||
}
|
||||
|
||||
func (r *route53Provider) GetNameservers(domain string) ([]*models.Nameserver, error) {
|
||||
if err := r.getZones(); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
zone, ok := r.zones[domain]
|
||||
if !ok {
|
||||
log.Printf("WARNING: Domain %s is not on your route 53 account. Dnscontrol will add it, but you will need to run a second time to configure nameservers properly.", domain)
|
||||
return nil, nil
|
||||
return nil, errNoExist{domain}
|
||||
}
|
||||
z, err := r.client.GetHostedZone(&r53.GetHostedZoneInput{Id: zone.Id})
|
||||
if err != nil {
|
||||
@@ -107,24 +113,7 @@ func (r *route53Provider) GetDomainCorrections(dc *models.DomainConfig) ([]*mode
|
||||
zone, ok := r.zones[dc.Name]
|
||||
// add zone if it doesn't exist
|
||||
if !ok {
|
||||
//add correction to add zone
|
||||
corrections = append(corrections,
|
||||
&models.Correction{
|
||||
Msg: "Add zone to aws",
|
||||
F: func() error {
|
||||
in := &r53.CreateHostedZoneInput{
|
||||
Name: &dc.Name,
|
||||
CallerReference: sPtr(fmt.Sprint(time.Now().UnixNano())),
|
||||
}
|
||||
out, err := r.client.CreateHostedZone(in)
|
||||
zone = out.HostedZone
|
||||
return err
|
||||
},
|
||||
})
|
||||
//fake zone
|
||||
zone = &r53.HostedZone{
|
||||
Id: sPtr(""),
|
||||
}
|
||||
return nil, errNoExist{dc.Name}
|
||||
}
|
||||
|
||||
records, err := r.fetchRecordSets(zone.Id)
|
||||
@@ -285,3 +274,21 @@ func unescape(s *string) string {
|
||||
name = strings.Replace(name, `\052`, "*", -1) //TODO: escape all octal sequences
|
||||
return name
|
||||
}
|
||||
|
||||
func (r *route53Provider) EnsureDomainExists(domain string) error {
|
||||
err := r.getZones()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if _, ok := r.zones[domain]; ok {
|
||||
return nil
|
||||
}
|
||||
fmt.Printf("Adding zone for %s to route 53 account\n", domain)
|
||||
in := &r53.CreateHostedZoneInput{
|
||||
Name: &domain,
|
||||
CallerReference: sPtr(fmt.Sprint(time.Now().UnixNano())),
|
||||
}
|
||||
_, err = r.client.CreateHostedZone(in)
|
||||
return err
|
||||
|
||||
}
|
||||
|
Reference in New Issue
Block a user