Логотип
Возобновленная рана много хуже противу новой (К. Прутков).

Руководство для начинающих по системным таймерам (2026)

Руководство для начинающих по системным таймерам (2026)

Если вы какое-то время пользовались Linux, то наверняка знакомы с заданиями cron. С их помощью можно запускать скрипт каждую ночь в 2 часа или каждые 5 минут. В большинстве современных систем Linux (Debian, Ubuntu, Fedora, Arch, RHEL) в качестве системы инициализации используется systemd, а у systemd есть собственный способ планирования заданий. Мы называем их таймерными модулями.

Таймеры systemd выполняют ту же функцию, что и cron, но они интегрированы в остальную часть systemd. Это означает, что вы получаете правильное логирование, обработку зависимостей и контроль ресурсов бесплатно.

Таймер systemd всегда состоит из двух частей:

  1. .timer unit. Определяет когда что-то должно запуститься.
  2. .service единица измерения. Это определяет, что будет выполняться.

 

Единственная задача таймера — запустить службу в нужное время. Как только вы разберетесь в этом разделении, все остальное встанет на свои места.

Попробуйте прямо сейчас, прежде чем что-то писать: запустите systemctl list-timers на своем компьютере. Вы почти наверняка увидите, что таймеры уже запущены, такие как apt-daily.timerlogrotate.timer или man-db.timer.

$ systemctl list-timers

NEXT                                 LEFT LAST                              PASSED UNIT                           ACTIVATES                       
Tue 2026-08-25 11:30:00 UTC      3min 40s Tue 2026-08-25 11:20:00 UTC     6min ago sysstat-collect.timer          sysstat-collect.service
Tue 2026-08-25 12:21:48 UTC         55min -                                      - fwupd-refresh.timer            fwupd-refresh.service
Tue 2026-08-25 19:37:38 UTC            8h Tue 2026-08-25 11:06:29 UTC            - motd-news.timer                motd-news.service
Tue 2026-08-25 21:35:55 UTC           10h -                                      - apt-daily.timer                apt-daily.service
Wed 2026-08-26 00:00:00 UTC           12h -                                      - dpkg-db-backup.timer           dpkg-db-backup.service
Wed 2026-08-26 00:00:00 UTC           12h -                                      - sysstat-rotate.timer           sysstat-rotate.service
Wed 2026-08-26 00:07:00 UTC           12h -                                      - sysstat-summary.timer          sysstat-summary.service
Wed 2026-08-26 00:45:21 UTC           13h -                                      - logrotate.timer                logrotate.service
Wed 2026-08-26 06:29:14 UTC           19h -                                      - apt-daily-upgrade.timer        apt-daily-upgrade.service
Wed 2026-08-26 11:06:17 UTC           23h -                                      - man-db.timer                   man-db.service
Wed 2026-08-26 11:12:00 UTC           23h Tue 2026-08-25 11:12:00 UTC    14min ago update-notifier-download.timer update-notifier-download.service
Wed 2026-08-26 11:22:00 UTC           23h Tue 2026-08-25 11:22:00 UTC 4min 19s ago systemd-tmpfiles-clean.timer   systemd-tmpfiles-clean.service
Sun 2026-08-30 03:10:01 UTC        4 days -                                      - xfs_scrub_all.timer            xfs_scrub_all.service
Sun 2026-08-30 03:10:34 UTC        4 days -                                      - e2scrub_all.timer              e2scrub_all.service
Mon 2026-08-31 00:55:31 UTC        5 days -                                      - fstrim.timer                   fstrim.service
Sun 2026-09-06 01:25:59 UTC 1 week 4 days -                                      - update-notifier-motd.timer     update-notifier-motd.service

16 timers listed.
Pass --all to see loaded but inactive timers, too.

 

В них нет ничего особенного. Это обычные таймеры, устроенные так же, как тот, который вы собираетесь собрать сами. Вы можете изучить любой из них с помощью systemctl cat man-db.timer, чтобы понять, как устроен настоящий промышленный таймер.

Обратите внимание, что таймеры зависят от systemd, запущенного с PID 1.

$ ps -p 1
 PID TTY TIME CMD
 1 ? 00:00:06 systemd

 

