简体   繁体   English

如何使用 Python 异步运行终端命令?

[英]How can I run a terminal command asynchronously using Python?

I am working on a Linux environment, trying to automate these 2 Linux commands using a Python script:我正在研究 Linux 环境,尝试使用 Python 脚本自动化这两个 Linux 命令:

  1. sudo rfcomm connect 0 XX:XX:XX:XX:XX:XX sudo rfcomm 连接 0 XX:XX:XX:XX:XX:XX
  2. hcitool rssi XX:XX:XX:XX:XX:XX hcitool rssi XX:XX:XX:XX:XX:XX

Command 1 connects to my bluetooth device, and command 2 returns the received signal strength inidication (RSSI) as long as the device is connected.命令 1 连接到我的蓝牙设备,只要设备连接,命令 2 就会返回接收到的信号强度指示 (RSSI)。 So the script must be able to connect and then extract RSSI without any human intervention.因此,脚本必须能够连接并提取 RSSI,而无需任何人工干预。 I am running these commands using the subprocess module.我正在使用subprocess模块运行这些命令。

The problem: When command 1 is run such that a connection is made, it says " Connected /dev/rfcomm0 to XX:XX:XX:XX:XX:XX on channel 1 Press CTRL-C for hangup ", however it does not return.问题:当命令 1 运行以建立连接时,它显示“ Connected /dev/rfcomm0 to XX:XX:XX:XX:XX:XX on channel 1 Press CTRL-C for hangup ”,但它没有返回。 It only returns once the connection is lost, at which point it would be impossible to extract RSSI.它仅在连接丢失时返回,此时无法提取 RSSI。 Currently the python script does not continue to the next line of code after running command 1, so I am unable to run command 2 afterwards.目前 python 脚本在运行命令 1 后不会继续到下一行代码,所以之后我无法运行命令 2。 Here is my code:这是我的代码:

def get_rssi(): 
    while True:
        p1 = subprocess.run(['hcitool', 'rssi', shimmer_id], capture_output=True, text=True)
        
        if p1.stderr:
            print('stderr:', p1.stderr)
            reconnect()
        if p1.stdout:
            print('stdout:', p1.stdout)
            time.sleep(0.3)


def reconnect():
    reconnected = False
    print('[-] lost connection, reconnecting...')
    
    while reconnected is False:
        p2 = subprocess.run(['sudo', 'rfcomm', 'connect', '0', shimmer_id], capture_output=True, text=True)
        
# If the connection on the previous line is successful, nothing is executed from  here onward! The script only continues once the above line returns (i.e. when the connection is lost)

        if p2.stderr:
            if 'Host is down' in p2.stderr.decode():
                print('Host is down')
                time.sleep(0.3)
                reconnect()
        else:
            reconnected = True
            
    get_rssi()

I have tried threading and multiprocessing, but they do not help since command 1 never "joins" in python threading lingo.我尝试过线程和多处理,但它们没有帮助,因为命令 1 从不“加入” python 线程术语。 I am aware that I probably need to run command 1 asynchronously , but I am struggling to implement it properly in python even while referring to the asyncio docs.我知道我可能需要异步运行命令 1,但即使在参考 asyncio 文档时,我也很难在 python 中正确实现它。 Any help is much appreciated!任何帮助深表感谢!

It looks like you are trying to make an RFCOMM connection.看起来您正在尝试建立 RFCOMM 连接。

Both rfcomm and hcitool have been deprecated by the BlueZ project back in 2017 so I wouldn't recommend starting a project using these. rfcommhcitool早在 2017 年就被 BlueZ 项目弃用了,所以我不建议使用它们来启动项目。

BlueZ has APIs that are designed to be accessed from languages like Python and these are documented at: https://git.kernel.org/pub/scm/bluetooth/bluez.git/tree/doc and the official examples are at: https://git.kernel.org/pub/scm/bluetooth/bluez.git/tree/test BlueZ has APIs that are designed to be accessed from languages like Python and these are documented at: https://git.kernel.org/pub/scm/bluetooth/bluez.git/tree/doc and the official examples are at: https ://git.kernel.org/pub/scm/bluetooth/bluez.git/tree/test

However, RFCOMM (or Serial Port Profile) connections can be done with the socket library in the standard Python releases.但是,可以使用标准 Python 版本中的套接字库来完成 RFCOMM(或串行端口配置文件)连接。 There are examples at https://stackoverflow.com/a/63382835/7721752 https://stackoverflow.com/a/63382835/7721752有示例

There are also examples in the above answer of using the Bluedot library to do the same.上面的答案中也有使用Bluedot库执行相同操作的示例。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM