Ответ 1
Try:
os.kill(pid, 0)
Должен преуспеть (и ничего не делать), если процесс существует, или выбросить исключение (которое вы можете поймать), если процесс не существует.
Я пытаюсь найти, работает ли процесс на основе идентификатора процесса. Код выглядит следующим образом, основываясь на одном из сообщений на форуме. Я не могу рассматривать имя процесса, поскольку существует несколько процессов, работающих под тем же именем.
def findProcess( processId ):
ps= subprocess.Popen("ps -ef | grep "+processId, shell=True, stdout=subprocess.PIPE)
output = ps.stdout.read()
ps.stdout.close()
ps.wait()
return output
def isProcessRunning( processId):
output = findProcess( processId )
if re.search(processId, output) is None:
return true
else:
return False
Выход:
1111 72312 72311 0 0:00.00 ttys000 0:00.00 /bin/sh -c ps -ef | grep 71676
1111 72314 72312 0 0:00.00 ttys000 0:00.00 grep 71676
Он всегда возвращает true, так как он может найти идентификатор процесса в выходной строке.
Любые предложения? Спасибо за любую помощь.
Try:
os.kill(pid, 0)
Должен преуспеть (и ничего не делать), если процесс существует, или выбросить исключение (которое вы можете поймать), если процесс не существует.
Самый простой ответ на мой взгляд (albiet, возможно, не идеальный), - это изменить ваш
ps -ef | grep <pid>
To:
ps -ef | grep <pid> | grep -v grep
Это будет игнорировать список процессов для поиска grep, содержащего PID процесса, который вы пытаетесь найти.
Кажется, user9876 ответ гораздо более "pythonic".
Вы можете проверить, существует ли папка /proc/ [process_id].
>>> import os.path
>>> os.path.exists("/proc/0")
False
>>> os.path.exists("/proc/12")
True
Смотрите это так: Как вы проверяете Linux с Python, если процесс все еще запущен?
Это немного kludge, но на * nix вы можете использовать os.getpgid(pid) или os.kill(pid, sig), чтобы проверить наличие идентификатора процесса.
import os
def is_process_running(process_id):
try:
os.kill(process_id, 0)
return True
except OSError:
return False
EDIT: Обратите внимание, что os.kill
работает в Windows (как и на Python 2.7), а os.getpgid
- нет. Но версия Windows вызывает TerminateProcess(), которая "безоговорочно заставит процесс выйти", поэтому я предсказываю, что он не будет безопасным вернуть требуемую информацию, не убивая процесс, если он существует.
Если вы используете Windows, сообщите нам об этом, потому что ни одно из этих решений не приемлемо в этом сценарии.
Я знаю, что это старо, но я использовал это и, похоже, работает; вы можете быстро адаптироваться к преобразованию из имени процесса в идентификатор процесса:
try:
if len( os.popen( "ps -aef | grep -i 'myprocess' | grep -v 'grep' | awk '{ print $3 }'" ).read().strip().split( '\n' ) ) > 1:
raise SystemExit(0)
except Exception, e:
raise e
Если вы не против использования внешнего модуля, я бы предложил psutil. Это кросс-платформенный и более простой в использовании, чем нерестовая подоболочка только для поиска текущего процесса.
Если этот процесс принадлежит одному и тому же пользователю в процессе проверки, вы можете просто попробовать kill
его. Если вы используете сигнал 0, kill не отправит ничего, но все же позволит вам узнать, доступен ли процесс.
От kill(2)
:
Если sig равно 0, тогда никакой сигнал не отправляется, но проверка ошибок по-прежнему выполнено; это можно использовать для проверки наличия идентификатора процесса или идентификатор группы процессов.
Это должно соответствующим образом распространяться на методы python.
В Windows другой вариант - использовать tasklist.exe:
Синтаксис: tasklist.exe/NH/FI "PID eq processID"
def IsProcessRunning( processId ):
ps= subprocess.Popen(r'tasklist.exe /NH /FI "PID eq %d"' % (processId), shell=True, stdout=subprocess.PIPE)
output = ps.stdout.read()
ps.stdout.close()
ps.wait()
if processId in output:
return True
return False
В Windows вы можете использовать WMI.
from win32com.client import GetObject
GetObject('winmgmts:').ExecQuery("Select * from Win32_Process where ProcessId = " + str(pid)).count
Вы также можете использовать другие фильтры. Например, я, скорее всего, просто хочу сказать, работает ли процесс по имени и предпринимает действия. Например, если DbgView не запущен, запустите его.
if not GetObject('winmgmts:').ExecQuery("Select * from Win32_Process where Name = 'dbgview.exe'").count:
subprocess.Popen(r"C:\U\dbgview.exe", shell=False)
Вы также можете перебирать и делать другие интересные вещи. Полный список полей здесь.
Недавно мне пришлось перечислить запущенные процессы и сделать это:
def check_process(process):
import re
import subprocess
returnprocess = False
s = subprocess.Popen(["ps", "ax"],stdout=subprocess.PIPE)
for x in s.stdout:
if re.search(process, x):
returnprocess = True
if returnprocess == False:
print 'no process executing'
if returnprocess == True:
print 'process executing'
Вы должны найти его дважды..
Вот так:
ps -ef | grep 71676 | sed 's/71676//' | grep 71676
Если это возвращает True
, тогда это действительно работает!!