AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / unix / 问题 / 780347
Accepted
Alexander Praehauser
Alexander Praehauser
Asked: 2024-07-18 04:30:50 +0800 CST2024-07-18 04:30:50 +0800 CST 2024-07-18 04:30:50 +0800 CST

Systemd-user-service 启用键盘没有错误,但不起作用

  • 772

我的笔记本电脑键盘很差,但 Lily58 好得多,所以我写了一个 bash 脚本来禁用我的笔记本电脑键盘,这样我就可以将 Lily58 放在上面,然后再重新启用它。但是当我禁用笔记本电脑键盘时,如果我将笔记本电脑挂起,它就会保持禁用状态,而我希望它在恢复时自动重新启用。所以我写了一个简短的 bash 脚本

#!/bin/bash

fconfig="/home/alex/.keyboard" 
id=$(xinput | grep AT | sed -n '2,2p' | awk '{print $7}' | sed 's/[^0-9]*//g')

if [ -f $fconfig ]; then
  read -r var< $fconfig
  if [ "$var" = "disabled" ]; then
      xinput enable $id
      echo "enabled" > $fconfig
  fi
fi

/home/alex/.keyboard这将检查跟踪键盘是否启用的文件中是否存在“disabled” ,如果是,则xinput使用通过筛选输出获得的 id 运行以重新启用,xinput 方式与 的定义相同id,然后设置/home/alex/.keyboard为enabled。当我从终端触发 bash 脚本时,此操作可以正常工作,但是当我启动 systemd 服务时

[Unit]
Description=This service enables your keyboard after suspension
PartOf=graphical-session.target

[Service]
Type=oneshot
ExecStart=/home/alex/bash/enable-keyboard

[Install]
WantedBy=multi-user.target

我想在暂停后运行,它设置/home/alex/.keyboard为enabled但实际上并没有重新启用我的键盘。此外,journalctl -xeu enable-keyboard.service没有指示任何错误:

Jul 17 22:16:25 gentoolaptop systemd[795]: Starting This service enables your keyboard after suspension.
░░ Subject: A start job for unit UNIT has begun execution
░░ Defined-By: systemd
░░ Support: https://gentoo.org/support/
░░ 
░░ A start job for unit UNIT has begun execution.
░░ 
░░ The job identifier is 8969.
Jul 17 22:16:25 gentoolaptop systemd[795]: Finished This service enables your keyboard after suspension.
░░ Subject: A start job for unit UNIT has finished successfully
░░ Defined-By: systemd
░░ Support: https://gentoo.org/support/
░░ 
░░ A start job for unit UNIT has finished successfully.
░░ 
░░ The job identifier is 8969.

出了什么问题?

编辑:如果我将一个子句放入脚本中以将输出打印xinput到文件中,则输出将由一个空行组成。

编辑:的输出systemctl --user status dbus.socket dbus.service是

● dbus.socket - D-Bus User Message Bus Socket
Loaded: loaded (/usr/lib/systemd/user/dbus.socket; static)
                Active: active (running) since Thu 2024-07-18 17:22:54 CEST; 5 days ago
                Triggers: ● dbus.service
                Listen: /run/user/1000/bus (Stream)
                Tasks: 0 (limit: 47295)
                Memory: 4.0K (peak: 1.5M)
                CPU: 8ms
                CGroup: /user.slice/user-1000.slice/[email protected]/app.slice/dbus.socket

                Jul 18 17:22:54 gentoolaptop systemd[830]: Starting D-Bus User Message Bus Socket...
                Jul 18 17:22:54 gentoolaptop systemd[830]: Listening on D-Bus User Message Bus Socket.

                ● dbus.service - D-Bus User Message Bus
                Loaded: loaded (/usr/lib/systemd/user/dbus.service; static)
                                Active: active (running) since Thu 2024-07-18 17:22:54 CEST; 5 days ago
                                TriggeredBy: ● dbus.socket
                                Docs: man:dbus-daemon(1)
                                Main PID: 897 (dbus-daemon)
                                Tasks: 1 (limit: 47295)
                                Memory: 1.0M (peak: 1.7M)
                                CPU: 252ms
                                CGroup: /user.slice/user-1000.slice/[email protected]/session.slice/dbus.service
                                └─897 /usr/bin/dbus-daemon --session --address=systemd: --nofork --nopidfile --systemd-activation --syslog-only

                                Jul 23 16:55:45 gentoolaptop dbus-daemon[897]: [session uid=1000 pid=897 pidfd=5] Activating via systemd: service name='org.freedesktop.Notifications' unit='dunst.service' requested by ':1.149' (uid=1000 pid=105378 comm="/bin/dunstify Battery <80 Battery under 80%.")
                                Jul 23 17:11:00 gentoolaptop dbus-daemon[897]: [session uid=1000 pid=897 pidfd=5] Failed to activate service 'org.freedesktop.Notifications': timed out (service_start_timeout=120000ms)
                                Jul 23 17:19:31 gentoolaptop dbus-daemon[897]: [session uid=1000 pid=897 pidfd=5] Activating via systemd: service name='org.freedesktop.Notifications' unit='dunst.service' requested by ':1.152' (uid=1000 pid=106706 comm="/bin/dunstify Battery <80 Battery under 80%.")
                                Jul 23 17:21:31 gentoolaptop dbus-daemon[897]: [session uid=1000 pid=897 pidfd=5] Failed to activate service 'org.freedesktop.Notifications': timed out (service_start_timeout=120000ms)
                                Jul 23 17:30:31 gentoolaptop dbus-daemon[897]: [session uid=1000 pid=897 pidfd=5] Activating via systemd: service name='org.freedesktop.Notifications' unit='dunst.service' requested by ':1.153' (uid=1000 pid=108520 comm="/bin/dunstify Battery <80 Battery under 80%.")
                                Jul 23 17:32:31 gentoolaptop dbus-daemon[897]: [session uid=1000 pid=897 pidfd=5] Failed to activate service 'org.freedesktop.Notifications': timed out (service_start_timeout=120000ms)
                                Jul 24 14:15:05 gentoolaptop dbus-daemon[897]: [session uid=1000 pid=897 pidfd=5] Activating via systemd: service name='org.freedesktop.Notifications' unit='dunst.service' requested by ':1.164' (uid=1000 pid=126615 comm="/bin/dunstify Battery <80 Battery under 80%.")
                                Jul 24 14:17:05 gentoolaptop dbus-daemon[897]: [session uid=1000 pid=897 pidfd=5] Failed to activate service 'org.freedesktop.Notifications': timed out (service_start_timeout=120000ms)
                                Jul 24 14:26:05 gentoolaptop dbus-daemon[897]: [session uid=1000 pid=897 pidfd=5] Activating via systemd: service name='org.freedesktop.Notifications' unit='dunst.service' requested by ':1.165' (uid=1000 pid=127823 comm="/bin/dunstify Battery <80 Battery under 80%.")
                                Jul 24 14:28:05 gentoolaptop dbus-daemon[897]: [session uid=1000 pid=897 pidfd=5] Failed to activate service 'org.freedesktop.Notifications': timed out (service_start_timeout=120000ms)

的输出ls -l /run/user/*/bus是

srw-rw-rw-   1 alex           alex            0 2024-07-18 17:22 /run/user/1000/bus
```.
systemd
  • 2 2 个回答
  • 83 Views

2 个回答

  • Voted
  1. Best Answer
    Tom Yan
    2024-07-21T19:00:03+08:002024-07-21T19:00:03+08:00

    注意:此答案假定您的桌面环境会将DISPLAY环境XAUTHORITY变量导入到 systemd 用户管理器,并且您始终使用相同的用户帐户登录。

    xinput是一个 X 实用程序。换句话说,它是一个 X 客户端。因此,您需要使用DISPLAY环境变量来指示它应该与哪个 X 服务器通信(即使只有一个正在运行),并允许它使用环境连接到该XAUTHORITY服务器。

    棘手的是,似乎没有一种巧妙的方法可以让登录用户的用户管理器在系统休眠(和恢复)时启动用户服务。此外,从技术上讲,您可以让多个用户登录并运行多个 X 服务器,因此实际上没有办法“改进”这种情况下的运作方式,至少在不依赖一些肮脏假设的情况下是没有办法的。

    话虽如此,只要您同意这些假设,您仍然可以“硬编码”解决方案:

    [Unit]
    Description=This service enables your keyboard after suspension
    PartOf=sleep.target
    Before=sleep.target
    
    [Service]
    Type=oneshot
    RemainAfterExit=yes
    ExecStart=/usr/bin/true
    ExecStop=/usr/bin/runuser alex -c 'systemd-run --user /home/alex/bash/enable-keyboard'
    
    [Install]
    WantedBy=sleep.target
    

    systemd-run --user可以在系统服务中使用runuser,因此请勿将其替换为User=。另外,请勿将其用作用户服务。


    编辑:由于看起来您的方法似乎runuser没有按预期工作,您可能想尝试以下版本:

    [Unit]
    Description=This service enables your keyboard after suspension
    PartOf=sleep.target
    Before=sleep.target
    
    [Service]
    Type=oneshot
    RemainAfterExit=yes
    User=alex
    Environment=XDG_RUNTIME_DIR=/run/user/1000 DBUS_SESSION_BUS_ADDRESS=unix:path=/run/user/1000/bus
    ExecStart=/usr/bin/true
    ExecStop=/usr/bin/systemd-run --user /home/alex/bash/enable-keyboard
    
    [Install]
    WantedBy=sleep.target
    

    确保在以下行之前~/.xinitrc至少包含一行源/etc/X11/xinit/xinitrc.d/50-systemd-user.sh (假设该文件存在于您的系统中)exec:

    . /etc/X11/xinit/xinitrc.d/50-systemd-user.sh
    

    启用服务后,每次系统恢复后(即sleep.target停止时,因此有PartOf=和ExecStop=)都应调用该脚本。

    PS 您甚至可以在脚本中硬编码(DISPLAY)。在这种情况下应该可以工作。XAUTHORITYexportExecStop=/home/alex/bash/enable-keyboard


    如果您还需要/home/alex/bash/enable-keyboard在图形登录时运行,请为其编写另一个服务(这次它可能应该是用户服务):

    [Unit]
    Description=This service enables your keyboard after suspension
    After=graphical-session.target
    
    [Service]
    Type=oneshot
    ExecStart=/home/alex/bash/enable-keyboard
    
    [Install]
    WantedBy=graphical-session.target
    

    确保使用 启用了此服务systemctl --user。此外,只有当您的桌面环境graphical-session.target在图形登录时被真正拉入时,它才会起作用。

    (注意:当您使用时startx,目标很可能不会被拉入。您应该在~/.xinitrc该exec行之前调用(而不是源,尽管它可能没问题)您的脚本,或者如果您真的希望用户管理器调用它,请使用systemctl --user启动目标或服务~/.xinitrc(再次,在该exec行之前)。)

    它不能是系统服务的原因是,假设脚本需要在用户会话中的 X 服务器启动后运行,您需要在脚本中轮询(或滥用Restart=)并等到那时。(但当然,您可以让它与显示管理器的 X 服务器对话(如果有的话),并且效果会保留。但随后您将需要找出并硬编码相应的DISPLAY和XAUTHORITY,并且根据显示管理器如何与 systemd“交互”,它可能注定是“不雅的”,您将需要一些令人讨厌的“睡眠 5”。)

    您甚至可以直接使用xinitrc.d脚本、XDG 自动启动或在您的 DE 下运行的任何脚本来调用该脚本。

    • 1
  2. Schmaehgrunza
    2024-07-20T00:16:55+08:002024-07-20T00:16:55+08:00

    您说得对,xinput 没有输出。我已经测试过了。
    系统服务单元在 Xorg 的范围/环境之外运行。
    您必须将您的单元放入 中/usr/lib/systemd/user/myservice.service,然后您才能获得完全访问权限。

    我尝试过。在或更好的是,在中创建了一个服务myservice.service/usr/lib/systemd/user/home/[username]/.config/systemd/user

    [Unit]
    Description=test
    
    [Service]
    Type=simple
    Restart=on-failure
    ExecStart=absolute path to service script
    
    [Install]
    WantedBy=graphical-session.target
    

    我的服务脚本:

    #!/usr/bin/bash
    while :; do
       if [[ -a "/tmp/suspension_wakeup" ]]; then
          wake_up=$(< /tmp/suspension_wakeup);
          if [[ $wake_up == "true" ]]; then
             echo "$(xinput)" > /tmp/xinput
             echo "false" > /tmp/suspension_wakeup
          fi
       fi
       sleep 10
    done
    

    我正在读取tmp 文件夹中名为pause_wakeup的文件。 如果pause_wakeup包含"true",则将xinput回显到tmp文件夹中名为xinput 的文件。您可以在此处添加代码,而不是回显。 然后将 false写入pause_wakeup。

    我将把另一个名为suspension_wakeup(可执行脚本)的文件放入/usr/lib/systemd/system-sleep

    #!/usr/bin/bash
    [[ $1 == "post" ]] && { umask 0111; echo "true" > /tmp/suspension_wakeup; }
    

    此脚本在tmp 文件夹中的 pause_wakeup 文件中写入“true”。这会导致服务单元回显 xinput 或执行您的工作(如果您插入该内容)。

    该服务已启用:
    systemctl --user enable myservice.service

    并开始
    systemctl --user start myservice.service

    您必须在每个 systemctl 命令的“systemctl”后面加上“--user”

    每次计算机进入睡眠状态并唤醒时,这种方法都有效。

    更好的办法是让脚本/usr/lib/systemd/system-sleep改变键盘。但我试了又试,没有解决办法。也许你有什么想法?如果你有,请告诉我。

    • 0

相关问题

  • journalctl 中的区分级别

  • 将默认编辑器更改为 vim for _ sudo systemctl edit [unit-file] _

  • systemd:如何在服务启动时运行脚本,而不编辑服务定义

  • 使用 systemd 看门狗支持重新启动应用程序

  • 使用键盘快捷键启动/停止 systemd 服务 [关闭]

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    模块 i915 可能缺少固件 /lib/firmware/i915/*

    • 3 个回答
  • Marko Smith

    无法获取 jessie backports 存储库

    • 4 个回答
  • Marko Smith

    如何将 GPG 私钥和公钥导出到文件

    • 4 个回答
  • Marko Smith

    我们如何运行存储在变量中的命令?

    • 5 个回答
  • Marko Smith

    如何配置 systemd-resolved 和 systemd-networkd 以使用本地 DNS 服务器来解析本地域和远程 DNS 服务器来解析远程域?

    • 3 个回答
  • Marko Smith

    dist-upgrade 后 Kali Linux 中的 apt-get update 错误 [重复]

    • 2 个回答
  • Marko Smith

    如何从 systemctl 服务日志中查看最新的 x 行

    • 5 个回答
  • Marko Smith

    Nano - 跳转到文件末尾

    • 8 个回答
  • Marko Smith

    grub 错误:你需要先加载内核

    • 4 个回答
  • Marko Smith

    如何下载软件包而不是使用 apt-get 命令安装它?

    • 7 个回答
  • Martin Hope
    user12345 无法获取 jessie backports 存储库 2019-03-27 04:39:28 +0800 CST
  • Martin Hope
    Carl 为什么大多数 systemd 示例都包含 WantedBy=multi-user.target? 2019-03-15 11:49:25 +0800 CST
  • Martin Hope
    rocky 如何将 GPG 私钥和公钥导出到文件 2018-11-16 05:36:15 +0800 CST
  • Martin Hope
    Evan Carroll systemctl 状态显示:“状态:降级” 2018-06-03 18:48:17 +0800 CST
  • Martin Hope
    Tim 我们如何运行存储在变量中的命令? 2018-05-21 04:46:29 +0800 CST
  • Martin Hope
    Ankur S 为什么 /dev/null 是一个文件?为什么它的功能不作为一个简单的程序来实现? 2018-04-17 07:28:04 +0800 CST
  • Martin Hope
    user3191334 如何从 systemctl 服务日志中查看最新的 x 行 2018-02-07 00:14:16 +0800 CST
  • Martin Hope
    Marko Pacak Nano - 跳转到文件末尾 2018-02-01 01:53:03 +0800 CST
  • Martin Hope
    Kidburla 为什么真假这么大? 2018-01-26 12:14:47 +0800 CST
  • Martin Hope
    Christos Baziotis 在一个巨大的(70GB)、一行、文本文件中替换字符串 2017-12-30 06:58:33 +0800 CST

热门标签

linux bash debian shell-script text-processing ubuntu centos shell awk ssh

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve