Снапшоты — это не резервные копии, и вам нужны оба варианта
Снапшот — это точечная во времени копия тома, которая живёт на той же инфраструктуре хранения, что и скопированный том. Это не критика, а констатация факта, и она точно объясняет, в чём снапшот превосходен, а что ему не под силу. Каждый тариф здесь включает почасовые снапшоты с хранением в течение семи дней, восстановление одного занимает около тридцати секунд, и это правильный ответ на самый распространённый инцидент в эксплуатации серверов: вы отредактировали конфигурационный файл в четыре часа дня, и с тех пор сервис не запускается. Для этого сценария сбоя ничто другое не сравнится — это быстрее любого инструмента резервного копирования, оно уже работает, и это не стоит ничего дополнительно.
Чего снапшот не может — так это пережить то, на чём он хранится. Он разделяет судьбу тома, хоста, гипервизора, а в большинстве архитектур — и аккаунта. Если машину изымают, если аккаунт закрывают, если у дата-центра выдался очень плохой день, снапшоты уходят вместе с ним — это копия данных, но не независимая копия. Это различие не академическое, если речь о провайдере, который намеренно не может вас идентифицировать: не существует пути поддержки, который восстановит ваш сервер по чьим-то чужим записям, нет процедуры восстановления, привязанной к номеру телефона, и нет истории платежей, привязанной к вашему настоящему имени. Что вы взяли — то у вас и есть.
Не помогает семидневное окно и при двух медленных типах сбоя. Файл, который вы удалили пять недель назад, исчезает из всех снапшотов задолго до того, как вы это заметите. Тихое повреждение данных — сбоящее приложение, которое незаметно пишет неверные данные, неудачная миграция, клиент синхронизации, который добросовестно распространяет ошибку, — часто обнаруживается месяц спустя, и к этому моменту повреждение уже есть в каждой сохранённой копии. От этого защищают резервные копии с более долгим хранением и подлинной историей, и защищают они именно потому, что не являются непрерывным зеркалом текущего состояния.
Модель, которую здесь стоит усвоить, стара и по-прежнему верна. Правило 3-2-1 требует три копии данных, на двух разных видах носителей, причём одна из них — вне площадки. Современное дополнение добавляет ещё две цифры — 3-2-1-1-0, — где дополнительная единица — это копия, которая неизменяема или офлайн, а ноль — это количество ошибок при последней проверке. Эти цифры — скорее мнемоника, чем стандарт, но они кодируют три свойства, которые действительно важны: независимость, неизменяемость и доказательство того, что всё работает. Почасовые снапшоты дают вам одно из этих трёх.
| Сбой | Почасовой снапшот | Бэкап вне площадки | Почему |
|---|---|---|---|
| Сломали конфиг час назад | Идеально | Избыточно | Тридцатисекундный откат бьёт любое восстановление. |
| Неудачное обновление пакета утром | Идеально | Подходит | Снапшот откатывает весь том одним действием. |
| Удалили файл пять недель назад | Нет | Покрывает | Семидневное хранение уже истекло. |
| Медленное повреждение, замечено месяц спустя | Нет | Покрывает | Повреждение уже есть в каждом сохранённом снапшоте. |
| Компрометация хоста, атакующий с root | Под угрозой | Покрывает, если только для дозаписи | Учётные данные на машине дают доступ ко всему, что машина может удалить. |
| Аккаунт закрыт или машина изъята | Нет | Покрывает | Снапшоты разделяют судьбу инфраструктуры, которая их хранит. |
| Хотите переехать к другому провайдеру | Непереносимо | Покрывает | Репозиторий восстанавливается где угодно; снапшот — только здесь. |
Читайте эту таблицу как аргумент в пользу использования обоих подходов, а не выбора между ними. Снапшоты отвечают за частоту и скорость; резервные копии — за независимость и историю. Они стоят по-разному, отказывают по-разному, непересекающимися способами, и их комбинация намного сильнее, чем удвоение любого из них по отдельности.
Два числа, которые определяют всё остальное
Прежде чем устанавливать какой-либо инструмент, зафиксируйте два показателя. Целевая точка восстановления — это то, сколько данных вы можете позволить себе потерять, измеряя это временем: если последняя пригодная для использования копия сделана шесть часов назад, ваш RPO равен шести часам, а шесть часов работы, выполненной за это время, потеряны. Целевое время восстановления — это то, как долго вы можете позволить себе оставаться недоступным, пока восстанавливаетесь. Всё, что следует дальше, — график, метод, где живёт вторая копия, сколько вы тратите, — вытекает из этих двух чисел, и если сначала выбирать программное обеспечение, а не эти числа, в итоге получают замысловатый ответ на вопрос, который никто не задавал.
Если спросить об этом мимоходом, большинство ответит «ноль и ноль». Это не бюджет, а желание, и у него есть вполне конкретная цена, которую стоит назвать прямо: RPO, близкий к нулю, означает непрерывную репликацию вместо запланированных копий, а RTO, близкий к нулю, означает уже работающую тёплую вторую машину. Оба варианта реализуемы, и оба примерно удваивают эксплуатационные расходы на то, что вы защищаете. Для подавляющего большинства self-hosted нагрузок честные ответы находятся где-то между одним часом и одними сутками для точки восстановления и несколькими часами для времени восстановления, а этому вполне удовлетворяет запланированное зашифрованное резервное копирование и задокументированная процедура пересборки.
Эти показатели также различаются для разных наборов данных даже на одной и той же машине, и именно эта деталь делает их полезными. Почта — самый яркий пример: письмо, пришедшее двадцать минут назад, не существует больше нигде, его нельзя сгенерировать заново, а отправитель понятия не имеет, что его нужно отправить повторно, — поэтому почтовому серверу нужна точка восстановления, измеряемая минутами, хотя само программное обеспечение переустанавливается за полдня. Узел Bitcoin переворачивает эту логику полностью: данные цепочки блоков — это несколько сотен гигабайт, которые любой пир в сети с готовностью пришлёт вам заново, так что резервное копирование этих данных — по большей части пустая трата места на диске, тогда как файл кошелька рядом с ними невосстановим и заслуживает защиты как приватный ключ, потому что это и есть приватный ключ.
| Нагрузка | По-настоящему незаменимо | Разумный RPO | Разумный RTO | Схема |
|---|---|---|---|---|
| Личный сайт или блог | Контент, ключ аккаунта TLS | 24 h | Сутки | Ночной репозиторий, пересборка по заметкам |
| Почтовый сервер | Maildir, ключи DKIM, алиасы | 15 min | 2–4 h | Частые инкрементальные копии, вторая машина наготове |
| Nextcloud или синхронизация файлов | Каталог данных, база данных, конфигурация | 6–24 h | Сутки | Ночной дамп в режиме обслуживания |
| Домашний сервер Matrix | Postgres, ключ подписи, хранилище медиа | 1–6 h | Часы | Почасовой дамп базы данных, ночная выгрузка медиа |
| Узел Bitcoin или Lightning | Кошелёк, состояние каналов, macaroons | Минуты (состояние каналов) | Часы | Данные цепочки досинхронизируются; резервируйте только ключи |
| Песочница для разработки | Обычно ничего | N/A | N/A | Одних снапшотов достаточно как оправданный ответ |
Последнюю строку стоит проговорить вслух, потому что у руководства о резервном копировании есть очевидный стимул этого не делать. Некоторым машинам резервная копия не нужна вовсе. Агент сборки, всё состояние которого берётся из репозитория git, одноразовая песочница, не хранящий состояние обратный прокси, чья конфигурация живёт в системе контроля версий, — для них почасовые снапшоты, включённые в тариф, являются полным и оправданным ответом, и правильный объём инженерии резервного копирования здесь — нулевой. Знать, какие из ваших серверов относятся к этой категории, стоит больше, чем плохо резервировать их все.
Что копировать — и гораздо больший ворох того, что следует пропустить
Инстинкт подсказывает сделать образ всего диска целиком, и на арендованной виртуальной машине этот инстинкт ошибочен. Операционная система расходуема: здесь новый инстанс разворачивается за медианные сорок одну секунду, а переустановка пакетов из зеркала дистрибутива быстрее и надёжнее, чем их восстановление из собственной копии. То, что не расходуемо, — на удивление небольшой набор, и дисциплина явно назвать этот набор — это и есть большая часть работы: резервную копию, которую можно описать одним абзацем, можно проверить, тогда как образ всего диска — это то, на что остаётся только надеяться.
Незаменимый набор обычно состоит из четырёх вещей. Во-первых, данные приложений: maildir, каталог данных, хранилище медиа, папка загрузок. Во-вторых, базы данных, которые требуют отдельного подхода и разбираются в следующем разделе. В-третьих, секреты — и это та категория, о которой забывают, пока это не обходится дорого. Приватные ключи TLS и ключ аккаунта ACME, ключи хоста SSH, если вы предпочитаете не доверять отпечатку заново на каждом клиенте, ключ подписи DKIM, без которого ваша почта начинает проваливать аутентификацию, приватные ключи WireGuard, и прежде всего приватный ключ onion-сервиса, который и есть .onion-адрес: потеряете его — и адрес исчезнет навсегда, и нет никакого реестра, куда можно было бы апеллировать. В-четвёртых, та горстка файлов в /etc, которые вы действительно изменили, плюс юниты systemd, записи cron и набор правил firewall, которые заставляют машину вести себя именно так, как она себя ведёт.
Ворох того, что следует пропустить, намного больше и по большей части очевиден, стоит его только назвать. Псевдофайловые системы вроде /proc, /sys и /dev — это представления ядра, а не данные. Кеши пакетов, образы контейнеров, виртуальные окружения и каталоги зависимостей — всё это можно за секунды заново получить из lock-файла. Логи за пределами вашей политики хранения — это шум, который плохо дедуплицируется и раздувает каждый последующий запуск. А объёмные датасеты, которые можно ресинхронизировать заново, — состояние блокчейна, публичное зеркало, медиатеку, которую можно переоцифровать заново, — заслуживают осознанного решения, а не решения по умолчанию: резервное копирование трёхсот гигабайт данных цепочки блоков обходится в реальные деньги каждый месяц, лишь бы избежать ресинхронизации, которую можно выполнить бесплатно, пока сервис работает в деградированном, но функциональном режиме.
Часть, в которую почти все инвестируют недостаточно, — это ответ на вопрос «восстанавливать во что?». Данные без цели восстановления — это не восстановление. Если то, как был построен ваш сервер, существует только у вас в памяти и в истории команд шелла, которую вы с тех пор потеряли, время восстановления у вас будет неограниченным, каким бы хорошим ни был репозиторий. Решение дешёвое и скучное: храните шаги развёртывания в виде скрипта или простого текстового runbook, кладите его внутрь репозитория резервных копий, чтобы он восстанавливался вместе с данными, и обновляйте его при каждом изменении машины. Даже сотня строк заметок — пакеты, версии, расположение конфигурационных файлов, записи DNS, порядок, в котором должны запускаться сервисы, — превращает плохую неделю в плохой день.
Один нюанс стоит отметить для всех, кто использует полное шифрование диска: заголовок LUKS и его слоты ключей тоже входят в ваш незаменимый набор. Повреждённый заголовок превращает полностью целый диск в случайный шум, заголовок весит несколько мегабайт, и его резервное копирование ничего не стоит. Храните его так же тщательно, как парольную фразу — тот, кто владеет и тем, и другим, владеет диском.
Базы данных: файл, который вы копируете, — это не база данных
Это самый распространённый способ, которым в остальном грамотная резервная копия оказывается бесполезной. Движок базы данных хранит состояние в памяти, в журнале упреждающей записи или журнале повторного выполнения, и в файлах данных, которые непрерывно изменяются. Копирование этих файлов, пока движок работает, захватывает их в разные моменты времени — четвёртая страница таблицы взята до транзакции, пятая — после, — и в результате получается набор файлов, каждый из которых по отдельности цел, а вместе они несогласованны. Жестокая особенность в том, что такая копия обычно восстанавливается. Она поднимается, отвечает на запросы, а повреждение всплывает неделями позже как испорченный индекс или строка, нарушающая ограничение, которое движок клянётся, что соблюдает. Резервная копия, которая отказывает громко, намного лучше той, что отказывает тихо.
Правильный подход зависит от движка и хорошо задокументирован в каждом случае. Для MariaDB и MySQL логический дамп, снятый в рамках одной согласованной транзакции, подходит для всего, что до нескольких десятков гигабайт; сверх этого Mariabackup выполняет физическое горячее копирование, пока сервер работает. Для PostgreSQL pg_dump даёт вам переносимый логический снапшот, а pg_basebackup в сочетании с архивными журналами упреждающей записи даёт вам восстановление на момент времени — возможность восстановиться на 14:32, а не на момент, когда случайно выполнялся последний дамп. Для SQLite используйте встроенное онлайн-резервное копирование или VACUUM INTO; cp для работающего файла базы данных — это именно та ошибка, что описана выше, и SQLite — движок, в котором эту ошибку совершают чаще всего, потому что он выглядит как обычный файл.
Согласованность между базой данных и файлами, которые она описывает, — это вторая половина проблемы, и именно она особенно больно бьёт по ПО для синхронизации файлов и форумам. База данных утверждает, что файл существует по такому-то пути; файловая система — это то, где физически лежат байты; если вы снимаете дамп базы данных в 02:00, а каталог данных копируете в 02:40, то всё, что было создано в промежутке, существует либо как байты без записи в базе, либо как запись без байтов. Приложения, которые предлагают режим обслуживания — Nextcloud — самый очевидный пример, — решают это, ненадолго отказывая в записи, пока снимаются оба среза. Там, где это неприемлемо, снапшот файловой системы или тома, снятый в один момент времени, даёт вам согласованную пару, которую можно спокойно скопировать позже, — это тот же самый приём, которым пользуются почасовые снапшоты.
Одна небольшая операционная деталь окупается немедленно: пишите дампы без сжатия и позвольте сжатием заниматься инструменту резервного копирования. И restic, и borg дедуплицируют данные с помощью чанкинга на основе содержимого, поэтому два дампа, снятые с разницей в сутки, разделяют подавляющее большинство своих чанков, и хранение второго обходится почти бесплатно. Сожмите дамп заранее — и один-единственный изменившийся байт в начале файла каскадно меняет весь сжатый поток целиком, ни один чанк ни с чем не совпадает, и каждый запуск сохраняет полную копию. Команды регулярно обнаруживают, что их репозиторий ежедневно растёт на полный размер базы данных именно по этой причине — а решение — убрать один пайп из shell-скрипта.
Наконец, осознанно решите, нужно ли вам восстановление на момент времени, потому что это ответ на сбой, с которым ежедневный дамп справиться не может. Если кто-то выполняет деструктивный запрос в 14:32, а вы обнаруживаете это в 17:00, восстановление вчерашнего ночного дампа означает потерю целого рабочего дня. Непрерывное архивирование вместо этого воспроизводит журнал вплоть до 14:31. Это стоит больше места на диске и заметно увеличивает операционную сложность, поэтому это не решение по умолчанию, — но там, где человек с правом записи может уничтожить данные быстрее, чем вы это заметите, это разница между инцидентом и катастрофой.
Шифруйте до того, как данные покинут сервер: restic, borg и ключ, который нельзя терять
Свойство, которое делает возможным всё остальное в этом руководстве, — это шифрование на стороне клиента: данные шифруются на той машине, которая их произвела, ещё до того, как хоть один байт попадёт в сеть, с использованием ключа, который получатель никогда не увидит. Именно это архитектурное решение превращает цель резервного копирования в недоверенное хранилище, а недоверенное хранилище может жить где угодно — на дешёвом сервере в другой стране, в объектном хранилище, на NAS у друга — и ни один из них не будет в состоянии прочитать ваши данные. Провайдеры, которые шифруют на стороне сервера, защищают вас от другого, гораздо более узкого набора угроз, и эта разница имеет наибольшее значение именно в тех ситуациях, ради выживания в которых вы и покупаете офшорный хостинг.
Restic и Borg одинаково корректно решают эту задачу, и выбор между ними — вопрос, в котором чаши весов действительно почти уравновешены. Restic — это один статический бинарник без зависимостей, который нативно поддерживает длинный список бэкендов: SFTP, S3-совместимые объектные хранилища, обычные локальные пути — и его проще, чем Borg, запускать в контейнере или минимальном образе. Borg — инструмент постарше и в некоторых отношениях более хирургически точный: более сильные опции сжатия, отличная поддержка append-only на стороне сервера и формат репозитория, в котором многим проще разобраться; при работе через SSH он требует, чтобы borg был установлен на обоих концах, а это небольшое ограничение, которое иногда и решает дело.
| Свойство | restic | borg |
|---|---|---|
| Шифрование на клиенте | Всегда включено | Всегда включено (repokey / keyfile) |
| Дедупликация | Контентное чанкование, между хостами | Контентное чанкование, в пределах репозитория |
| Бэкенды | SFTP, S3, B2, Azure, локально, REST | SSH с borg на другом конце, локально |
| Установка на целевой машине | Не требуется для SFTP | Требуется |
| Принудительный append-only | rest-server --append-only | borg serve --append-only |
| Просмотр снапшота как файловой системы | restic mount | borg mount |
| Одновременные клиенты, один репозиторий | Поддерживается | Один клиент на запись одновременно |
| Проверка | check --read-data-subset | check --verify-data |
Какой бы вариант вы ни выбрали, теперь всё решает парольная фраза, и относиться к ней стоит так же, как к seed-фразе криптокошелька. Она не должна храниться только на той машине, которую защищает, — парольная фраза, лежащая рядом с данными, которые она шифрует, не защищает вас вообще ни от чего, потому что при потере сервера вместе с ним теряется и ключ в любом сценарии. Храните её в менеджере паролей на другом устройстве или на бумаге в другом здании — а в идеале и там, и там. Borg позволяет экспортировать ключ репозитория в отдельный файл, restic позволяет репозиторию нести несколько независимых ключей, и оба механизма дают запасной способ доступа, который не зависит от того, помните ли вы строку наизусть. Здесь нет ни восстановления, ни ссылки для сброса, ни тикета в поддержку, который мог бы это отменить: зашифрованный репозиторий без ключа неотличим от случайных данных — в этом и весь смысл.
Стоит явно проговорить, почему обычный rsync на другой сервер не заменяет резервное копирование, — ведь это первое, за что хватаются. Rsync создаёт зеркало, а у зеркала нет истории: удалите файл сегодня, и сегодняшний же ночной запуск добросовестно удалит его и там. Дедупликации нет, поэтому хранение тридцати дней означает тридцать копий, если только не изворачиваться с жёсткими ссылками. Встроенного шифрования данных при хранении нет, поэтому на принимающей стороне видно всё. И проверочной истории у него нет никакой, кроме повторного чтения источника. Это отличное средство передачи данных, но никудышная резервная копия, и разница становится очевидной в тот день, когда вам нужна версия трёхнедельной давности.
Append-only, иначе это просто копия, а не резервная копия
Вот сценарий, который определяет архитектуру. Кто-то получает root на вашем сервере — через неисправленное приложение, утёкший токен, зависимость, которая стала вредоносной. Теперь он находится внутри машины, которая хранит действующие учётные данные для собственного целевого сервера резервного копирования, — именно так устроено резервное копирование по расписанию. Всё, что может удалить эта машина, может удалить и он, а удаление резервных копий при современном вторжении — не второстепенная деталь, а первый шаг. То же самое верно и без злоумышленника: благонамеренный скрипт с ошибочной переменной, запущенный от root, вполне способен вычистить репозиторий до пустоты.
Мера, которая закрывает эту дыру, — принудительный append-only на принимающей стороне. При такой настройке клиент может создавать новые снапшоты, но не может удалять или переписывать старые — ограничение обеспечивается процессом на хосте резервного копирования, а не добросовестностью клиента. Borg реализует это через borg serve --append-only, привязанный к ключу в authorized_keys целевой машины, так что клиент не может запросить ничего другого. У Restic та же схема через rest-server с --append-only. В объектном хранилище эквивалентом служит версионирование плюс политика удержания object-lock, которая достигает того же результата другим механизмом.
Конфигурацию SSH, которая всё это несёт, стоит настроить абсолютно точно, потому что это несущая строка. В authorized_keys пользователя резервного копирования добавьте перед ключом клиента принудительную команду и ограничения, которые описывает руководство sshd: command="borg serve --append-only --restrict-to-path /srv/backups/web01",restrict. Одна эта строка означает, что украденный у клиента ключ не сможет открыть shell, не сможет пробросить порт, не сможет затронуть репозиторий другого хоста и не сможет ничего удалить. Выдавайте каждому клиенту собственный ключ и собственный путь.
Отсюда напрашивается очевидный вопрос: если клиент никогда не может удалять, то что убирает старые снапшоты? Прунинг происходит в другом месте, по расписанию, с учётными данными, которых защищаемая машина никогда не держала в руках. На практике это означает, что хост резервного копирования сам чистит свои репозитории через локальный cron, либо третья небольшая машина хранит привилегированный ключ и еженедельно выполняет прунинг. У Borg здесь есть известная особенность: у append-only репозитория компактификация должна запускаться на стороне сервера, а не клиентом, — и если считать хост резервного копирования ответственным за прунинг, это снимает проблему без сложностей. Принцип обобщается: машина, которая записывает резервные копии, никогда не должна быть машиной, способной их уничтожить.
Сама политика хранения — вопрос с давно устоявшимся ответом, который работает на практике: хранить несколько последних ежедневных снапшотов, четыре-пять еженедельных и от шести до двенадцати ежемесячных. Оба инструмента описывают это декларативно: вы задаёте желаемую форму, а какие снапшоты ей удовлетворяют, решает сам инструмент. Именно ежемесячные снапшоты ловят медленную порчу данных, и именно их обычно урезают первыми, когда репозиторий разрастается, — что совершенно неверно, поскольку сжатый дедуплицированный ежемесячный снапшот набора данных, который почти не меняется, стоит практически ничего.
Где хранить вторую копию, если вас невозможно идентифицировать
Формулировка «за пределами площадки» несёт на себе значительную часть смысла правила 3-2-1, а у провайдера без KYC она означает нечто более конкретное, чем просто «другое здание». Она означает копию, выживание которой не зависит от той же компании, того же аккаунта, тех же платёжных отношений или той же юрисдикции, что и оригинал. Два сервера в одном аккаунте — это два сервера с одной судьбой, как бы далеко друг от друга ни находились их дата-центры: закрытие аккаунта по любой причине заберёт оба, а юридический документ, предъявленный одному юридическому лицу, достаёт до всего, чем это лицо владеет. Независимость — это свойство отношений, а не только географии.
На практике это проще, чем звучит, потому что та же панель управления уже предлагает четыре юрисдикции. Продакшн-инстанс в Нидерландах с репозиторием, отправляемым на тариф Starter в Исландии, стоит $8.50 в месяц и выводит ваше восстановление за пределы досягаемости любого отдельно взятого национального процесса — а поскольку юрисдикции отличаются тем, чему именно они на практике способны противостоять, эта пара заслуживает минуты размышления, а не подброшенной монеты. Поскольку репозиторий шифруется ещё до того, как покидает источник, хосту резервного копирования по замыслу не доверяют: вторая локация покупает вам доступность и юридическую дистанцию, а не конфиденциальность. Конфиденциальность у вас уже есть.
Для по-настоящему независимой третьей копии самая надёжная архитектура разворачивает направление соединения. Вместо того чтобы сервер отправлял данные на цель, для которой у него есть учётные данные, машина, которую контролируете вы, — компьютер дома, NAS, ноутбук, просыпающийся по расписанию, — забирает данные с сервера. Тогда продакшн-машина вообще не хранит учётных данных ни для одного места назначения резервных копий, что делает сценарий взлома из предыдущего раздела структурно невозможным, а не просто смягчённым. Это обходится вам в отдельную машину, которая должна быть доступна или бодрствовать по расписанию, — именно поэтому такой подход дополняет копию, отправляемую за пределы площадки, а не заменяет её.
| Размещение | Стоимость | Переживает взлом хоста | Переживает потерю аккаунта | Примечания |
|---|---|---|---|---|
| Почасовые снапшоты, тот же тариф | Включено | Нет | Нет | Самый быстрый откат; окно в семь дней |
| Второй инстанс, другая юрисдикция | От $8.50/mo | Да, если append-only | Нет — тот же аккаунт | Дешёвая юридическая и физическая дистанция |
| Выделенный сервер, зеркалированный NVMe | От $39.50/mo | Да, если append-only | Нет — тот же аккаунт | Оправдан начиная с нескольких сотен гигабайт |
| Pull с собственного оборудования | Электричество | Да, структурно | Да | Сервер вообще не хранит учётных данных |
| Стороннее объектное хранилище | За GB | Да, с object lock | Да | Нужен отдельный анонимный способ оплаты |
Стоит без прикрас проговорить два ограничения, характерных именно для такого хостинга. Восстановления доступа к аккаунту не существует: нет документа, удостоверяющего личность, который можно предъявить, нет номера телефона, на который придёт код, нет представителя, способного подтвердить, что вы — это вы. Это то же самое свойство, за которое вы платите при регистрации, и действует оно симметрично — из-за чего парольная фраза и runbook становятся несущими элементами так, как этого никогда не бывает у массового провайдера. И если за целевой сервер резервного копирования нужно платить, платить за него тоже нужно анонимно, иначе вторая копия незаметно возвращает ту самую привязку к личности, которой была призвана избежать первая. Платить за обе машины с одного и того же криптокошелька — нормально; платить за резервную копию картой — это решение, а не недосмотр.
Репетиция, и как вы узнаёте, что резервное копирование перестало работать
Задания резервного копирования обычно не отказывают драматично. Они отказывают постепенно: шаблон исключений расширили при уборке конфигурации, учётные данные обновили только с одной стороны, диск на целевой машине заполнился, запись cron потерялась при обновлении дистрибутива. В каждом из этих случаев машина продолжает работать, ничего не сигнализирует, а репозиторий тихо перестаёт расти. Схема, которая это ловит, — не «сигнализировать при сбое» (задание, которое больше не запускается, не может сообщить о собственном сбое), а сигнализировать при отсутствии успеха. Настройте так, чтобы каждый успешный запуск пинговал эндпоинт dead man's switch, а этот эндпоинт поднимал тревогу, если пинг не пришёл вовремя. Это десять минут настройки, и именно они определяют разницу между тем, заметите вы проблему через день или во время восстановления.
Проверка целостности — вторая половина дела. Оба инструмента умеют проверять, что метаданные репозитория согласованы, а что ещё полезнее — что сохранённые чанки действительно расшифровываются и совпадают со своими хешами. Чтение всего целиком дорого обходится по трафику, поэтому оба предлагают частичную форму проверки — restic проверяет процент данных за каждый запуск, borg проверяет данные по требованию, — и разумная периодичность такая: полная проверка метаданных еженедельно и частичная проверка данных ежемесячно, с таким расчётом, чтобы полный проход набегал за квартал. Хранилища действительно деградируют со временем, и смысл проверки — узнать об этом, пока у вас ещё есть другая копия.
Ничто из этого не доказывает, что вы способны восстановиться. У этого доказательства ровно один источник — само восстановление. Разверните новый инстанс — самый младший тариф стоит $8.50, и вы уничтожите его в течение часа, — восстановите в него репозиторий, а затем сделайте то, что все пропускают: запустите приложение и посмотрите на реальные данные. Войдите в систему. Откройте документ за прошлый месяц. Отправьте тестовое сообщение через почтовый сервер. Сделайте запрос к таблице, в которой должны быть вчерашние строки. Проверка — это не наличие файлов, а работа сервиса поверх них. Делайте это в первый раз сразу при настройке резервного копирования, а затем — с реальной, соблюдаемой периодичностью по календарю, потому что репетиция заодно проверяет и runbook, а runbook устаревает быстрее, чем данные.
| Проверка | Периодичность | Что она доказывает |
|---|---|---|
| Пинг dead man's switch после каждого запуска | Каждый запуск | Задание всё ещё запускается и завершается успешно |
| Проверка метаданных репозитория | Еженедельно | Индекс и структура снапшотов согласованы |
| Частичная проверка данных | Ежемесячно | Сохранённые чанки расшифровываются и совпадают со своими хешами |
| Восстановление одного файла на рабочую машину | Ежемесячно | Учётные данные, парольная фраза и путь всё ещё работают |
| Полное восстановление на одноразовый сервер | Ежеквартально | Приложение действительно поднимается |
| Перечитать runbook во время восстановления | Ежеквартально | Инструкции соответствуют текущей машине |
Runbook заслуживает отдельного абзаца, потому что это самый дешёвый пункт из всех и при этом чаще всего отсутствующий. Запишите по порядку: где находится репозиторий и как до него добраться, где хранится парольная фраза, как развернуть машину на замену, какие пакеты и версии устанавливать, что восстанавливать и в каком порядке, какие записи DNS менять и как убедиться, что всё сработало. Храните его вне машины, которую он описывает, — в самом репозитории, в менеджере паролей, на бумаге, — и исходите из того, что читающий его человек устал, работает в неудобное время суток и, возможно, это не вы. Именно это последнее допущение превращает набор заметок в то, что сможет выполнить коллега или член семьи.
Собранная воедино, вся эта схема ничем не примечательна — и в этом её достоинство: почасовые снапшоты, которые уже включены в ваш тариф, — на случай происшествий за последние несколько дней, зашифрованный репозиторий, отправляемый каждую ночь во вторую юрисдикцию, где его невозможно удалить, парольная фраза там, где её никогда не видел сервер, пинг, который жалуется, когда задание замолкает, и репетиция, отмеченная в календаре. Ничего из этого списка не сложно, на большую часть хватит нескольких часов, а всё вместе стоит в месяц меньше, чем кофе, который вы купите, пока будете восстанавливаться с нуля. Если вы настраиваете это прямо сейчас, вторая машина разворачивается примерно за минуту — начните с восстановления, которое вы ни разу не тестировали, потому что это единственная часть всего процесса, которая говорит вам правду.