【问题标题】:[: : integer expression expected , by systemctl status of my service that is calling a bash script in ubuntu 18.04[: : 整数表达式,通过我的服务的 systemctl 状态,在 ubuntu 18.04 中调用 bash 脚本
【发布时间】:2019-07-30 15:07:50
【问题描述】:

我对 bash 脚本没有太多经验,但我从互联网上得到了这个想法。

我的 bash 脚本在计算机空闲一段时间后使用 xprintidle 关闭。

我可以在终端运行脚本没有任何问题。 但是当 /etc/systemd/system/poweroff.service 调用脚本时,它会在 systemctl 状态中给出错误。

Jul 30 16:43:40 godo systemd[1]: Started autopoweroff.
Jul 30 16:43:42 godo bash[3107]: couldn't open display
Jul 30 16:43:42 godo bash[3107]: /usr/local/bin/poweroff.sh: line 5: [: : integer expression expected
Jul 30 16:43:42 godo bash[3107]: end

这是脚本:

#!/bin/bash
sleep 2
myidle=$(xprintidle)
myidletime=$((10000))
while [ "$myidle" -le "$myidletime" ]; do
        echo $myidle
        sleep 1
        myidle=$(xprintidle)
done
#sudo shutdown -P now
#shutdown -P 5
echo "end"

这里是服务:

[Unit]
Description=autopoweroff

[Service]
ExecStart=/bin/bash /usr/local/bin/poweroff.sh

[Install]
WantedBy=multi-user.target

我希望你能帮助我,我不会在这些初学者问题上浪费你的时间。

谢谢

【问题讨论】:

  • xprintidle 的输出是什么?
  • couldn't open display 可能会被xprintidle 写入stderr,而不会写入stdout,空的不是有效的整数。可以检查 xprintidle 的退出状态myidle=$(xprintidle) || exit 1 以防止继续执行
  • xprintidle 的退出状态为 status=1/FAILURE 。
  • $((10000)) 没有做任何有用的事情; myidletime=10000 是等价的。

标签: linux bash service ubuntu-18.04 systemd


【解决方案1】:

当 xprintidle 没有显示时,它会打印:“无法打开显示”,然后您尝试使用“-le”将此无效值作为整数进行比较。

由于xprintidle在没有显示的时候返回退出码1,所以可以使用

       set -e

在脚本开始时出现错误时退出。

【讨论】:

  • 是的,它在带有 xprintidle 的行退出。所以它不返回整数?但是在终端中运行它有什么不同,因为我从 xprintidle 得到了 echo 输出?
【解决方案2】:

xprintidle - 实用程序打印用户在 X 中的空闲时间

当您的脚本在 systemd 上下文中运行时,它没有 X 服务器,因此 xprintidle 失败并将 couldn't open display 输出到 stderr。

您的语句myidle=$(xprintidle) 导致myidle 分配失败。

此时你必须决定当 X 环境不可用时你想做什么。

一种可能性,是让myidle 具有默认值 0:

typeset -i myidle # Tells Bash it is an int and default to 0 if not assigned a value
myidle=$(xprintidle 2>/dev/null) || true # no error state generated

我认为您需要另一种方法来获取当前正在运行的 X 会话的空闲值。

这里是:

#!/bin/dash
sleep 2
# get the X DISPLAY of the first logged-in user with a X session
DISPLAY="$(
  w --short --no-header \
    | awk '{ if( match($3, ":") ) { print $3; exit; } }'
)"
export DISPLAY

myidletime=$((10000))
while myidle=$(xprintidle 2>/dev/null) && [ "$myidle" -le $myidletime ]; do
  echo "$myidle"
  sleep 1
done
#sudo shutdown -P now
#shutdown -P 5
echo "end"

【讨论】:

  • 在终端中它显示:排版:未找到,但它可以在没有终端排版的情况下工作。但是作为服务它仍然不起作用: + DISPLAY=:0 + export DISPLAY ++ xprintidle + myidle= + true + '[' '' -le 10000 ']' [: : integer expression expected
  • @jonas99g 忘记systemd 使用dash 而不是bash。我更改了答案中的代码以适应dash
  • 非常感谢。我不知道。
  • 不知何故它仍然无法正常运行......但也许我首先需要了解你的代码来学习它。 + export DISPLAY + myidletime=50000 + xprintidle + myidle= + echo end
  • xprintidle 需要一个 X 显示服务器才能与之通信。在systemd 的上下文中,没有显示服务器。我的代码对 w 和 awk 的作用是从他能找到的第一个登录用户中提取 X 显示。然后它导出 DISPLAY 变量。
猜你喜欢
  • 2017-07-12
  • 2014-11-30
  • 2019-08-20
  • 2020-06-12
  • 2020-06-03
  • 2020-08-02
  • 1970-01-01
  • 2016-11-26
  • 2012-07-07
相关资源
最近更新 更多