В большинстве контейнеров Docker, некоторых минимальных chroot-окружениях и некоторых конфигурациях WSL systemd вообще не запущен, поэтому таймеры (и systemctl сам systemd) там не будут работать без дополнительной настройки. Если созданный вами таймер не выполняет никаких действий, сначала проверьте ps -p 1 , прежде чем приступать к отладке файлов модулей.

 

1. Базовая настройка

Допустим, вы хотите создавать резервную копию папки каждый день в 3:30 утра. Вам понадобятся два файла.

  1. Блок службы
  2. Блок таймера

 

Сначала создайте блок службы:

sudo nano /etc/systemd/system/backup.service

 

Добавьте в него следующие строки:

[Unit]
Description=Back up home directory

[Service]
Type=oneshot
ExecStart=/usr/local/bin/backup.sh
Nice=19
IOSchedulingClass=idle
ProtectSystem=strict
ReadWritePaths=/var/backups

 

Затем создайте таймер:

sudo nano /etc/systemd/system/backup.timer

 

Добавьте следующие строки:

[Unit]
Description=Запускать backup.service ежедневно в 3:30

[Timer]
OnCalendar=*-*-* 03:30:00
Persistent=true

[Install]
WantedBy=timers.target

 

Обратите внимание на несколько моментов:

  • Таймер и служба имеют одно и то же имя (backup). systemd использует это совпадение имен для их связывания. Указывать таймеру другое имя службы нужно только в том случае, если вы сами задали Unit= .
  • Type=oneshot подходит для большинства запланированных задач, которые выполняются до конца самостоятельно. Если ваш скрипт запускает фоновый процесс или переходит в режим демона, Type=oneshot не будет корректно отслеживать его выполнение, и вам понадобятся Type=forking или RemainAfterExit=true . В большинстве скриптов, которые вы пишете сами, это не понадобится.
  • Nice=19 и IOSchedulingClass=idle сообщают ядру, что у этой задачи низкий приоритет, поэтому она не конкурирует с более срочными задачами. ProtectSystem=strict делает всю файловую систему доступной только для чтения для этой службы, за исключением путей, которые вы явно разрешаете с помощью ReadWritePaths=. Все это не является обязательным условием для работы таймера, но это небольшие и недорогие меры предосторожности, которые стоит добавить по умолчанию, когда вы минуете этап «а запустится ли это вообще».
  • Вы включаете и запускаете таймер, а не службу. Непосредственно запускать службу нужно только для тестирования.
Читать  APTUI — современный TUI-интерфейс для управления пакетами в Debian, Ubuntu и Linux Mint

 

sudo systemctl daemon-reload
sudo systemctl enable --now backup.timer

2. Два способа планирования: календарное время и относительное время

Здесь большинство новичков путаются, так что давайте не будем торопиться.

2.1 Календарные таймеры (OnCalendar=)

Они срабатывают в фиксированное время, как и cron. Синтаксис взят из systemd.time(7):

OnCalendar=*-*-* 03:30:00 # каждый день в 3:30:00 утра
OnCalendar = Mon,Fri *-*-* 09:00:00 # каждый понедельник и пятницу в 9 утра
OnCalendar=*-*-01 00:00:00 # первого числа каждого месяца, в полночь
OnCalendar=weekly # сокращенный список для понедельника в 00:00
OnCalendar=daily # сокращенный список для каждого дня в полночь
OnCalendar=hourly # сокращенный список для начала каждого часа
OnCalendar=*:0/15 # каждые 15 минут

 

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

$ systemd-analyze calendar "Mon,Fri *-*-* 09:00:00"
  Original form: Mon,Fri *-*-* 09:00:00
Normalized form: Mon,Fri *-*-* 09:00:00
    Next elapse: Mon 2026-08-17 09:00:00 IST
       (in UTC): Mon 2026-08-17 03:30:00 UTC
       From now: 1 day 18h left

 

Запустите это перед включением нового таймера. Это убережет вас от классической ошибки — написания строки OnCalendar, которая выглядит правильно, но срабатывает не вовремя.

Есть и вторая, дополнительная проверка, которую тоже стоит провести:

systemd-analyze verify

 

Эта команда загружает файл модуля так же, как это делает systemd, и выводит все синтаксические ошибки, ничего не запуская.

sudo systemd-analyze verify /etc/systemd/system/backup.timer

 

Это важно, потому что systemd часто прощает опечатки в файлах модулей. Неправильно написанная директива может быть проигнорирована без каких-либо уведомлений, и ваш таймер просто не будет работать так, как вы ожидали. Возьмите за правило запускать команду systemd-analyze verify после каждого редактирования, сразу после daemon-reload.

Обратите внимание, что таймеры systemd по умолчанию не являются точными. Существует скрытая AccuracySec= настройка со значением по умолчанию 1 минута, поэтому systemd может сдвинуть время запуска вашего задания на минуту в ту или иную сторону. Это делается намеренно, чтобы объединять близкие по времени пробуждения и экономить электроэнергию (это очень важно для ноутбуков).

Если вам действительно нужна точность до секунды, установите AccuracySec=1us в разделе [Timer]. Почти для всего, что вы будете создавать на начальном этапе, подойдут настройки по умолчанию, и вы можете ими пренебречь.

 

2.2 Относительные таймеры (OnBootSec=OnUnitActiveSec= и другие)

Этим не нужны настенные часы. Вместо этого они запускаются через определенное время после какого-либо события. В cron нет ничего подобного, так что стоит хорошо в этом разобраться.

ДирективаFires…
OnBootSec=15minЧерез 15 минут после загрузки компьютера
OnStartupSec=15minЧерез 15 минут после запуска systemd
OnUnitActiveSec=1hЧерез 1 час после последнего запуска
OnUnitInactiveSec=1hэтого модуля1 час после последнего остановки
OnActiveSec=30sэтого модуля30 секунд после активации самого модуля таймера

 

Вот ловушка, в которую попадает много людей. OnUnitActiveSec= и OnUnitInactiveSec= звучат почти одинаково, но это не так. Для короткой oneshot задачи разница едва ли имеет значение, поскольку задача в любом случае запускается и останавливается практически мгновенно. Но в случае с долго работающим сервисом эти два метода ведут себя совершенно по-разному. OnUnitActiveSec=1h отсчитывает время с момента запуска сервиса. OnUnitInactiveSec=1h отсчитывает время с момента его остановки. Если перепутать эти методы, ваше расписание незаметно сойдет с курса.

Распространенный шаблон: запускать скрипт очистки через 10 минут после загрузки, а затем еще раз каждые 6 часов.

[Timer]
OnBootSec=10min
OnUnitActiveSec=6h

3. Восполнение пропущенных запусков с помощью Persistent=

Допустим, ваш ноутбук находится в спящем режиме в 3:30 утра, когда backup.timer должен запуститься. Ничего не происходит. Задание просто пропускается, если только вы не добавите эту строку:

[Timer]
Persistent=true

 

При использовании Persistent=true systemd запоминает, когда таймер срабатывал в последний раз (это значение сохраняется в /var/lib/systemd/timers/). Если ваш компьютер пропустил запланированное выполнение задачи из-за того, что был выключен или находился в режиме сна, задание будет выполнено один раз вскоре после следующей загрузки, чтобы наверстать упущенное. Это во многом похоже на работу старого инструмента anacron . Вот почему вам почти по умолчанию понадобится Persistent=true на ноутбуках и настольных компьютерах, в то время как серверам, которые работают постоянно, это часто не требуется.

 

4. Распределение нагрузки с помощью RandomizedDelaySec=

Представьте себе: вы управляете пятьюдесятью серверами, и все они запускают OnCalendar=daily в полночь. Все пятьдесят серверов обращаются к вашему серверу резервного копирования в одну и ту же секунду. Это как стадо слонов, которое может все разрушить.

Читать  Как проверить сведения о версии Ubuntu и другую системную информацию

Исправьте это следующим образом:

[Timer]
OnCalendar=daily
RandomizedDelaySec=1800

 

Теперь каждая машина выбирает свою собственную случайную задержку до 30 минут, прежде чем запустить таймер. Нагрузка распределяется естественным образом. Если вы хотите, чтобы каждая машина каждый раз выбирала одну и ту же задержку (а не новую случайную при каждом запуске), добавьте FixedRandomDelay=true (доступно начиная с systemd 247).

 

