Администрирование

Делаем бекап OS X на сетевое хранилище

У Apple для хранения резервных копий данных есть такое устройство под названием Time Capsule. Есть модели на 1, 2, 3TB, а может уже и больше есть... А что, если я не хочу тратить 10-20 тысяч родных рублей и хочу использовать уже имеющиеся средства, такие как NAS-сервер, или удаленную Linux машину с приличным массивом дисков? По простому, макосевскую Time Machine, а также Aperture Vault не подружить с сетевыми дисками, т.к. в ответ вы получите только ругань и упреки от Стива в том, что до сих пор не купили тайм капсулу. Но, все таки, надо что-то попробовать...

Итак, в этой статье я расскажу, как заставить Time Machine и Aperture сохранять все бекапы на Linux-сервере. Статья, также, может быть полезна владельцем NAS устройств, поддерживающих протокол AFP. Поехали! Первым делом нужно убедить Time Machine отображать в списке выбора дисков сетевые шары, для чего открываем терминал и выполняем команду:

defaults write com.apple.systempreferences TMShowUnsupportedNetworkVolumes 1

Довольно просто пока, да? Далее, на linux-сервере (в моем случае под управлением Fedora), нужно установить netatalk версии не ниже 2.2. Важно, чтобы версия не была ниже, иначе ничего работать не будет! После установки, конфигурим следующим образом:

  • В директории /etc/netatalk, в AppleVolumes.default в самом низу прописываем /mnt/storage/tm TimeMachine allow:YOURUSER rwlist:YOURUSER cnidscheme:tdb options:usedots,upriv,tm, где /mnt/storage/tm - путь до того места на сервере, где будут лежать бекапы, а YOURUSER - логин пользователя на сервере, под которым будет работать шара
  • В afpd.conf тоже в самом низу добавляем - -uamlist uams_dhx.so,uams_dhx2.so -unixcodepage UTF-8 -maccodepage MAC_CYRILLIC -savepassword -setpassword -tcp -advertise_ssh
  • Приводим вид содержимого файла netatalk.conf в такой вид:

Синхронизация MySQL баз после ошибки репликации

В процессе длительной работы с двумя и более MySQL баз данных, между которым происходит репликация, можно столкнуться с массой мелких ошибок, вызванных, например, конфликтами первичных ключей, повреждениями журналов и т.п. Особенно, если репликация настроена, как мастер-мастер, конфликты гарантированы. Естественно, из-за мелких ошибок никто не станет полностью заново синхронизировать две базы данных, а скорее всего, пропустит ошибку через установку SQL_SLAVE_SKIP_COUNTER или slave-skip-errors. Со временем, две БД накопят некий запас неконсистентности, благодаря таким пропущенным конфликтам. Итак, что делать, если нужно восстановить полную консистентность, или в случае, когда ошибка в репликации совсем критичная и не решается вышеописанными способами? Единственный выход - полная синхронизация двух БД "с нуля" и сброс состояния репликации.

Порядок действий таков - на мастере:

mysql-master> STOP SLAVE;
mysql-master> RESET MASTER;
mysql-master> FLUSH TABLES WITH READ LOCK;
mysql-master> SHOW MASTER STATUS;
+------------+----------+--------------+------------------+
| File       | Position | Binlog_Do_DB | Binlog_Ignore_DB |
+------------+----------+--------------+------------------+
| bin.000002 |      654 |              | mysql            |
+------------+----------+--------------+------------------+

Сохраните вывод последней команды. Первая команда нужна только в случае мастер-мастер репликации. Вторая и третья команды сотрут все журналы мастера, предназначенные для слейвов и переведут все таблицы в режим только чтения, чтобы во время переноса дампа не появилось никаких новых данных.

MySQL: Could not parse relay log event entry

На днях на одном из серверов внезапно остановилась репликация. Команда SHOW SLAVE STATUS показала ошибку: Last_Error: Could not parse relay log event entry. The possible reasons are: the master's binary log is corrupted (you can check this by running 'mysqlbinlog' on the binary log), the slave's relay log is corrupted (you can check this by running 'mysqlbinlog' on the relay log), a network problem, or a bug in the master's or slave's MySQL code. If you want to check the master's binary log or slave's relay log, you will be able to know their names by issuing 'SHOW SLAVE STATUS' on this slave. Выглядит внушительно и слегка пугающе - все таки, не каждый день повреждаются файлы на жестком диске, к тому же файлы журнала репликации. Так или иначе, с ошибкой надо что-то делать и как всегда есть два варианта: простой, надежный, но муторный, связанный с ручной синхронизацией БД через импорт/экспорт, либо быстрый, но требующий внимания, т.к. связан со сбросом текущего положения "курсора" репликации на проблемном сервере.

Какое бы решение вы не приняли, оно поможет от любых ошибок репликации, связанных с повреждением журнала на подчиненном (слейв) сервере. Если бинарный журнал повредился на главном (мастер) сервере, статью дальше можно не читать. Итак, я пошел вторым путем, т.е. через сброс состояния репликации. Все, что нужно сделать - это выполнить несколько команд на проблемном сервере. Поехали:

umount: device is busy - безопасное извлечение

Работая в системе Linux, каждый, рано или поздно, сталкивался с проблемой, когда нужно извлечь примонтированный диск/флешку/камеру, но система дает отлуп, ссылаясь на то, что устройство занято каким-то другим процессом:

[me@serv ~]$ sudo umount /mnt/storage-disk
umount: /mnt/storage-disk: device is busy.

Чтобы найти процессы, использующие данный ресурс и безопасно их завершить, нам поможет утилита fuser:

[me@serv ~]$ sudo fuser -m /mnt/storage-disk
/mnt/storage-disk:     1454 24398c

[me@serv ~]$ sudo fuser -m -k TERM /mnt/storage-disk
/mnt/storage-disk:     1454 24398c
[me@serv ~]$ sudo umount /mnt/storage-disk

Первой командой мы направили процессам 1454 и 24398 сигнал SIGTERM, а затем отмонтировали наш диск. Если же umount по прежнему не дает извлечь устройство, можно, в крайнем случае, отправить сигнал SIGKILL, но это уже не будет безопасным извлечением :)

Ошибки MySQL репликации

Если у вас есть сервер, на котором настроена MySQL репликация, то рано или поздно вы столкнетесь с разного рода ошибками этой самой репликации. Ошибки могут быть вызваны как некорректной настройкой mysql-сервера, так и неправильной структурой самой БД.

В моей практике, наиболее распространенной ошибкой была 1062 Duplicate entry '...' for key 1, которая возникает в случае нарушения уникальности какого-либо unique-поля таблицы. Если вы не можете изменить структуру таблиц так, чтобы избежать подобной ситуации, но, при этом, репликацию надо как-то запускать, есть простой выход - в настройки MySQL (my.cnf) добавить строку slave-skip-errors = 1062. С этого момента, сервер просто будет игнорировать именно эту ошибку и репликация останавливаться не будет. Но надо понимать, что при таком подходе вы будете терять часть данных, которые не попадут в реплицируемые таблицы из-за описанного выше конфликта.

Unexpected inconsistency, run fsck manually

Сегодня после удаленного рестарта системы неожиданно сервер отказался подниматься... просто пал смертью храбрых. Добравшись до машины и подключив монитор, увидел в терминале следующее:

Checking root filesystem
/dev/VolGroup00/LogVol00: UNEXPECTED INCONSISTENCY; RUN fsck MANUALLY

Ну что поделать, раз просят запустить fsck, так и сделал. Он нашел какие-то ошибки, спросил меня, стоит ли их исправить и велел рестартовать систему. Но увы, машина опять не поднялась и все с той же ошибкой. Проблему решил более грамотный запуск fsck:

[root@localhost ~]# fsck -f -c -y -v /

MySQL мастер-мастер репликация

Многие используют в MySQL функцию Master - Slave репликации для зеркалирования или бекапа данных. А что, если slave должен иметь возможность записать данные в БД, которые затем должны реплицироваться на Master? Настройка Master - Master репликации на самом деле не представляет из себя ничего сложного.

Дано:

  • Хост 1 (192.168.1.1) - главный сервер
  • Хост 2 (192.168.1.2) - второй сервер, зеркало первого, который должен реплицировать все с главного, а также передавать ему свои изменения

Необходимо настроить мастер-мастер репликацию между главным сервером и зеркалом. Поехали!

На главном сервере:

  • В файле конфигурации MySQL (my.cnf) отключаем параметр skip-networking и прописываем в bind-address внешний IP данного сервера

Настройка iptables

Iptables - это достаточно надежный, конфигурируемый файервол для Linux-систем, поставляющийся со всеми дистрибутивами на базе ядер 2.4.х и выше. Настройка достаточно простой процесс и не займет у вас много времени.

Первое, что нужно сделать - убедиться, что в файле конфигурации /etc/sysconfig/iptables-config параметр IPTABLES_SAVE_ON_STOP="yes". Это заставит сервис iptables сохранять свою конфигурацию в файл при каждом завершении работы, чтобы не пришлось конфигурировать все повторно. Начнем с того, что создадим начальный файл конфигурации

iptables-save > /etc/sysconfig/iptables

На свежеустановленной системе файл будет иметь примерно следующее содержимое:

# Generated by iptables-save v1.4.5 on Sat Dec  5 11:46:18 2009
*filter
:INPUT ACCEPT [17:1201]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [12:1341]
COMMIT
# Completed on Sat Dec  5 11:46:18 2009

Что означает полностью прозрачный (открытый) режим работы. Никаких ограничений не задано. Здесь цепочка INPUT отвечает за фильтрацию входящего трафика, OUTPUT - исходящего.

Ошибка в Drupal: function is deprecated

Если вы недавно обновили на своем сервере PHP до версии 5.3, то на вашем сайте, который работает под CMS Drupal не исключено появление сообщений вида:

Function ereg() is deprecated in includes/file.inc on line 895

К сожалению, на момент написания статьи, drupal официально еще не поддерживал php 5.3. Чтобы обойти эту ошибку, а точнее убрать вывод сообщений, нужно всего ничего - отредактировать файл includes/common.inc, находящийся в вашей директории с друпалом и заменить в нем строку:

if ($errno & (E_ALL ^ E_NOTICE)) {

на

if ($errno & (E_ALL & ~E_NOTICE & ~E_DEPRECATED)) {

У меня этот код был на строке 580.

Ошибка в Cacti: Cron is configured to run too often

Быстрая заметка, для тех, кто столкнулся с проблемой, когда Cacti вдруг перестает рисовать новые значения графиков, а в логах появляется строка

POLLER: Poller[0] NOTE: Cron is configured to run too often!  The Poller Interval is '300' seconds, with a minimum Cron period of '300' seconds, but only -6600 seconds have passed since the poller last ran

Случилось это после рестарта системы, т.е. вручную, конечно же, никто не запускал poller.php. Лечится это установкой $force = TRUE; в poller.php. После очередного, на сей раз успешного срабатывания, меняем значение обратно на FALSE.

Если же этот фокус не помог, а в логах теперь ругательства rrdtool

illegal attempt to update using time 1254675401 when last update time is 1254681400 (minimum one second step)

то все сложнее - Cacti мало того, что успела себе поставить неверную дату последнего срабатывания, так еще и в rrd файлы успела ее проставить. Тут два пути - либо посмотреть, что за дату поставил кактуст (date -r 1254681400) и дождатся ее, либо делать дамп каждого RRD, удалять там "левые" даты и затем restore.

Реклама на stremoukhov.ru: