我有一个用 python 编写的脚本:
#!/usr/bin/python3
from tkinter import messagebox
variable = messagebox.showinfo('title', 'question')
这个 python 脚本除了在屏幕上显示一个消息框之外什么也不做。当我将 USB 驱动器连接到我的计算机时,我想启动该脚本。
所以我在目录/etc/udev/rules.d/中创建了一个新文件10-myself.rules。
KERNEL="sdb",RUN+="/usr/bin/python3 /home/user/projects/path_to_python.py"
但当我将 USB 驱动器插入计算机时,我没有看到任何消息框。错误在哪里?我该如何调试呢?
我也调用了命令
udevadm control --reload-rules
我尝试将规则更改为
KERNEL="sdb*",RUN+="/usr/bin/python3 /home/user/projects/path_to_python.py"
或按规则
KERNEL="sdb1",RUN+="/usr/bin/python3 /home/user/projects/path_to_python.py"
如果我将脚本更改为
file1 = open("/home/user/udev.txt", "w")
file1.write("Hello")
file1.close()
那么这个脚本就可以工作了。
答案1
我猜测代码以 root 或 udev 用户身份运行,并且这些用户无权与您的窗口管理器聊天并创建 Tk 窗口等。某种形式的通信可能会有所帮助,例如 udev 脚本写入日志条目,或将消息发送到套接字,窗口管理器环境中的另一端可以从中读取消息并采取适当的操作。
答案2
当您从交互式 shell 运行该脚本时,您有一个DISPLAY
环境变量指示您有权连接的服务器。
当它运行时,udev
情况并非如此。
一般来说,您不想udev
做任何依赖于 X11 启动和运行的事情,并且您当然不想以这种方式增加其攻击面。
看来您正在寻找订阅/通知系统,因此您可以使用 X 会话启动侦听器(像您自己一样),并让通知程序从 运行udev
。为此,您可能需要研究 DBus 或 UDisks;或者,您可以开始inotifywait
监视设备文件的创建,并在脚本中读取其事件(同样,全部以用户身份,而不是 root 身份)。