0

I have a problem. I need to kill the batch file using the python script residing within the same batch file. The batch file has abc.py script as the first one along with other scripts. So I need to kill the batch file so that others don't get executed. Here is what I have tried:

for proc in psutil.process_iter():
     if proc.name() == "python.exe" and len(proc.cmdline()) > 1 and 
         "abc.py" in proc.cmdline()[1]:
    proc.terminate()

But this only kills the python script, not the batch file. Tried killing the pid with the same effect.

os.system("taskkill /F /PID " + str(os.getpid()))

Edit 1 The script checks for existence of another running script and then needs to terminate itself.

Mallik Kumar
  • 520
  • 4
  • 20
  • Not a solution, but an alternative. See https://stackoverflow.com/questions/11907163/how-can-i-stop-a-programs-execution-with-python . – user202729 Aug 21 '18 at 06:22
  • Try using https://stackoverflow.com/questions/12978013/need-to-find-which-program-called-the-python-script or https://stackoverflow.com/questions/1728330/how-to-get-processs-grandparent-id/4229596 . – user202729 Aug 21 '18 at 06:28
  • sys.exit() terminates abc.py but not the others. I need to kill the batch file. – Mallik Kumar Aug 21 '18 at 06:29
  • I need to kill the batch file programatically. So cannot use process explorer. – Mallik Kumar Aug 21 '18 at 06:33

2 Answers2

3

If you're just looking to kill whoever your parent is, that's easy: just use os.getppid() instead of os.getpid():

os.system("taskkill /F /PID " + str(os.getppid()))

Of course it's better to use subprocess instead of os.system for all the usual reasons, like getting a useful error if it fails:

subprocess.run(['taskkill', '/F', '/PID', str(os.getppid())])

Or, even better, don't use taskkill, just kill it directly. This also gives you the option of using a nicer Ctrl-C or Ctrl-Break kill instead of a hard kill, if preferred:

os.kill(os.getppid(), signal.CTRL_BREAK_EVENT)

If you're using Python 2.7, getppid doesn't work on Windows; that was only added in 3.2. (And I think the same is true for os.kill, and definitely for signal.CTRL_BREAK_EVENT.)

Since you're already apparently amenable to using psutil, you can use that.

There's no need to search through every process on the system to find yourself, just construct a default Process. And you can go from any process to its parent with parent. And then you can use the kill or terminate

proc = psutil.Process().parent()
proc.kill()

All of the above, except using CTRL_C_EVENT or CTRL_BREAK_EVENT instead of a standard signal), have the nice advantage of being cross-platform—you can run the same script on Linux or macOS or whatever and it'll kill the shell script that ran it.

abarnert
  • 313,628
  • 35
  • 508
  • 596
  • Thanks for the wonderful explanation. I wanted a programmatic solution. It works!! – Mallik Kumar Aug 21 '18 at 07:03
  • @MallikKumar One thing: this will kill _whoever_ its parent is. If, say, you accidentally run this program from your IDE, it'll kill your IDE. Is that a problem? – abarnert Aug 21 '18 at 07:07
1

Your batch file will need to check whether the last command succeeded and exit if it didn't.

See How do I make a batch file terminate upon encountering an error?

AKX
  • 93,995
  • 11
  • 81
  • 98