package domain

import (
	"context"
	"net"
	"strings"

	"github.com/tidbcloud/tiinf/monitor/tilog"
	"go.uber.org/zap"
)

type DnsVerifier interface {
	VerifyTXTRecord(ctx context.Context, domainName string, expectedValue string) (bool, error)
}

type DnsTxtVerifier struct{}

func NewDnsTxtVerifier() DnsVerifier {
	return &DnsTxtVerifier{}
}

func (v *DnsTxtVerifier) VerifyTXTRecord(ctx context.Context, domainName string, expectedValue string) (bool, error) {
	tilog.Info(ctx, "DnsTxtVerifier verifying TXT record", zap.String("domain", domainName), zap.String("expected", expectedValue))

	txtRecords, err := net.LookupTXT(domainName)
	tilog.Info(ctx, "DnsTxtVerifier LookupTXT result", zap.String("domain", domainName), zap.Any("txtRecords", txtRecords), zap.Any("err", err))
	if err != nil {
		dnsErr, ok := err.(*net.DNSError)
		if ok && dnsErr.IsNotFound {
			tilog.Info(ctx, "DnsTxtVerifier no TXT records found for domain", zap.String("domain", domainName))
			return false, nil
		}
		tilog.Error(ctx, "DnsTxtVerifier DNS lookup failed", zap.String("domain", domainName), zap.Error(err))
		return false, err
	}

	for _, record := range txtRecords {
		if strings.TrimSpace(record) == strings.TrimSpace(expectedValue) {
			tilog.Info(ctx, "DnsTxtVerifier TXT record matched", zap.String("domain", domainName))
			return true, nil
		}
	}

	tilog.Info(ctx, "DnsTxtVerifier no matching TXT record found", zap.String("domain", domainName), zap.Strings("records", txtRecords))
	return false, nil
}