5. Команды systemd Timers, которые вы будете использовать каждый день

# Перечислите все активные таймеры и время следующего запуска каждого из них
systemctl list-timers

# Включить таймеры, которые отключены или еще не сработали
systemctl list-timers --all

# Проверить состояние определенного таймера
systemctl status backup.timer

# Проверьте, как прошел последний запуск службы
systemctl status backup.service

# Прочитайте журналы службы, в которой сработал таймер
journalctl -u backup.service

# Запустите службу прямо сейчас, не дожидаясь срабатывания таймера
sudo systemctl start backup.service

# Включите при загрузке и запустите немедленно
sudo systemctl enable --now backup.timer

# Остановите и отключите его
sudo systemctl disable --now backup.timer

# Запустите это после редактирования любого модульного файла
sudo systemctl daemon-reload

 

systemctl list-timers дает вам краткое описание в одной строке:

NEXT                        LEFT     LAST                         PASSED  UNIT           ACTIVATES
Mon 2026-08-17 03:30:00 IST 12h left Sun 2026-08-16 03:30:00 IST  9h ago  backup.timer   backup.service

 

Вы сразу видите, когда он запустится в следующий раз, сколько времени осталось, когда он запускался в последний раз и какую службу он запускает. При использовании cron вам, как правило, приходится полагаться на crontab -l и надеяться на лучшее. Это действительно шаг вперед.

Одно небольшое замечание по поводу логов: journalctl -u backup.service предполагает, что журнал действительно ведет историю. Некоторые минимальные или встроенные дистрибутивы поставляются с Storage=volatile в /etc/systemd/journald.conf, а это значит, что логи хранятся только в памяти и исчезают при перезагрузке. Если вам кажется, что логи исчезли, в первую очередь проверьте этот параметр.

 

6. Что происходит, если задание все еще выполняется, когда таймер срабатывает повторно

Допустим, backup.service обычно завершается за 5 минут, но сегодня по какой-то причине оно все еще выполняется спустя 6 часов, когда таймер должен сработать повторно. Что происходит?

Ничего страшного, но, возможно, не совсем того, чего вы ожидали: systemd не запускает второй экземпляр, который будет работать параллельно. Активация уже активного модуля фактически ничего не меняет. Следующий запланированный запуск таймера проходит без изменений, и сервис продолжает работать до завершения.

Для большинства задач это именно то, что вам нужно, поскольку она предотвращает неконтролируемое нагромождение задач. Но это также означает, что если задание зависнет, вы можете потерять целый день работы, и нигде не будет отображаться ошибка.

Два практических совета:

  • Если задача действительно не должна выполняться параллельно и не должна зависать без каких-либо признаков, используйте TimeoutStartSec= в [Service] (см. список подводных камней ниже), чтобы зависшее задание прерывалось, а не блокировало все последующие.
  • Если вы подозреваете, что работа застопорилась, systemctl status backup.service покажет, что она выполняется active (running) гораздо дольше, чем ожидалось. Это ваш сигнал.

 

7. Быстрые одноразовые таймеры без написания файлов модулей

Иногда нужно запустить что-то один раз, как можно скорее, не создавая пару .timer и .service . systemd-runКоманда выполняет это на лету:

# Запустите команду через 10 минут
sudo systemd-run --on-active="10min" /path/to/script.sh
# Запуск в определенную дату и время
sudo systemd-run --on-calendar="2026-08-20 22:00:00" /path/to/script.sh
# Запускайте через 5 минут после каждой загрузки от имени вашего собственного пользователя
systemd-run --user --on-boot="5min" /path/to/script.sh

 

systemd-run создает временный таймер и службу в фоновом режиме (их можно увидеть с помощью systemctl list-timers), которые автоматически удаляются при перезагрузке.

Это отличный вариант для тестирования идеи расписания или для задачи, которая нужна вам только один раз. Если вы хотите, чтобы что-то пережило перезагрузку и работало вечно, вернитесь к написанию полноценных файлов модулей, как показано выше.

 

8. Запуск таймеров без прав суперпользователя

До сих пор мы рассматривали общесистемные модули в /etc/systemd/system/. Вы также можете настроить таймеры от имени обычного пользователя с помощью флага --user. root не требуется!

mkdir -p ~/.config/systemd/user
# поместите backup.service и backup.timer в эту папку
systemctl --user daemon-reload
systemctl --user enable --now backup.timer

 

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

sudo loginctl enable-linger $USER

9. Таймеры systemd в сравнении с cron: когда что использовать

Преимущества таймеров:

они обеспечивают настоящий логинг через journalctl, так что вам больше не нужны MAILTO= хаки или ручное перенаправление вывода. Вы также можете указать правильные зависимости, например After=network-online.target или Requires=postgresql.service, чего просто не может сделать cron.

Читать  После Arch Linux в Mageia произошел сбой в работе инфраструктуры

Вы можете изолировать службу с помощью таких параметров, как ProtectSystem=strict или PrivateTmp=true. Кроме того, вы получаете встроенное тестирование (systemd-analyze calendar) и наглядный обзор (list-timers), а также упреждающее поведение и джиттер, которые реализованы изначально, а не с помощью скриптов.

 

Аргументы в пользу cron:

Он работает практически везде, включая системы без systemd, такие как Alpine с OpenRC, BSD или урезанная версия контейнера. Однострочная crontab запись намного проще, чем написание двух юнит-файлов, особенно для задачи, у которой вообще нет зависимостей.

И если ваша команда уже много лет использует инструменты на основе cron, то переход на новый способ может не стоить затраченных усилий.

 

Так что же выбрать?

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

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

 

9.1 Преобразование строки crontab в OnCalendar

Если вы переносите существующие задания cron, то будете использовать это сопоставление снова и снова. Поля cron: minute hour day month weekdayOnCalendar= меняет порядок на weekday year-month-day hour:minute:second.

cronЗначениеOnCalendar=
0 3 * * *Каждый день в 3:00OnCalendar=*-*-* 03:00:00
*/15 * * * *Каждые 15 минутOnCalendar=*:0/15
0 9 * * 1-5В будние дни в 9:00OnCalendar=Mon..Fri 09:00:00
0 0 1 * *В первое число каждого месяцаOnCalendar=*-*-01 00:00:00
0 0 * * 0Каждое воскресенье в полночьOnCalendar=Sun *-*-* 00:00:00
@rebootПри загрузкеOnBootSec=0 (эквивалента в OnCalendar нет — это монотонный таймер)

 

Обратите внимание на последнюю строку: @reboot не имеет календарного эквивалента, потому что вообще не привязано ко времени на настенных часах. Именно для этого и существует OnBootSec= — хороший пример того, как таймеры systemd делают то, что структурно невозможно в cron.

 

10. Оповещение о сбое задания

Этот вопрос почти все задают сразу после того, как их первый таймер начинает работать: «Как узнать, что он перестал работать?»

В случае с cron честный ответ обычно звучал так: «Никак, пока кто-нибудь не заметит, что резервные копии пропали».

У systemd есть реальный ответ: OnFailure=.

Добавьте его в свой сервис, указав на второй, небольшой сервис, который отправляет уведомления:

# /etc/systemd/system/backup.service

[Unit]
Description=Back up home directory
OnFailure=alert-on-failure@%n.service

[Service]
Type=oneshot
ExecStart=/usr/local/bin/backup.sh
# /etc/systemd/system/alert-on-failure@.service

[Unit]
Description=Send a failure alert for %i

[Service]
Type=oneshot
ExecStart=/usr/local/bin/notify-failure.sh "%i"

 

%n расширяется до имени устройства, вышедшего из строя, и %i служба оповещения получает его. notify-failure.sh может быть таким же простым, как curl вызов вебхука или вызов mail. Дело не в механизме уведомления, а в том, что OnFailure= срабатывает автоматически, только в случае сбоя, без опрашивания и без дополнительного таймера для проверки первого срабатывания.

 

11. Полный пример: Еженедельная очистка журнала

# /etc/systemd/system/logcleanup.service

[Unit]
Description=Purge logs older than 30 days
After=network.target

