Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Can we add an option to not start a geckodriver listener? #607

Open
halfer opened this issue Oct 3, 2023 · 0 comments
Open

Can we add an option to not start a geckodriver listener? #607

halfer opened this issue Oct 3, 2023 · 0 comments

Comments

@halfer
Copy link
Contributor

halfer commented Oct 3, 2023

I have a change suggestion for Panther that I want to check with you first. I might be able to find the time to raise a PR here, but I want to see if the project is alive, committers are able to review the work, that the change is inline with best practices, etc.

I have a Dockerised app and I want to browser-test it. I decided against putting test systems in the same container, so found an image for Firefox+GeckoDriver (instrumentisto/geckodriver) and connect the two via a Docker Compose network. This container starts a geckodriver listener already, so I want Panther not to do this.

Unfortunately the FirefoxManager does not support this. Here is the relevant code:

    public function start(): WebDriver
    {
        $url = $this->options['scheme'].'://'.$this->options['host'].':'.$this->options['port'];
        if (!$this->process->isRunning()) {
            $this->checkPortAvailable($this->options['host'], $this->options['port']);
            $this->process->start();
            $this->waitUntilReady($this->process, $url.$this->options['path'], 'firefox');
        }

        $firefoxOptions = [];
        if (isset($_SERVER['PANTHER_FIREFOX_BINARY'])) {
            $firefoxOptions['binary'] = $_SERVER['PANTHER_FIREFOX_BINARY'];
        }
        if ($this->arguments) {
            $firefoxOptions['args'] = $this->arguments;
        }

        $capabilities = DesiredCapabilities::firefox();
        $capabilities->setCapability('moz:firefoxOptions', $firefoxOptions);

        foreach ($this->options['capabilities'] as $capability => $value) {
            $capabilities->setCapability($capability, $value);
        }

        return RemoteWebDriver::create($url, $capabilities, $this->options['connection_timeout_in_ms'] ?? null, $this->options['request_timeout_in_ms'] ?? null);
    }

I have passed a fake geckodriver shell to the ctor, and set up a host/port on a geckodriver container, but $this->checkPortAvailable() gets in the way. It requires the port to not be listening, so the listener process can be started, and then the port is checked until it is ready. Since the port is already listening, an error is thrown:

RuntimeException: The port 4444 is already in use.

It looks like this whole block could do with being skipped:

if (!$this->process->isRunning()) {
    $this->checkPortAvailable($this->options['host'], $this->options['port']);
    $this->process->start();
    $this->waitUntilReady($this->process, $url.$this->options['path'], 'firefox');
}

If I could call start() on this object then I assume that this would be skipped, but the Process instantiation is buried in a ctor, so I can't get to it.

I also can't extend the class because it is marked as final.

I have fixed this in the short term by copying FirefoxManager and making some edits to my copy, but I wonder if there is a more elegant solution. Perhaps an option can be passed in to skip the process checks? (Whatever changes are done here would have to be done for ChromeManager too).

I appreciate I could switch to Selenium, but I'd be unpicking a fair bit of work, and the existence of a separate geckodriver container suggests to me that some folks are using already-started FF listeners in their test stack.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant