diff --git a/pkg/realDynDns/realDynDns.go b/pkg/realDynDns/realDynDns.go index 3de1db1..15cd4dd 100644 --- a/pkg/realDynDns/realDynDns.go +++ b/pkg/realDynDns/realDynDns.go @@ -3,6 +3,7 @@ package realDynDns import ( "fmt" "log/slog" + "sync" "time" "realdnydns/pkg/config" @@ -70,63 +71,82 @@ func (c *ChangeDetector) detectAndApplyChanges() (int, error) { return 0, err } - var numberUpdated int + var wg sync.WaitGroup + + numberUpdatedChannel := make(chan int) for _, domain := range c.domains { for _, subdomain := range domain.Subdomains { - c.logger.Info("Checking record", - slog.String("tld", domain.TLD), - slog.String("subdomain", subdomain), - ) - currentRecord, err := c.dnsProvider.GetRecord(domain.TLD, subdomain) - if err != nil { - c.logger.Error("Failed to retrieve record", - slog.String("error", err.Error()), + wg.Add(1) + + go func(domain config.DomainConfig, subdomain string) { + defer wg.Done() + + c.logger.Info("Checking record", slog.String("tld", domain.TLD), slog.String("subdomain", subdomain), ) - continue - } - - if currentRecord.IP != externalIp.String() { - c.logger.Info("Record has changed", - slog.String("tld", domain.TLD), - slog.String("subdomain", subdomain), - slog.String("current_ip", currentRecord.IP), - slog.String("external_ip", externalIp.String()), - ) - - err = c.notificationProvider.SendNotification( - fmt.Sprintf("Update %s.%s", subdomain, domain.TLD), - fmt.Sprintf("The IP of %s has changed from %s to %s", domain.TLD, currentRecord.IP, externalIp.String()), - ) + currentRecord, err := c.dnsProvider.GetRecord(domain.TLD, subdomain) if err != nil { - c.logger.Warn("Failed to send notification", - slog.String("error", err.Error()), - ) - continue - } - - c.logger.Info("Updating record", - slog.String("tld", domain.TLD), - slog.String("subdomain", subdomain), - slog.String("current_ip", currentRecord.IP), - slog.String("external_ip", externalIp.String()), - ) - _, err = c.dnsProvider.UpdateRecord(domain.TLD, subdomain, externalIp, currentRecord.TTL, currentRecord.Prio, currentRecord.Disabled) - if err != nil { - c.logger.Error("Failed to update record", + c.logger.Error("Failed to retrieve record", slog.String("error", err.Error()), slog.String("tld", domain.TLD), slog.String("subdomain", subdomain), ) - continue + return } - numberUpdated++ - } + + if currentRecord.IP != externalIp.String() { + c.logger.Info("Record has changed", + slog.String("tld", domain.TLD), + slog.String("subdomain", subdomain), + slog.String("current_ip", currentRecord.IP), + slog.String("external_ip", externalIp.String()), + ) + + err = c.notificationProvider.SendNotification( + fmt.Sprintf("Update %s.%s", subdomain, domain.TLD), + fmt.Sprintf("The IP of %s has changed from %s to %s", domain.TLD, currentRecord.IP, externalIp.String()), + ) + if err != nil { + c.logger.Warn("Failed to send notification", + slog.String("error", err.Error()), + ) + return + } + + c.logger.Info("Updating record", + slog.String("tld", domain.TLD), + slog.String("subdomain", subdomain), + slog.String("current_ip", currentRecord.IP), + slog.String("external_ip", externalIp.String()), + ) + _, err = c.dnsProvider.UpdateRecord(domain.TLD, subdomain, externalIp, currentRecord.TTL, currentRecord.Prio, currentRecord.Disabled) + if err != nil { + c.logger.Error("Failed to update record", + slog.String("error", err.Error()), + slog.String("tld", domain.TLD), + slog.String("subdomain", subdomain), + ) + return + } + + numberUpdatedChannel <- 1 + } + }(domain, subdomain) } } + go func() { + wg.Wait() + close(numberUpdatedChannel) + }() + + numberUpdated := 0 + for v := range numberUpdatedChannel { + numberUpdated += v + } + c.logger.Info("Run completed", slog.Int("number_of_changes", numberUpdated)) return numberUpdated, nil }