Всем привет! Спешу поделиться кое-какой разработкой. Golang-клиент для NIC.ru API.

У нас есть тесная интеграция с nic.ru, так сложилось исторически, уверен, многие пользуются DNS-услугами nic.ru, может быть, не так активно как мы, но, так или иначе, для нас это важно, ранее у нас была разработка на Python, но, в последнее время мы активно переезжаем на Go, поэтому пришлось поддержать это дело. Буду рад, если кому-то это облегчит жизнь / сэкономить время.
Исходные данные
Изначально есть вот такой пакет для python https://pypi.org/project/nic-api/
Его написал наш коллега некоторое время назад, не утверждаю, что оно работает, но и не утверждаю обратное, у нас не было возможности это проверить, так как не было необходимости этим пользоваться, тем не менее, нельзя это не упомянуть.
Формат API описан тут, веселого там мало, всё на xml, но, унывать не приходится, приходится работать с тем, что дают.
Структуры
После чтения документации у нас получились следующие структуры
Request
Это общая структура для создания записей
type Request struct {
XMLName xml.Name `xml:"request"`
Text string `xml:",chardata"`
RrList *RrList `xml:"rr-list"`
}RrList
Структура, описывающая список записей
type RrList struct {
Text string `xml:",chardata"`
Rr []*RR `xml:"rr"`
}RR
Структура записи в DNS
type RR struct {
Text string `xml:",chardata"`
ID string `xml:"id,attr,omitempty"`
Name string `xml:"name"`
IdnName string `xml:"idn-name,omitempty"`
Ttl string `xml:"ttl"`
Type string `xml:"type"`
Soa *Soa `xml:"soa"`
Ns *Ns `xml:"ns"`
A *A `xml:"a"`
Txt *Txt `xml:"txt"`
Cname *Cname `xml:"cname"`
}A
Структура, хранящая в себе IPv4-адрес А-записи. У нас, пока что, нет IPv6, не вникали даже, как жить с этим делом в NIC.ru, но, тут главная особенность в том, что, по сравнению с CNAME, нет никаких атрибутов, значение хранится как текст
type A string
func (a *A) String() string {
return string(*a)
}CNAME
Структура, хранящая в себе каскадное имя, всё взято из API, IdnName может быть чем-то типа "наш-любимый-сайт.рф", в то время, как Name буде хранить значение, которые понятно всем узлам в сети Интернет, в данном случае:
xn-----6kccd6bhcmmf0dp7e6b4b.xn--p1aitype Cname struct {
Text string `xml:",chardata"`
Name string `xml:"name"`
IdnName string `xml:"idn-name,omitempty"`
}Service
Структура, отражающая сервис NIC.ru, тут отражён тариф, количество доменов и т.п, сервисная информация.
type Service struct {
Text string `xml:",chardata"`
Admin string `xml:"admin,attr"`
DomainsLimit string `xml:"domains-limit,attr"`
DomainsNum string `xml:"domains-num,attr"`
Enable string `xml:"enable,attr"`
HasPrimary string `xml:"has-primary,attr"`
Name string `xml:"name,attr"`
Payer string `xml:"payer,attr"`
Tariff string `xml:"tariff,attr"`
RrLimit string `xml:"rr-limit,attr"`
RrNum string `xml:"rr-num,attr"`
}SOA
Структура SOA-записи
type Soa struct {
Text string `xml:",chardata"`
Mname struct {
Text string `xml:",chardata"`
Name string `xml:"name"`
IdnName string `xml:"idn-name,omitempty"`
} `xml:"mname"`
Rname struct {
Text string `xml:",chardata"`
Name string `xml:"name"`
IdnName string `xml:"idn-name,omitempty"`
} `xml:"rname"`
Serial string `xml:"serial"`
Refresh string `xml:"refresh"`
Retry string `xml:"retry"`
Expire string `xml:"expire"`
Minimum string `xml:"minimum"`
}NS
Структура NS-записи
type Ns struct {
Text string `xml:",chardata"`
Name string `xml:"name"`
IdnName string `xml:"idn-name,omitempty"`
}TXT
Структура TXT-записи
type Ns struct {
Text string `xml:",chardata"`
Name string `xml:"name"`
IdnName string `xml:"idn-name,omitempty"`
}Zone
Структура зоны
type Zone struct {
Text string `xml:",chardata"`
Admin string `xml:"admin,attr"`
Enable string `xml:"enable,attr"`
HasChanges string `xml:"has-changes,attr"`
HasPrimary string `xml:"has-primary,attr"`
ID string `xml:"id,attr"`
IdnName string `xml:"idn-name,attr"`
Name string `xml:"name,attr"`
Payer string `xml:"payer,attr"`
Service string `xml:"service,attr"`
Rr []*RR `xml:"rr"`
}Revision
Структура ревизии
type Revision struct {
Text string `xml:",chardata"`
Date string `xml:"date,attr"`
Ip string `xml:"ip,attr"`
Number string `xml:"number,attr"`
}Error
Структура ошибки в ответе от API
type Error struct {
Text string `xml:",chardata"`
Code string `xml:"code,attr"`
}Response
Структура ответа от API
type Response struct {
XMLName xml.Name `xml:"response"`
Text string `xml:",chardata"`
Status string `xml:"status"`
Errors struct {
Text string `xml:",chardata"`
Error *error `xml:"error"`
} `xml:"errors"`
Data struct {
Text string `xml:",chardata"`
Service []*Service
Zone []*Zone `xml:"zone"`
Address []*A `xml:"address"`
Revision []*Revision `xml:"revision"`
} `xml:"data"`
}Как пользоваться
Клиент лежит тут https://github.com/maetx777/nic.ru-golang-client.git, готов к использованию. В examples описано как создавать и удалять A/CNAME записи, а также как скачать зону целиком.
Заключение
Изначально была идея делиться со всеми какими-то, полезными, по моему мнению, разработками, мы вынуждены много писать, иногда находим готовые решения, иногда - нет, и тогда мы пишем свои велосипеды.
Комментариев в коде пока что нет, в связи с тем, что сегодня карма резко понизилась из-за комментария в посте. С учётом стремительного ухудшения кармы, в скором времени я уже ничего не смогу писать тут, так что это завершающий пост.
Клиента обязательно разовьём, всё прокомментируем, разовьём ридми и сами будем им пользоваться непосредственно из гитхаба
Желаю всем мира и добра! Готов ответить на любые вопросы.
