Friday, April 5, 2019

Resolve: Killing Zombie Processes created by Selenium

Problem

Here's my problem.

I'm working with Selenium 2.53 (an old version, I know) and Firefox 52.8. The Gecko (driver) version is whichever works with FF 52.8. Anyhow, I create a my test script, run the test script, and see the command invokes the call to run the test. However, my browser does not open. My terminal just sits at this command running the test. Eventually, my command ends and the test failed to run. I'm running this in a secure environment on a separate machine and can't copy/paste a screenshot here.

However, here's what the error looks like - if you're lucky enough to get one.

Results :
Tests in error:
my.test.script.TestPageAUT.enterMaxChars...
    Run 1:  .... >> WebDriver Unable to bind to locking port 70...


Solution

Here's my solution.

I knew from experience that a system process opened by the driver via Java is hanging. Since I'm running this on Linux, I had to make sure I used the right Linux commands to find the processes that are running (active). Throughout my research, I learned that Linux actually has processes that are zombies (not quite dead, but not live either) which are marked with "<defunct>" next to the process.

Once I found out the process ID (PID) of the zombie process, then I just needed to kill the parent process of the zombie (because I can't kill the zombie - which I think is weird). It would be nice to just kill the zombie and automatically the parents of the zombie also die. Anyhow, in this particular case I had to kill the most super parent of the zombie in order to completely make sure the zombie process for my selenium script is dead. Selenium runs via Java by triggering the gecko driver which controls a FF process. So, to kill the zombie FF process, need to kill the Java process controlling the zombie FF process which might have a grandparent Java process.

Double check the process is dead by showing the list of active processes and seeing that there is no zombie process in the list.


Steps/Commands

Here's how I did it.

Important Note: A "kill" command has no effect on a zombie process.

List all zombie processes (ID).
$ ps aux | grep -w Z

Find the parent PID.
$ ps -o ppid <defunct_PID>         

Kill the parent
$ kill -9 <parent_PID_of_defunct_PID>


Other Useful Commands

List all running processes.
$ ps

List the running processes with Firefox.
$ ps -A | grep firefox

For more details, list with these parameters.
$ ps aux | grep firefox

Find the parent process ID.
$ ps -o ppid= -p <defunct_PID>

You can try this (kill all firefox PIDs), but this didn't work for me.
$ kill $(pgrep firefox)


Reference


1 comment: