Задание из anacron падает с «Interval "daily" unknown», а вручную работает: файл создан веб-панелью в формате DOS с переводом строки CRLF

Что было. Резервное копирование через rsnapshot перенесли с cron на anacron. Из anacron задание падает: ERROR: Interval "daily" unknown, check /etc/rsnapshot.conf. Та же команда rsnapshot daily из терминала работает.

Причина. Файл anacrontab редактировали через веб-панель администрирования, и она сохранила его с переводами строк в стиле DOS (\r\n). anacron прочитал аргумент как daily\r, и rsnapshot честно не нашёл интервал с таким именем: в ошибке невидимый символ возврата каретки не виден. Автор преобразовал файл в формат Unix; подтверждено.

Как обнаружить.

file /etc/anacrontab                 # "with CRLF line terminators"
cat -A /etc/anacrontab | head        # ^M в конце строк
grep -c $'\r' /etc/anacrontab

Исправление: sed -i 's/\r$//' файл или dos2unix файл (пакет dos2unix).

Где ещё CRLF ломает серверы тихо.

  • Скрипты: #!/bin/bash\r даёт bad interpreter: No such file or directory, хотя /bin/bash есть; в cron это выглядит как «задание не выполняется».
  • crontab: строки с \r могут не распознаться или передать \r в команду.
  • Конфиги nginx/Apache/sshd: значения с \r приводят к «unknown directive» или неверным путям к сертификатам.
  • authorized_keys: ключ с \r в конце не совпадает, вход по ключу отвергается без объяснений.
  • Переменные окружения в .env для Docker Compose и systemd EnvironmentFile: значения получают хвост \r, пароли «не подходят».
    Общий признак: ошибка ссылается на строку, которая выглядит правильно.

Откуда берётся. Редакторы на Windows (Блокнот в старых версиях), копирование через веб-формы панелей, вставка из документов, передача файлов в текстовом режиме FTP. В Git полезен .gitattributes с * text=auto eol=lf для серверных репозиториев.

Профилактика. Редактировать конфиги на сервере (nano, vim) или в редакторах с явным выбором LF; после любого «внешнего» редактирования запускать file на файл; в скриптах развёртывания проверка grep -l $'\r' по каталогу конфигов.

Формат описан в документации Ubuntu.