func answerCNAME(q *dns.Question, v *DNSValue) (dns.RR, string) { // Info: http://en.wikipedia.org/wiki/CNAME_record answer := new(dns.CNAME) answer.Header().Name = q.Name answer.Header().Rrtype = dns.TypeCNAME answer.Header().Class = dns.ClassINET answer.Target = strings.TrimSuffix(v.Value, ".") + "." return answer, answer.Target }
func (c *config) flattenCNAME(in *dns.CNAME) ([]dns.RR, error) { // TODO: cache CNAME lookups h := in.Header() answers := []dns.RR{} m := new(dns.Msg) m.SetQuestion(in.Target, dns.TypeA) m.RecursionDesired = true d := new(dns.Client) record, _, err := d.Exchange(m, c.resolver) // TODO: try multiple resolvers if err != nil { return nil, err } if record == nil || record.Rcode == dns.RcodeNameError || record.Rcode != dns.RcodeSuccess { return nil, fmt.Errorf("Record error code %s: %s", record.Rcode, err.Error()) } for _, a := range record.Answer { if r, ok := a.(*dns.A); ok { out := new(dns.A) out.Hdr = dns.RR_Header{Name: h.Name, Rrtype: dns.TypeA, Class: dns.ClassINET, Ttl: 300} out.A = r.A answers = append(answers, out) } } return answers, nil }