脚本如何检测用户的空闲时间?

jos*_*lvo 37 xorg bash

我想在 bash 脚本中检查 X 会话的用户空闲多长时间。

用户自己不必使用 bash,而只需使用 X。例如,如果用户只是移动鼠标,一个好的答案是“空闲 0 秒”。如果他在 5 分钟内没有碰过电脑,好的答案应该是“空闲 300 秒”

不立即使用 xautolock 的原因是能够实现一些复杂的行为。例如,如果用户闲置 10 分钟,尝试挂起,如果他闲置超过 5 分钟,则关闭(我知道这听起来很奇怪,但挂起在这里并不总是有效......)

jos*_*lvo 45

刚刚找到了一个简单的方法来做到这一点。

有一个名为 xprintidle 的程序可以解决这个问题

获取空闲时间(以毫秒为单位)非常简单

xprintidle
Run Code Online (Sandbox Code Playgroud)

并安装

apt-get install xprintidle
Run Code Online (Sandbox Code Playgroud)

对于系统管理员,它也可以远程工作

ssh 会话

export DISPLAY=:0 && sudo -u john xprintidle
Run Code Online (Sandbox Code Playgroud)

其中 john 是登录到远程机器上的 X 会话的用户。


请注意,某些程序(例如 MPlayer)似乎会重置计数器。

这可能是可取的,也可能不是,这取决于您的应用程序。对我来说,我打算用它来挂起计算机,而 MPlayer 异常很有帮助。

对于那些不想重置的人,还有另一个答案(https://askubuntu.com/a/1303464/56440),但我还没有亲自测试过


小智 5

使用 josinalvo 的答案可能对某些人有用,但对我来说效果不佳,因为某些程序似乎定期重置计时器xprintidle,意外地依赖于它。此外,我也不希望全屏应用程序重置空闲计时器,至少在我的用例中不是。

所以我在一个不依赖于 X11 屏幕保护程序扩展的 shell 脚本中将我自己的解决方案串在一起。相反,它转储所有用户输入,如鼠标移动和按键使用xinput test-xi2 --root一秒钟,然后将其与最后一秒的转储进行比较。如果它们相同,则变量$t增加 1 并在其他情况下重置。这是循环的,当变量$t超过 treshold 时$idletime,将打印用户空闲。

idleloop() {
    touch /tmp/.{,last_}input
    cmd='stat --printf="%s"'
    idletime=120
    a=2
    t=0
    while true
    do
        timeout 1 xinput test-xi2 --root > /tmp/.input
        
        if [[ `eval $cmd /tmp/.input` == `eval $cmd /tmp/.last_input` ]]
        then
            let t++ # increases $t by 1
        else
            t=0     # resets $t
        fi

        mv /tmp/.{,last_}input -f

        if [ $t -ge $idletime ] && [[ $a == "2" ]]
        then
            echo "user has gone idle"
            a=1
        fi
        if [ $t -lt $idletime ] && [[ $a == "1" ]]
        then
            echo "user has come back from idle"
            a=2
        fi
    done
}

idleloop
Run Code Online (Sandbox Code Playgroud)

随意留下任何建议。