python执行cmd命令 python创建子进程
项目需求描述:
1.第一阶段:首先有一个本地机器人项目有个Bot进程负责接收服务端的任务,并执行
2.第二阶段:服务端想要控制Bot的启动停止,并且监控状态,机器人项目就加了个Bot_Runner主进程产生Bot子进程,Bot_Runner主进程监听服务端的卡夫卡服务器接受任务操作Bot子进程,从而实现服务端对Bot的控制
2)python使用卡夫卡
3.第三阶段:Bot_Runner主进程和Bot子进程的代码更新后,需要登录每台云服务器去升级代码安装一堆依赖,太麻烦,就做了一个git_helper项目,通过卡夫卡接收服务端clone/pull命令,对机器人项目进行远程更新
1)python操作git
2)python杀死无关的python进程
3) python删除文件夹
4.第四阶段: git_helper项目虽然可以更新机器人代码,但是这个项目还是要手动clone安装依赖什么的,这个活也挺麻烦,就想把git_helper项目的 clone+依赖安装+启动 做成windows服务,开机自启,搞来搞去各种出错就放弃做成服务,做成了个exe,双击就好了
这个流程下来会频繁执行cmd命令,就总结一下python执行cmd命令的方式:
一、python使用subprocess执行cmd命令创建进程
特点:
1.subprocess.Popen创建的子进程随主进程结束而终止(好像是,记不太清楚了,懒得试,哈哈哈)
2.可以通过popen获得子进程运行状态,并且控制子进程
详见:subprocess创建子进程,subprocess执行py脚本文件,subprocess使用pipenv管理的虚拟环境执行子进程
二、python使用os.syetem执行cmd命令创建进程
特点:
system 函数可以将字符串转化成命令在服务器上运行
其原理是每一条 system 函数执行时,其会创建一个子进程在系统上执行命令行,子进程的执行结果无法影响主进程。
system创建的子进程运行不依赖于主进程,主进程结束子进程也能正常运行
根据切换盘符方式不同,执行多条语句有不同的语法,如下:
2.1 os.seytem
(1)os.seytem直接cd切换
# 第一种 os.system执行cd命令切换子进程盘符,执行其他文件 # 当前目录D:\gittest,要再D:/gittest/代码/weebot_wxbot目录中安装依赖,并启动666.py os.system('cd ..') # 这个只能改变os创建的子进程的目录,不能改变当前主进程工作目录 print(os.getcwd()) # 还是当前目录D:\gittest # 所以用os.system执行cd命令切换盘符的,只能一气呵成用 && 或者 ; 来拼接执行命令,不能分步执行 os.system('cd ../代码/weebot_wxbot && pipenv install && start pipenv run python 666.py')# 在 cmd 命令前加入 start 可不阻塞当前程序执行 # os.system('cd ../代码/weebot_wxbot ; pipenv install ; start pipenv run python 666.py')
(2)os.seytem切换到C盘,有些操作系统不能直接,切换需要特殊处理
后来发现可能是反斜杠造成的,可以使用:
C:\/WEEBOT/wibot_bot/bot.exe
# Windows中文家庭版 2010 :不能直接cd到C盘++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ res = os.system(r"cd D:\ && dir") # 这样是ok的,dir显示是D盘 # res = os.system(r"cd C:\BR_autoupdate\AutoUpdate && dir") # dir显示还是当前盘符,切换失败 res = os.system(r"C: && cd BR_autoupdate\AutoUpdate && dir") # 这样就对了 print(res) # 0/1 0表示执行正常,不代表执行成功 # res = os.system(r"C: && cd BR_autoupdate\AutoUpdate && start AutoUpdate.exe http://127.0.0.1"") #执行exe成功 # windows server 2019 英文版: 服务器版本可以直接cd到C盘+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ # res = os.system(r"cd C:\BR_autoupdate\AutoUpdate && start AutoUpdate.exe http://127.0.0.1"") # windows server 2019 # 如果可以用相对路径的话两个系统都可以用++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ res = os.system(r"start ..\AutoUpdate\AutoUpdate.exe http://127.0.0.1"") print(res)
2.2 os.chdir切换盘符
# 第二种os.chdir切换主进程盘符,执行其他文件 base_path = os.getcwd() # 获取当前主进程基础目录 os.chdir('../代码/weebot_wxbot_bieyang') # 这个可以改变当前主进程工作目录到指定的路径 print(os.getcwd()) # D:\代码\weebot_wxbot,主进程目录已经变化 os.system('pipenv install') # 默认阻塞当前程序执行依赖安装 aa = os.system('start pipenv run python 666.py') # 在 cmd 命令前加入 start 可不阻塞当前程序执行 # os.system('pipenv install && start pipenv run python 666.py') # 可以分开执行也可以这样 os.chdir(base_path) # 更新并启动后从子进程的工作目录再次切回当前主进程基础目录
2.3 python杀死进程
# taskkill /f /t /im Wechat.exe taskkill更多参数可以百度 # /f 指定将强制终止的进程 /t终止指定的进程与该进程启动的任何子进程 /im 表示指定的进程名称,例如“explor.exe" # 第一种 os的方法 os.system(f"taskkill /t /f /pid {self.wx_pid}") os.system(f"taskkill /t /f /im Wechat.exe") # 第二种 使用subprocess的方法 subprocess.run(['taskkill', '/f', '/t', '/im', 'WeChat.exe'])
2.4 python启动exe os.system打开程序路径有空格 os.system切换路径到C盘
1)常规来说 使用os.system(r'../wechat/Wechat.exe'),是可以的,但是当路径中有空格时就会出错,如下:
import os cmd = "start D:\Program Files\Tencent\QQ\Bin\QQScLauncher.exe" os.system(cmd)
可以这样执行:
# 第一种 subprocess.Popen(r'C:\Program Files (x86)\Tencent\WeChat\WeChat.exe') # 不阻塞 # 第二种 os.chdir(r'C:\Program Files (x86)\Tencent\WeChat') # 注意:会改变运行主目录的 print(os.getcwd()) # 当前运行目录改变为:C:\Program Files (x86)\Tencent\WeChat os.system('start WeChat.exe') # 加start不阻塞运行