Python Bash-如何在连接USB设备时运行代码

Python Bash-如何在连接USB设备时运行代码,python,linux,bash,keyboard,usb,Python,Linux,Bash,Keyboard,Usb,我正在编写一个bash脚本来自动检测USB键盘何时插入我的笔记本电脑(运行Ubuntu 14),这样我就可以自动更改键盘布局 这是我到目前为止的代码(我是从另一篇关于堆栈溢出的文章中得到的,所以我不能100%确定它是如何工作的) 到目前为止,我已经在启动时运行了这个。。。但我希望它在每次连接或断开USB设备时运行 重要的是,我必须在一个Bash脚本中运行所有这些脚本,而不是在…udev/…中作为.rules文件运行。。。或者别的什么。但是,一个Python脚本也可以。这很有效,因为在linux系

我正在编写一个bash脚本来自动检测USB键盘何时插入我的笔记本电脑(运行Ubuntu 14),这样我就可以自动更改键盘布局

这是我到目前为止的代码(我是从另一篇关于堆栈溢出的文章中得到的,所以我不能100%确定它是如何工作的)

到目前为止,我已经在启动时运行了这个。。。但我希望它在每次连接或断开USB设备时运行


重要的是,我必须在一个Bash脚本中运行所有这些脚本,而不是在…udev/…中作为.rules文件运行。。。或者别的什么。但是,一个Python脚本也可以。这很有效,因为在linux系统上,文件系统结构总是相同的

cat$dev/bInterfaceClass
查询每个usb设备的接口类

cat$dev/bInterfaceProtocol
查询每个usb设备的接口协议

尝试
ls/sys/bus/usb/devices/
,您将看到所有usb设备节点

然后选择一个,即
ls/sys/bus/usb/devices/usb1
并使用
ls/sys/bus/usb/devices/usb1/idVendor

我将使用
idVendor
idProduct
而不是
bInterfaceProtocol
,您可以通过连接键盘,使用
lsusb
并从列表中选择来确定键盘的产品ID和供应商ID

更新

下面的脚本将完成此操作。插入设备的供应商和产品id。可能在没有
setxkbmap
命令的情况下进行测试。
标志
变量用于不每隔5秒设置键盘映射

#!/bin/bash

flag=0


while true

do

for dev in /sys/bus/usb/devices/*-*
do
    if [ -f $dev/idVendor ]
    then
        if [[ "$(cat $dev/idVendor)" == "your_vendor_id" && "$(cat $dev/idProduct)" == "your_product_id" ]]
        then
            if [[ "$flag" == "0" ]]
              then
                echo 'USB device attached'
                 setxkbmap gb
            fi
            flag=1
            break
        fi 
            if [[ "$flag" == "1" ]]
               then
                 echo 'USB device detached'
                 setxkbmap es
            fi
            flag=0
    fi

 done

  sleep 5s

done
请注意,要使
setxkbmap
正常工作,必须安装
x11 xkb utils

()

多亏了你,我才想出了下面的解决方案。 它有以下改进:

  • 它不依赖于特定的键盘,它将以相同的方式处理所有USB键盘
  • 如果用户手动切换到不同的键盘布局(既不是默认键盘也不是USB键盘),则不会自动将其切换回默认或USB布局
请随时在以下位置改进此代码:


@贝塞拉先生,这不是我要找的。。“重要的是,我必须在一个Bash脚本中运行它,而不是在…udev/…中作为.rules文件运行。”感谢改进,但这并不能真正回答我的问题。我想问的是,如何让它检测usb的插入或拔出时间,这样每当我插入键盘时,它都会改变,而不是只插入一次(启动时)。我想这会起作用,但是每5秒钟检查一次似乎不是很正统​... 是否没有一种方法可以在每次连接或分离USB设备时运行?我决定使用这个方法,但我保留了接口类和协议,而不是供应商和产品ID。我将其放在这里的要点中:更新了上面的答案,删除了下面的另一个版本,因为SIGPIPE机制工作不可靠。每5秒轮询一次非常节省CPU…为什么要重复几乎相同的代码两次?为什么它比以前更好?这似乎只运行一次代码,然后在循环中每隔5秒再次运行一次。让第一次跑步不在循环中有什么意义?
#!/bin/bash

flag=0


while true

do

for dev in /sys/bus/usb/devices/*-*
do
    if [ -f $dev/idVendor ]
    then
        if [[ "$(cat $dev/idVendor)" == "your_vendor_id" && "$(cat $dev/idProduct)" == "your_product_id" ]]
        then
            if [[ "$flag" == "0" ]]
              then
                echo 'USB device attached'
                 setxkbmap gb
            fi
            flag=1
            break
        fi 
            if [[ "$flag" == "1" ]]
               then
                 echo 'USB device detached'
                 setxkbmap es
            fi
            flag=0
    fi

 done

  sleep 5s

done
#!/bin/bash
kbd1=es #default keyboard layout
kbd2=gb #USB keyboard layout

flag=0
while true
do
    layout="$(setxkbmap -query | grep -a layout | cut -c13-14)"
    if [[ $layout == $kbd1 ]] || [[ $layout == $kbd2 ]]
    then
        for dev in /sys/bus/usb/devices*-*
        do
            if [ -f $dev/bInterfaceClass ]
            then
                if [[ "$(cat $dev/bInterfaceClass)" == "03" && "$(cat 
$dev/bInterfaceProtocol)" == "01" ]]
                then
                    if [[ "$flag" == "0" ]]
                    then
                            setxkbmap $kbd2
                    fi
                    flag=1
                    break
                fi 
                if [[ "$flag" == "1" ]]
                then
                    setxkbmap $kbd1
                fi
                flag=0
            fi
        done
    fi
    sleep 5s
done