Корректное завершение работы компьютера через терминал

Аватар пользователя DA

Многим известны команды shutdown, halt, reboot, но у них есть как минимум два недостатка:

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

К счастью, мы живём в просвещённый век D-Bus, где это уже решено.

KDE

Среда KDE тесно интегрирована с этой системой и предоставляет метод org.kde.KSMServerInterface.logout для корректного завершения работы компьютера: qdbus org.kde.ksmserver /KSMServer org.kde.KSMServerInterface.logout -1 -1 -1
Рассмотрим параметры, которые передаются методу. Для начала, -1 передаёт значение по умолчанию.
Первый параметр называется confirm и отвечает за подтверждение завершения работы. 0 приводит к непосредственному выключению, а 1 вызывает всем известное окошко с 30 секундной задержкой.
Второй параметр — sdtype — выбирает тип завершения работы:

  • 0 — не завершать работу (у меня идентичен 3);
  • 1 — перезагрузка;
  • 2 — выключение;
  • 3 — завершение сеанса.

Третий параметр — sdmode — выбирает режим завершения работы:

  • 0 — отложить завершение до того, как будут закрыты все активные сессии;
  • 1 — завершить сейчас, если нет активных сессий, иначе ничего не делать;
  • 2 — закрыть все сессии и завершить работу
  • 3 — если есть активные сессии, спросить у пользователя, как поступить.

С помощью systemd

  • Завершить работу и перезагрузить компьютер: systemctl reboot
  • Завершить работу и выключить компьютер: systemctl poweroff
  • Завершить работу и остановить(без выключения питания?) компьютер: systemctl halt
  • Перевести систему в состояние ожидания: systemctl suspend
  • Перевести систему в состояние гибернации: systemctl hibernate

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

Общий случай

Также можно воспользоваться ConsoleKit и UPower:

  • выключение: dbus-send --system --print-reply --dest="org.freedesktop.ConsoleKit" /org/freedesktop/ConsoleKit/Manager org.freedesktop.ConsoleKit.Manager.Stop
  • перезагрузка: dbus-send --system --print-reply --dest="org.freedesktop.ConsoleKit" /org/freedesktop/ConsoleKit/Manager org.freedesktop.ConsoleKit.Manager.Restart
  • ждущий режим: dbus-send --system --print-reply --dest="org.freedesktop.UPower" /org/freedesktop/UPower org.freedesktop.UPower.Suspend
  • спящий режим: dbus-send --system --print-reply --dest="org.freedesktop.UPower" /org/freedesktop/UPower org.freedesktop.UPower.Hibernate

Ещё больше удобства

Чтобы не запоминать все эти простыни, можно добавить соответствующие алиасы в конфиг вашего шелла. Например, я добавил в ~/.zshrc
alias haltk='qdbus org.kde.ksmserver /KSMServer org.kde.KSMServerInterface.logout 1 2 2'
alias rebootk='qdbus org.kde.ksmserver /KSMServer org.kde.KSMServerInterface.logout 1 1 2'
alias logoutk='qdbus org.kde.ksmserver /KSMServer org.kde.KSMServerInterface.logout 1 3 2'

alias haltd='dbus-send --system --print-reply --dest="org.freedesktop.ConsoleKit" /org/freedesktop/ConsoleKit/Manager org.freedesktop.ConsoleKit.Manager.Stop'
alias rebootd='dbus-send --system --print-reply --dest="org.freedesktop.ConsoleKit" /org/freedesktop/ConsoleKit/Manager org.freedesktop.ConsoleKit.Manager.Restart'

Credits