Скрипт для обновления DNS записей CloudFlare
Пост называется "опять не спится" или "как бесплатно завернуть домен второго уровня на ваш домашний динамический IP адрес". Для чего это вам может быть нужно? Вариантов много. Например, это возможность впоследствии поднять дома какие-нибудь сервисы. Например, создать собственное облако для хранения и расшаривания файлов и смотреть в пути фильмы, лежащие на домашнем жёстком диске или развернуть личный блог, сайт-визитку, сервис умного дома, да хоть устроить станцию онлайн вещания - всё ограничивается вашей фантазией, вариантов использования может найтись масса, когда существует возможность.
Начну издалека. Мне не нравится, когда с меня пытаются любыми способами вытянуть деньги и повышают цену на какой-то продукт в два или три раза без особых на то оснований. Конечно, я могу и не знать об этих основаниях, но скорее всего цена повысилась исходя из принципа "да куда вы нахрен денетесь с подводной лодки?". Я имею в виду интернет от билайн, точнее их услугу предоставления белого IP адреса.
Много лет я пользовался интернетом от Dom.ru, меня всё устраивало, но меня достали менеджеры билайна, пытающиеся обратить меня в свою веру. Мне звонили раз 15 и предлагали перейти на их интернет. Свидетели Святого Коннектия, честное слово! В конечном итоге я разобрался в тарифах и это действительно оказалось выгодно.
За Dom.ru (интернет + телевидение) я платил раз в месяц 550 рублей + 20 рублей за белый адрес, затем мне пришло письмо, где меня уведомляли, что стоимость повышают и я буду платить 600 с хвостиком за то же самое. Что-ж, я пришёл в оффис и положил партбилет тв карту на стол, заявив, что их телевидением я всё равно пользовался два раза за последние несколько лет и хотел бы от него отказаться. Тогда мне предложили какую-то сказочную скидку в 20 процентов на ближайшие полгода, оставив тариф прежним. Я согласился. Примерно через три месяца мне снова пришло письмо о том, что я опять должен платить больше. На этот раз я настаивал и перешёл на тариф без телевидения. Скорость интернета увеличилась в два раза, но платил я по-прежнему примерно ту же сумму в 570 рублей. Прошло ещё два или три месяца и я снова получил письмо, где было сказано, что теперь уже точно стоимость услуг будет около 670 рублей в месяц. Казалось бы, какие-то 100 рублей в месяц ничего не решают, но это было делом принципа.
На протяжении всех этих событий я параллельно отслеживал, что может предложить билайн в отношении домашнего интернета. Цены и условия были довольно заманчивыми, но вот стоимость белого IP адреса, который мне действительно нужен, менее чем за год выросла с 50-ти до 150-ти рублей. Как несложно заметить, это 1800 рублей в год и при этом никто не обещает, что стоимость этой услуги не будет повышаться и дальше. Меня это не устраивало. В остальном тариф позволял производить оплату за домашний интернет, свой телефон и телефон жены на один счёт, что несомненно, было очень удобно, да и так получалось, что в итоге я на этом экономил полее 5600 в год. Нужно было как-то решать задачу с IP адресом.
Мой домен был делегирован на Яндекс. У них есть сервис "Почта для домена", который меня всем устраивал. Тогда я почитал документацию на их API и написал скрипт, которому в параметрах можно было передать список DNS записей и IP адрес, после чего скрипт обновлял их. Конечно, подобных скриптов было навалом, но чего я только не видел - python, perl, php и, прости, господи, npm (спасибо, что без gradle для сборки обошлось)!!! Импортирование нескольких библиотек, развесистые зависимости - и всё это для того, чтобы сделать пару вызовов курлом к апи. У меня аллергия на вещи, которые для решения простых задач требуют библиотеки валидации ввода, работы с json, ещё чего-то мне неизвестного и, заодно, библиотеку поддержки цыган с медведями и балалайками просто так, на всякий случай. Это всё-равно что в булочную за углом ездить на карьерном самосвале.
Конечно, нашёл я и варианты, написанные на bash, но пара просмотренных мной не подходили, поскольку так же использовали сущности, которые мне ставить не хотелось, либо представлялось затруднительным. Принцип был простой - скрипт должен работать на роутере и использовать минимум из того, что можно поставить на роутер. А если уж писать свой велосипед, то вполне можно добавить немного магии, локального блекджека и падших женщин, не прибегая к импорту внешних "цыган, медведей и балалаек". В скрипте я реализовал нормальное многоуровневое логирование (что существенно облегчило отладку, благо, метод этот я написал уже очень давно) и возможность обновлять сразу несколько записей, передавая их через запятую. Например, можно было написать test,gw01,*,@.shumiloff.ru и скрипт обновил бы сразу четыре записи, что экономило время, не требовало множества дополнительных запусков и, как следствие, дополнительных вызовов API.
Я перешёл на билайн и скрипт работал как часы, исправно обновляя необходимые DNS записи, что позволяло мне постоянно иметь доступ извне к своей машине и пользоваться теми сервисами, которые крутились на домашнем сервисе. Этот блог был в их числе. В какой-то момент я причесал код, убрал лишнее, добавил помощь, readme и выложил это всё на github.
Всё шло замечательно, пока в один прекрасный момент Яндекс без объявления войны не мигрировал мой домен с почты для домена на Яндекс.Коннект. Нужно было срочно решать, что делать с блогом и я, посидев ночью, перенёс его на Github Pages. Но это решало лишь малую часть проблем. Мне по-прежнему нужен был доступ извне к своим сервисам, домашним проектам и данным. Да даже музыка, которую я порой слушаю в процессе работы или передвижения по городу, воспроизводится с домашнего сервера.
Я покопался на гитхабе и нашёл некий репозиторий, не разобравшись в содержимом которого, я решил, что задача написания скрипта для обновления DNS записей реализуема и для Яндекс.Коннект. Спойлер: это не так. Я начал писать, параллельно изучая документацию к API Яндекс.Коннект, разобрался с авторизацией через OAuth 2, написал кусок кода, но потом с удивлением для себя обнаружил, что возможности изменить DNS записи просто нет! Её не реализовали. Параллельно на гитхабе в issues мне написал один человек - мол, спасибо за скрипт, всё работало, но после переноса на коннект перестало. Мы с ним пообщались и оказалось, что после его запроса в техподдержку яндекса, его домен перенесли обратно, в сервис "Почта для домена". Я тоже написал в поддержку, объяснил ситуацию. Мне пришёл автоматический ответ - тикет создан, номер такой-то, обращение будет рассмотрено в срок от трёх до пяти рабочих дней. Прошла неделя, воз и ныне там, ни ответа, ни привета.
После отправки письма в поддержку, я начал искать альтернативные решения и в конце-концов, решил взять себе ещё один бесплатный домен второго уровня на http://freenom.com/. Был удивлён, когда узнал, что пара моих знакомых, разбирающихся в теме не знала об этой возможности. Когда-то я уже брал там пару доменов под свои домашние проекты, это было ещё лет 6 тому назад, хотя я и был наслышан о том, что в один прекрасный момент этот домен просто могут прикрыть и потребовать деньги за продолжение поддержки, если проект окажется успешным. В моём случае это некритично. Мне просто нужен доступ снаружи, а публичные DDNS сервисы меня по ряду причин не устраивают. В общем, для домена я долго выбирал DNS хостинг с поддержкой апи. Попробовал https://dnspod.com - вроде бы всё неплохо и всё работает, кроме одной мелочи - не приходит ни одного письма на почту даже после того, как на сайте пишут, что письмо выслано. То есть, в случае необходимости я даже пароль своего аккаунта восстановить не смогу. В итоге выбор пал на https://cloudflare.com. Я не пожалел и смело могу его порекомендовать.
По аналогии со скриптом для обновления записей на Почте для домена от Яндекс, я написал свой скрипт для CloudFlare. Причины создания собственного велосипеда были точно такими же, как и в случае с Яндексом, а вот спектр азартных игр и падших женщин функционал расширился. В процессе написания мне в голову пришла идея о том, что неплохо было бы во-первых, сохранять параметры запуска в самом скрипте, во-вторых, при необходимости запрашивать их в интерактивном режиме при вводе и, в третьих, валидировать. Тогда я сделал метод, реализующий эту идею. Затем метод эволюционировал и начал проверять, изменилось ли значение и перезаписывать его только в случае изменения, что поможет сохранить флешпамять роутера на больший срок. Появился метод очистки заданных переменных и оператор case, позволяющий обновлять/задавать и очищать необходимые параметры. Это позволило реализовать и другие идеи. Например, если нам для обновления зоны нужно получить её ID, то зачем дёргать для этого апи каждый раз? Можно закешировать имя зоны, ID и избавиться от лишнего вызова и обработки его результатов, сэкономив время и ресурсы CPU. А если мы проверяем изменение IP адреса на интерфейсе, скажем, в кроне раз в минуту, то какой смысл вообще обновлять записи, если адрес не изменился? Правильно! Можно опять же закешировать содержимое записи в самом скрипте и сверять его с адресом, обновляя зону только в том случае, если адрес изменился. Логирование тоже никуда не делось. Одним словом, у меня постепенно получается некий свой крошечный фреймворк с шахматами и поэтессами для написания скриптов на sh. И с каждым следующим скриптом он эволюционирует и нравится мне всё больше.
Так как CloudFlare в отличие от Яндекс сервисов пользуются не только у нас, но и по всему земному шару, пришлось написать два README - для соотечественников и для всех остальных. Не уверен, что у меня это получилось хорошо, но какая-то документация в любом случае лучше, чем никакой.
P.S.: Я бы не рекомендовал пользоваться freenom.com для чего-то, что вам дорого и важно, но для пет проектов связка freenom.com + CloudFlare + вышеописанный скрипт - это то, что доктор прописал, потому что интернет с динамическим белым IP адресом есть дома практически у всех, а тут вы без оплаты и смс каких-либо дополнительных затрат средств получаете на его основе свой бесплатный хостинг без рекламы с доменом второго уровня и ресурсами, ограниченными тем железом, какое у вас дома найдётся (например, старый смартфон или планшет тоже вполне может для этого сгодиться, не говоря уже о всяких Raspberry и роутерах, поддерживающих *wrt). В какой-нибудь другой статье напишу более подробно, как сделать свою песочницу, используя всё вышеописанное и получить зелёный сертификат от Let's encrypt.
Теги: shell, automatization, networking, админское