forked from xellio/whois
-
Notifications
You must be signed in to change notification settings - Fork 0
/
domain.go
93 lines (77 loc) · 2.02 KB
/
domain.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
package whois
import (
"strings"
)
//
// Domain performs a whois query for the given domain or hostname.
//
func Domain(domainOrHost string, cache *KVCache) (result QueryResult, err error) {
domain, tld := domainTld(domainOrHost)
if cache != nil {
var found bool
result, found = cache.Get(domain)
if found {
return
}
}
whoisServer := IanaServer
result, _, err = findWhois(whoisServer, tld, domain)
if cache != nil {
cache.Add(domain, result)
}
return
}
//
// domainTld returns the domain and tld from the given domain.
// it removes all hosts related parts from the fqdn.
//
func domainTld(domain string) (string, string) {
domainParts := strings.Split(domain, ".")
for i := 1; i < len(domainParts)-2; i++ {
eTld := strings.Join(domainParts[i:], ".")
tld, ok := tldlist[eTld]
if ok && tld {
return strings.Join(domainParts[i-1:], "."), eTld
}
}
// in theory this should no happen but use the simple
// way to have at least a fallback
return strings.Join(domainParts[len(domainParts)-2:], "."), domainParts[len(domainParts)-1]
}
//
// findWhois loops ofer whois servers and tries to find the server responsible for the the domain.
//
// -> start @whois.iana.org via tld
// -> fetch data from whois tld server
// -> loop as long a registrant whois server is set in the records
//
func findWhois(server string, queryData string, domain string) (parsedData QueryResult, whoisServer string, err error) {
data, err := query(server, queryData)
if err != nil {
return
}
var format string
switch server {
case DenicServer:
format = FormatDenic
case IanaServer:
format = FormatIana
default:
format = FormatIcaan
}
parsedData = Parse(data, format)
parsedData.target = domain
whoisServer = server
for _, d := range parsedData.Records() {
for _, key := range []string{"whois", "Registrar WHOIS Server"} {
whois, ok := d.data[key]
if ok && len(whois) > 0 {
whoisServer := whois + ":43"
if whoisServer != server {
return findWhois(whoisServer, domain, domain)
}
}
}
}
return
}