[Service]
Type=oneshot
ExecStart=/usr/bin/find /var/log/myapp -name "*.log" -mtime +30 -delete
# /etc/systemd/system/logcleanup.timer

[Unit]
Description=Weekly log cleanup

[Timer]
OnCalendar=Sun *-*-* 04:00:00
Persistent=true
RandomizedDelaySec=600

[Install]
WantedBy=timers.target

 

Теперь запускаем его и проверяем, что он действительно запланирован:

sudo systemctl daemon-reload
sudo systemctl enable --now logcleanup.timer
systemd-analyze calendar "Sun *-*-* 04:00:00" # подтверждаем правильность расписания
systemctl list-timers logcleanup.timer # подтверждаем, что systemd знает о нем
sudo systemctl start logcleanup.service # сразу же проверяем его работу
journalctl -u logcleanup.service -n 20 # проверяем, что все сработало

12. Ошибки, которые совершают новички (и как их избежать)

  1. Пропускdaemon-reload. После редактирования файла unit в памяти systemd остается старая версия, кэшированная в памяти. Всегда перезагружайте.
  2. Включение службы вместо таймера. При этом задание выполняется один раз, немедленно, и больше никогда не выполняется по расписанию.
  3. Перепутывание OnUnitActiveSec= и OnUnitInactiveSec=. В основном это связано с длительной работой сервисов, как описано в разделе 3.2.
  4. Не учитываемPersistent=true. На ноутбуке это означает, что ваша ежедневная работа незаметно пропускает дни, когда машина переходит в режим ожидания в запланированное время.
  5. Забываем о [Install] разделе. Без WantedBy=timers.targetподключать systemctl enable не к чему, поэтому таймер не запустится при загрузке.
  6. Не проверяет состояние после того, как что-то пошло не так. Неудачное oneshot задание отображается как failed, и таймер все равно сработает снова в следующем цикле. Но вы не заметите, пока не проверите журналы или не настроите OnFailure= оповещение.
  7. Ожидая OnCalendar= выстрела в ту же секунду. Как описано в разделе 3.1, значение по умолчанию AccuracySec=1min означает, что ваша работа может затянуться до минуты. Это нормально, а не ошибка.
  8. Доверять файлу unit только потому, что daemon-reload не жаловался. systemd может молча игнорировать директиву с ошибкой, а не выдавать ошибку. Запускайте systemd-analyze verify после внесения изменений, чтобы уловить это.
  9. Предполагая, что зависшее задание в конечном итоге завершится само по себе. По умолчанию этого не происходит. Если выполнение скрипта может зависнуть (из-за устаревшего сетевого подключения или ожидания ввода, который так и не поступил), добавьте TimeoutStartSec= в [Service], чтобы systemd завершила его, а не блокировала при каждом последующем запуске, как описано в разделе 7.

 

13. Краткое руководство по таймерам Systemd

ЗадачаКоманда
Список всех запланированных таймеровsystemctl list-timers --all
Проверка календарного выраженияsystemd-analyze calendar "EXPR"
Проверка файла модуля на наличие синтаксических ошибокsudo systemd-analyze verify /path/to/name.timer
Просмотр активной конфигурации файла модуляsystemctl cat name.timer
Включить и запустить таймерsudo systemctl enable --now name.timer
Запустить службу прямо сейчасsudo systemctl start name.service
Проверить журналы службыjournalctl -u name.service
Перезагрузить после редактирования модулейsudo systemctl daemon-reload
Отключить таймерsudo systemctl disable --now name.timer
Выполнить разовую команду в ближайшее время, без юнит-файлаsystemd-run --on-active="10min" /path/to/script.sh

 

Подробнее о systemd-таймерах читайте на страницах руководства.

  • man systemd.timer полный список директив
  • man systemd.time синтаксис календаря и временных интервалов
  • man systemd.service для параметров службы, таких как Type= и директив «песочницы»

Редактор: AndreyEx

Рейтинг: 5 (1 голос)
Если статья понравилась, то поделитесь ей в социальных сетях:

Оставить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *

14 − 13 =

Это может быть вам интересно


Спасибо!

Теперь редакторы в курсе.

Прокрутить страницу до начала