TL;DR
- macOS には
caffeinate
というコマンドが標準であって、スリープ突入を一時的に抑制できるよ -
launchd
というプロセスが macOS では常時動いていて、システム起動のタイミングとかログインのタイミングでプログラムを起動したりしてくれているよ -
launchd
にcaffeinate
コマンドをユーザーログインのタイミングで起動させたらあとは自動的にスリープ突入が抑制できたよ
使い方
caffeinate.plist
ファイルを作る
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>Label</key>
<string>caffeinate</string>
<key>ProgramArguments</key>
<array>
<string>/bin/sh</string>
<string>-c</string>
<string>exec caffeinate -s -w $$</string>
</array>
<key>RunAtLoad</key>
<true/>
</dict>
</plist>
~/Library/LaunchAgents
ディレクトリにコピー
launchd に認識させる
ターミナルなどで以下のコマンドを実行する。
launchctl load ~/Library/LaunchAgents/caffeinate.plist
補足
適用範囲
この小細工を上記の手順で導入した場合、導入された Mac は導入したユーザーがログインすると AC 電源が繋がっている限り蓋を閉めようが何をしようが勝手にスリープしない状態になる。
ログアウトだけして放置するなどした場合の挙動については未調査。
一時停止
この小細工を一時的に無効にして、勝手にスリープする状態に戻すには、以下のコマンドを実行する。
launchctl stop caffeinate
再度有効にするには以下のコマンドを実行するか、 Mac を再起動する。
launchctl start caffeinate
アンインストール
この小細工を取り除いて恒久的に向こうにするには、以下のコマンドを実行する。
launchctl unload ~/Library/LaunchAgents/caffeinate.plist
caffeinate.plist ファイルは削除してもしなくても良い。
~/Library/LaunchAgents
以外のインストール先
インストール先によって、どのタイミングでスリープ抑制がかかるのかが変化する。
詳しくは launchd.plist(5) を参照。
/Library/LaunchAgents
/Library/LaunchDaemons
-
/System/Library/LaunchAgents
(今日の macOS では勝手にここへファイルを置けない) -
/System/Library/LaunchDaemons
(同上)
agent と daemon の違いは http://www.maruko2.com/mw/LaunchDaemons_(launchctl,_launchd.plist)_%E3%81%AE%E4%BD%BF%E3%81%84%E6%96%B9#Daemon_.E3.81.A8_Agent_.E3.81.AE.E9.81.95.E3.81.84 が端的にまとまっている。
動作原理
launchd に caffeinate コマンドを自動起動させることで、スリープを抑制する。
caffeinate コマンドのオプションに -w pid
というものがあるが、これによって pid をプロセス ID に持つプロセスが終了するまでスリープをしないで欲しいとカーネルに要請できる。
ところで、この pid の検査がザルのため、 caffeinate コマンド自身の PID を指定しても問題なくカーネルに受理されてしまい、結果として caffeinate コマンドが自身の終了を待つような動き、すなわち永久にスリープ突入を阻止できるという目標が達成できる。
詳しくは launchd.plist(5) caffeinate(8) を参照。