'Click succeeded but Load Failed. Status: 'fail'' - Post click Ajax event #202

Closed
dutchb opened this Issue Mar 26, 2013 · 56 comments

Projects

None yet
@dutchb
dutchb commented Mar 26, 2013
public void clearCompanyTree() {
        if (isElementPresent(clearCompanyTreeLink)) {
            wait.until(elementToBeClickable(clearCompanyTreeLink, "Company tree clear link"));
            clearCompanyTreeLink.click(); // <-- this line is what fails
            wait.until(a4jRequestsComplete());

The code doesn't show you a lot, I know. To see this happen make a webpage with a button. Have the button fire an Ajax event that will load a subsequent page on a random timer (say 1 to more than the phantomjs page load timeout threshold). Run a java/selenium script that clicks the button.

The clearCompanyTreeLink is a link which, on click, fires an Ajax event that makes some back end calls to clear the tree and reloads the page. On most tests we run which call this block of code it will fail with ghostdriver/phantom js with:

org.jbehave.core.failures.UUIDExceptionWrapper: When I enter customer data/john_doe.table details on the registration page.
    at org.jbehave.core.steps.StepCreator$ParameterisedStep.perform(StepCreator.java:564)
    at org.jbehave.core.embedder.StoryRunner$FineSoFar.run(StoryRunner.java:499)
    at org.jbehave.core.embedder.StoryRunner.runStepsWhileKeepingState(StoryRunner.java:479)
    at org.jbehave.core.embedder.StoryRunner.runScenarioSteps(StoryRunner.java:443)
    at org.jbehave.core.embedder.StoryRunner.runScenariosParametrisedByExamples(StoryRunner.java:412)
    at org.jbehave.core.embedder.StoryRunner.runCancellable(StoryRunner.java:301)
    at org.jbehave.core.embedder.StoryRunner.run(StoryRunner.java:219)
    at org.jbehave.core.embedder.StoryRunner.run(StoryRunner.java:180)
    at org.jbehave.core.embedder.StoryManager$EnqueuedStory.call(StoryManager.java:229)
    at org.jbehave.core.embedder.StoryManager$EnqueuedStory.call(StoryManager.java:201)
    at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:303)
    at java.util.concurrent.FutureTask.run(FutureTask.java:138)
    at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:895)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:918)
    at java.lang.Thread.run(Thread.java:680)
Caused by: org.openqa.selenium.WebDriverException: Error Message => 'Click succeeded but Load Failed. Status: 'fail''
 caused by Request => {"headers":{"Accept":"application/json, image/png","Connection":"Keep-Alive","Content-Length":"27","Content-Type":"application/json; charset=utf-8","Host":"localhost:14222"},"httpVersion":"1.1","method":"POST","post":"{\"id\":\":wdc:1363995747367\"}","url":"/click","urlParsed":{"anchor":"","query":"","file":"click","directory":"/","path":"/click","relative":"/click","port":"","host":"","password":"","user":"","userInfo":"","authority":"","protocol":"","source":"/click","queryKey":{},"chunks":["click"]},"urlOriginal":"/session/e6ae3b50-9349-11e2-a73d-55fb5432ff8b/element/%3Awdc%3A1363995747367/click"}
Command duration or timeout: 173 milliseconds
Build info: version: '2.30.0', revision: 'dc1ef9ceb805a672f56dc49198f9ffbd4ca345c7', time: '2013-02-19 09:14:38'
System info: os.name: 'Mac OS X', os.arch: 'x86_64', os.version: '10.8.2', java.version: '1.6.0_43'
Session ID: e6ae3b50-9349-11e2-a73d-55fb5432ff8b
Driver info: org.openqa.selenium.phantomjs.PhantomJSDriver
Capabilities [{platform=MAC, acceptSslCerts=false, javascriptEnabled=true, browserName=phantomjs, rotatable=false, locationContextEnabled=false, version=1.9.0, databaseEnabled=false, cssSelectorsEnabled=true, handlesAlerts=false, browserConnectionEnabled=false, webStorageEnabled=false, proxy={proxyType=direct}, nativeEvents=true, applicationCacheEnabled=false, takesScreenshot=true}]
    at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:39)
    at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:27)
    at java.lang.reflect.Constructor.newInstance(Constructor.java:513)
    at org.openqa.selenium.remote.ErrorHandler.createThrowable(ErrorHandler.java:187)
    at org.openqa.selenium.remote.ErrorHandler.throwIfResponseFailed(ErrorHandler.java:145)
    at org.openqa.selenium.remote.RemoteWebDriver.execute(RemoteWebDriver.java:533)
    at org.openqa.selenium.remote.RemoteWebElement.execute(RemoteWebElement.java:246)
    at org.openqa.selenium.remote.RemoteWebElement.click(RemoteWebElement.java:79)
    at org.openqa.selenium.support.ui.Select.setSelected(Select.java:318)
    at org.openqa.selenium.support.ui.Select.selectByVisibleText(Select.java:116)
    at com.dandb.ecomm.test.pages.telesales.RegistrationPage.enterRegistrationInformation(RegistrationPage.java:127)
    at com.dandb.ecomm.test.steps.telesales.PurchaseSteps.enterCustomerDetailsToRegistrationPage(PurchaseSteps.java:70)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at org.jbehave.core.steps.StepCreator$ParameterisedStep.perform(StepCreator.java:550)
    ... 14 more

The captured screenshots always show the Ajax spinner is present on the page in a pre-reload state. Manually signing into the same page immediately after failure shows the action was successful.

The same tests executed with Firefox succeed. Digging into prior reports of the same failure message show this comes from the phantomjs onPageLoad event. Digging into the ghostdriver code I've reached:

    _postClickCommand = function(req, res) 

Specifically:

    else {
                        _errors.handleFailedCommandEH(
                            _errors.FAILED_CMD_STATUS.UNKNOWN_ERROR,
                            "Click succeeded but Load Failed. Status: '" + status + "'",
                            req,
                            res,
                            _session,
                            "WebElementReqHand");
                    }

This combined with what I've read in other threads suggests that phantomjs doesn't use any kind of Ajax listener in it's handling of click events. It acts on the click, looks for a page load, doesn't see it fast enough, and pukes up an error. There is some code in the same file for handling some async but it doesn't seem to be tied into click events by default.

The options I'm considering are changing the else block locally to ignore the phantomjs return (which isn't desirable but would be functional), change the test to fire the event without the click event (which needlessly complicates validating the functionality of the button in question, not to mention completely hackish), get our developers to put a special hook in for ghostdriver (idiotic and not going to happen), or work with you guys to get an Ajax listener in the correct place.

I'm a bit unclear as to the need for the page load validation at the phantomjs level, but if you feel there's technical merit to having it there I'd love to work with you on getting to handle more of the possible click event scenarios.

  • Java/Selenium/jbehave
  • Phantomjs 1.8 built
  • mvn installed with ghostdriver 1.0.3-dev
@detro
Owner
detro commented Mar 26, 2013

U can't be using GD 1.0.3 with Phantom 1.8, as there is a strong
requirement for 1.9 latest features.

Please try with PhabtomJS 1.9.0 and let me know.
On 26 Mar 2013 19:30, "Dutch Buckholz" notifications@github.com wrote:

public void clearCompanyTree() {
if (isElementPresent(clearCompanyTreeLink)) {
wait.until(elementToBeClickable(clearCompanyTreeLink, "Company tree clear
link"));
clearCompanyTreeLink.click(); // <-- this line is what fails
wait.until(a4jRequestsComplete());

The code doesn't show you a lot, I know. To see this happen make a webpage
with a button. Have the button fire an Ajax event that will load a
subsequent page on a random timer (say 1 to more than the phantomjs page
load timeout threshold). Run a java/selenium script that clicks the button.

The clearCompanyTreeLink is a link which, on click, fires an Ajax event
that makes some back end calls to clear the tree and reloads the page. On
most tests we run which call this block of code it will fail with
ghostdriver/phantom js with:

org.jbehave.core.failures.UUIDExceptionWrapper: When I enter customer
data/john_doe.table details on the registration page.
at
org.jbehave.core.steps.StepCreator$ParameterisedStep.perform(StepCreator.java:564)
at
org.jbehave.core.embedder.StoryRunner$FineSoFar.run(StoryRunner.java:499)
at
org.jbehave.core.embedder.StoryRunner.runStepsWhileKeepingState(StoryRunner.java:479)
at
org.jbehave.core.embedder.StoryRunner.runScenarioSteps(StoryRunner.java:443)
at
org.jbehave.core.embedder.StoryRunner.runScenariosParametrisedByExamples(StoryRunner.java:412)
at
org.jbehave.core.embedder.StoryRunner.runCancellable(StoryRunner.java:301)
at org.jbehave.core.embedder.StoryRunner.run(StoryRunner.java:219)
at org.jbehave.core.embedder.StoryRunner.run(StoryRunner.java:180)
at
org.jbehave.core.embedder.StoryManager$EnqueuedStory.call(StoryManager.java:229)
at
org.jbehave.core.embedder.StoryManager$EnqueuedStory.call(StoryManager.java:201)
at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:303)
at java.util.concurrent.FutureTask.run(FutureTask.java:138)
at
java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:895)
at
java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:918)
at java.lang.Thread.run(Thread.java:680)
Caused by: org.openqa.selenium.WebDriverException: Error Message => 'Click
succeeded but Load Failed. Status: 'fail''
caused by Request => {"headers":{"Accept":"application/json,
image/png","Connection":"Keep-Alive","Content-Length":"27","Content-Type":"application/json;
charset=utf-8","Host":"localhost:14222"},"httpVersion":"1.1","method":"POST","post":"{"id":":wdc:1363995747367"}","url":"/click","urlParsed":{"anchor":"","query":"","file":"click","directory":"/","path":"/click","relative":"/click","port":"","host":"","password":"","user":"","userInfo":"","authority":"","protocol":"","source":"/click","queryKey":{},"chunks":["click"]},"urlOriginal":"/session/e6ae3b50-9349-11e2-a73d-55fb5432ff8b/element/%3Awdc%3A1363995747367/click"}
Command duration or timeout: 173 milliseconds
Build info: version: '2.30.0', revision:
'dc1ef9ceb805a672f56dc49198f9ffbd4ca345c7', time: '2013-02-19 09:14:38'
System info: os.name: 'Mac OS X', os.arch: 'x86_64', os.version:
'10.8.2', java.version: '1.6.0_43'
Session ID: e6ae3b50-9349-11e2-a73d-55fb5432ff8b
Driver info: org.openqa.selenium.phantomjs.PhantomJSDriver
Capabilities [{platform=MAC, acceptSslCerts=false, javascriptEnabled=true,
browserName=phantomjs, rotatable=false, locationContextEnabled=false,
version=1.9.0, databaseEnabled=false, cssSelectorsEnabled=true,
handlesAlerts=false, browserConnectionEnabled=false,
webStorageEnabled=false, proxy={proxyType=direct}, nativeEvents=true,
applicationCacheEnabled=false, takesScreenshot=true}]
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at
sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:39)
at
sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:27)
at java.lang.reflect.Constructor.newInstance(Constructor.java:513)
at
org.openqa.selenium.remote.ErrorHandler.createThrowable(ErrorHandler.java:187)
at
org.openqa.selenium.remote.ErrorHandler.throwIfResponseFailed(ErrorHandler.java:145)
at
org.openqa.selenium.remote.RemoteWebDriver.execute(RemoteWebDriver.java:533)
at
org.openqa.selenium.remote.RemoteWebElement.execute(RemoteWebElement.java:246)
at
org.openqa.selenium.remote.RemoteWebElement.click(RemoteWebElement.java:79)
at org.openqa.selenium.support.ui.Select.setSelected(Select.java:318)
at
org.openqa.selenium.support.ui.Select.selectByVisibleText(Select.java:116)
at
com.dandb.ecomm.test.pages.telesales.RegistrationPage.enterRegistrationInformation(RegistrationPage.java:127)
at
com.dandb.ecomm.test.steps.telesales.PurchaseSteps.enterCustomerDetailsToRegistrationPage(PurchaseSteps.java:70)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at
sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at
sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at
org.jbehave.core.steps.StepCreator$ParameterisedStep.perform(StepCreator.java:550)
... 14 more

The captured screenshots always show the Ajax spinner is present on the
page in a pre-reload state. Manually signing into the same page immediately
after failure shows the action was successful.

The same tests executed with Firefox succeed. Digging into prior reports
of the same failure message show this comes from the phantomjs onPageLoad
event. Digging into the ghostdriver code I've reached:
_postClickCommand = function(req, res)

Specifically:
else {
_errors.handleFailedCommandEH(
_errors.FAILED_CMD_STATUS.UNKNOWN_ERROR,
"Click succeeded but Load Failed. Status: '" + status + "'",
req,
res,
_session,
"WebElementReqHand");
}

This combined with what I've read in other threads suggests that phantomjs
doesn't use any kind of Ajax listener in it's handling of click events. It
acts on the click, looks for a page load, doesn't see it fast enough, and
pukes up an error. There is some code in the same file for handling some
async but it doesn't seem to be tied into click events by default.

The options I'm considering are changing the else block locally to ignore
the phantomjs return (which isn't desirable but would be functional),
change the test to fire the event without the click event (which needlessly
complicates validating the functionality of the button in question, not to
mention completely hackish), get our developers to put a special hook in
for ghostdriver (idiotic and not going to happen), or work with you guys to
get an Ajax listener in the correct place.

I'm a bit unclear as to the need for the page load validation at the
phantomjs level, but if you feel there's technical merit to having it there
I'd love to work with you on getting to handle more of the possible click
event scenarios.

  • Java/Selenium/jbehave w/ phantomjs 1.8 built & mvn installed with
    ghostdriver 1.0.3-dev


Reply to this email directly or view it on GitHubhttps://github.com/detro/ghostdriver/issues/202
.

@dutchb
dutchb commented Mar 28, 2013

Sorry for the delay, got pulled into meetings and other tasks. Put in PhantomJS 1.9.0, updated the maven dependency to 1.0.3 phantomjsdriver. No difference in behavior.

@toxik
toxik commented Mar 29, 2013

I also have this issue, it works with the chromedriver though..

It's just a regular click with a page reload.

@FPurchess

After 2h of recompiling the latest phantomjs / ghostdriver, I can say I get the same exception :/

@carolmirakove

Same here. I am running selenium-webdriver tests on two applications, and using ghostdriver the tests fail after submitting log in credentials. Usernames and passwords are passed, sign in is clicked, but then this exception is returned.

@FPurchess

We wrote a proxy now that simply ignores this exception, which is - in fact - not really intentioned, but we're at least able to deliver continously again.

@luksch
luksch commented May 8, 2013

is there any development on this issue? I get the same error on a simple click to an element that triggers a page reload. all works fine in ff and chrome, but phantomjs throws this error.

@tehprofessor

I'm getting this as well; web driver works fine with Firefox but fails with ghost (phantomjs). I'm definitely using version 1.9.0. On OS X 10.8.3 if that matters.

@aaronromeo

I too have a problem which has the same symptoms.

@ghost
ghost commented Jun 5, 2013

Same for me with v1.9.0.

@tehprofessor

Any updates on this? I've had to stop using phantom as a result of this.

I'd be happy to lend a hand fixing it, or tracking it down, but I'm not even sure where to start looking.

@jfroehlich

Me too. As a quick fix I'm catching the exception and log a warning (I'm not very proud about this). Like @carolmirakove it's when the login in form is sumitted. In our case there is at least one redirect. After a successful login there are often two.

@stefanvanwouw

I am using v1.9.0 as well (The python bindings), and occasionally this error pops up in a similar context as described above. This error prevents us from using PhantomJS with GhostDriver, although we really would like to (According to our benchmarks it is significantly faster and uses less memory and CPU compared to he FirefoxDriver we are currently using).

Does anyone have an update on this issue? I am willing to contribute to a fix if someone can point out the part of the code responsible.

@dutchb
dutchb commented Jun 10, 2013

Hi Stefan,
I haven't had time to find the exact location yet but either GhostDriver or PhantomdriverJS is doing a load verification on the click event. detro hasn't commented on that but it really isn't the place of either of those to do the verification, especially with the variety of possible actions a click can trigger. The code that would need to be forked and submitted would be to rip out either the page load verification or the call to it by the click handling. There are some good pointers to it in the stack I originally listed.

If you do fork let me know, otherwise I'll likely do something with this in my own time about 3 - 5 weeks from now.
Cheers,
Dutch

@stefanvanwouw

Trying to fix bugs in code I am not familiar with is a very time consuming activity, and therefore I prefer not to. What I can do, however, is help verifying if a possible fix works (many test cases for that are present in the project I am working on). I will try to contact detro to see if he has any heads up on this issue. This issue is pretty critical.

@detro
Owner
detro commented Jun 12, 2013
Trying to fix bugs in code I am not familiar with is a very time consuming activity, and therefore I prefer not to.

I have to say that reading something like that is a bit "demotivating".

Any open source project, when first approached, it's made of code you are not familiar with.
This doesn't mean that me spending time on it is better than you spending time on it :)

Anyway, I'll look into this.
Assuming within all the previous comments there is a reproducible example.

@detro
Owner
detro commented Jun 12, 2013

I have "an idea" of what the issue scenario is but if any of you would be so kind to share CODE to reproduce it I'd be very happy.

Again, as said many times, it's not enough to just complain.

@dutchb
dutchb commented Jun 12, 2013

Ivan,

The scenario is a click event that triggers an Ajax script running longer than the page load timeout. I will have personal time to spend on this in 3 - 5 weeks and will be happy to do so if you haven't addressed it yet. You're doing great work or we wouldn't be here to complain about that one thing that's bugging us.

Sent from my Android phone using TouchDown (www.nitrodesk.com)

-----Original Message-----
From: Ivan De Marino [notifications@github.com]
Received: Tuesday, 11 Jun 2013, 5:56PM
To: detro/ghostdriver [ghostdriver@noreply.github.com]
CC: Dutch Buckholz [dbuckholz@dandb.com]
Subject: Re: [ghostdriver] 'Click succeeded but Load Failed. Status: 'fail'' - Post click Ajax event (#202)

Trying to fix bugs in code I am not familiar with is a very time consuming activity, and therefore I prefer not to.

I have to say that reading something like that is a bit "demotivating".

Any open source project, when first approached, it's made of code you are not familiar with.
This doesn't mean that me spending time on it is better than you spending time on it :)

Anyway, I'll look into this.
Assuming within all the previous comments there is a reproducible example.


Reply to this email directly or view it on GitHubhttps://github.com/detro/ghostdriver/issues/202#issuecomment-19301773.

This e-mail and any files transmitted with it may contain privileged or confidential information. It is solely for use by the individual for whom it is intended, even if addressed incorrectly. If you received this e-mail in error, please notify the sender; do not disclose, copy, distribute, or take any action in reliance on the contents of this information; and delete it from your system. Any other use of this e-mail is prohibited. Thank you.

@stefanvanwouw

I have to say that reading something like that is a bit "demotivating".

I might have formulated a bit bluntly. I did not intend it that way, and in fact am very happy the GhostDriver project exists and I would like to contribute. My intention with putting it like that was that maybe you had experienced this issue yourself, being able to give some pointers (narrowing down the search space for people not that familiar with the code).

Like dutchb, I will try to come up with example (using the python bindings in my case) which demonstrates the problem. This might take some time, as the situation might be quite hard to reproduce (without using the proprietary code which is triggering it as well).

@detro
Owner
detro commented Jun 12, 2013

OK.
But it would be much better if you had given me CODE.
I have to come up with a test, see if it passes and also validate it's actually what you mean.

What if the test I write DOESN'T match your specific situation?

Code speaks

@detro
Owner
detro commented Jun 12, 2013

Btw, if any of who is reading this IS at the Selenium Conference right now, we should meet and chat face2face.

@detro
Owner
detro commented Jun 12, 2013

Does the following test looks good (less then 5 minutes to write...):

    @Test
    public void shouldHandleCasesWhenAsyncJavascriptInitiatesALoad() {
        server.setGetHandler(new HttpRequestCallback() {
            @Override
            public void call(HttpServletRequest req, HttpServletResponse res) throws IOException {
                res.getOutputStream().println("<script type=\"text/javascript\">\n" +
                        "    function myFunction() {\n" +
                        "        setTimeout(function() {\n" +
                        "            window.location.href = 'http://www.google.com';\n" +
                        "        }, 5000);\n" +
                        "    }\n" +
                        "    </script>\n" +
                        "    <a href=\"#\" onclick=\"myFunction()\">Click Here</a>");
            }
        });

        WebDriver d = getDriver();

        d.get(server.getBaseUrl());
        System.out.println(d.getPageSource());

        d.findElement(By.xpath("html/body/a")).click();

        System.out.println(d.getPageSource());

        assertTrue(d.getTitle().toLowerCase().contains("google"));
    }
@detro
Owner
detro commented Jun 12, 2013

BTW, the above fails on Chrome.

@detro
Owner
detro commented Jun 12, 2013

I don't think the scenario described by @dutchb it's actally causing your issue.

But default the Page Load Timeout is INFINITE (well, being GhostDriver written in Javascript, is the largest integer supported by "setTimeout" - google it for better understanding: it's really not relevant here).

Because of this, if your Ajax action begins a page load, GhostDriver WILL wait for a very long time before timing out.

BUT, if your page load starts later on (above is 5 seconds later to the click), no browser can know that such an action will eventually initiate a page load.

As I said before, I need reproducible code otherwise this is a no-issue for me.

Ah, btw, I assume you are using PhantomJS 1.9.x and/or a GhostDriver >= 1.0.3. Otherwise an update will solve your issue :)

@aaronromeo

I might be able to get a test together. It won't be for a couple days though.

@nathandace

Can you verify that when you click the element, that you do not have any javascript errors?

I had a similar issue with an application I was testing with GhostDriver. The issue that was an onclick event was attempting to load some CSS, but the CSS file was coming up as a 404 because it was missing.

The click would actually work, but GhostDriver would report the click as failing, which helped us fix the issue in our application.

@detro
Owner
detro commented Jun 12, 2013

@nathandace Not sure what are you asking me to do really...

Anyway, given the lack of examples provided I'm considering closing this issue.
Happy to reopen if anyone comes back with a reproducible and clear scenario of code.

@detro
Owner
detro commented Jun 12, 2013

WAIT - Are you guys sure that, between the Ajax HTTP requests that your click initiates, there are NO failing HTTP calls?

If that happens, GhostDriver detects the following:

  • a click happened
  • 1 or more HTTP requests have started
  • ... wait for them to finish...
  • requests finished loading but 1 or more failed
    => "click succeeded bu load failed"

Would that possibly be your scenario?

@detro
Owner
detro commented Jun 12, 2013

Added test related to this in 6f73abd.

@nathandace

@detro My comments were directed to those having this issue. The only time I've encountered this issue is if the click results in a GET error, such as an onclick trying to load a resource that is missing. In which case, I agree that GhostDriver is handling this correctly in detecting that an error occurred.

Chrome/Firefox/IE doesn't seem to check for those errors, but I actually found it beneficial with GhostDriver, because otherwise I would not have seen it.

@detro
Owner
detro commented Jun 12, 2013

I'd hug and kiss you right now :)
On 12 Jun 2013 12:44, "Nathan Dace" notifications@github.com wrote:

@detro https://github.com/detro My comments were directed to those
having this issue. The only time I've encountered this issue is ifif the
click results in a GET error, such as an onclick trying to load a resource
that is missing. In which case, I agree that GhostDriver is handling this
correctly in detecting that an error occurred.

Chrome/Firefox/IE doesn't seem to check for those errors, but I actually
found it beneficial with GhostDriver, because otherwise I would not have
seen it.


Reply to this email directly or view it on GitHubhttps://github.com/detro/ghostdriver/issues/202#issuecomment-19338624
.

@detro
Owner
detro commented Jun 12, 2013

Just wrote this other test:

@Test
    public void shouldHandleCasesWhereJavascriptCodeInitiatesPageLoadsThatFail() throws InterruptedException {
        server.setGetHandler(new HttpRequestCallback() {
            @Override
            public void call(HttpServletRequest req, HttpServletResponse res) throws IOException {
                res.getOutputStream().println("<script type=\"text/javascript\">\n" +
                        "    function myFunction() {\n" +
                        "        window.location.href = 'http://www.ksdajlkdsajlksadj.kdsjhakadjh';\n" +
                        "    }\n" +
                        "    </script>\n" +
                        "    <a href=\"#\" onclick=\"myFunction()\">Click Here</a>\n" +
                        "    <span id='here_i_am'>here</span>");
            }
        });

        WebDriver d = getDriver();
        d.get(server.getBaseUrl());

        d.findElement(By.xpath("html/body/a")).click();

        // "google.com" hasn't loaded yet at this stage
        assertEquals(0, d.findElements(By.id("here_i_am")).size());
    }

This passes with ChromeDriver and FirefoxDriver but fails with GhostDriver.

That means that any page load initiated by user interaction that fails, will be ignored by "click()" and the error will be "swallowed".

@stefanvanwouw

Thanks for the effort put into this issue thus far, detro. I will try and see if I have time tomorrow to look into it.

@detro detro added a commit that closed this issue Jun 13, 2013
@detro Ignore page load failures initiated by Click action.
If the click finishes, it's finished.
The fact that the expected destination page didn't load it's irrelevant.

This implies that, in case a "onLoadFinished" occurred
but resulting "status === 'fail'" we have to ignore it.

This is how Chrome and Firefox Drivers seem to behave…

Fixes #202.
d0615a5
@detro detro closed this in d0615a5 Jun 13, 2013
@stefanvanwouw

It took a while for me to verify that this bugfix also solves the issue I encountered. I had to use blackbox testing (since the website we accessed was not made by us). Before this fix the issue would arise at least once during 5 test iterations. With the fix, it did not occur at all during 100 iterations of blackbox testing. The fix seems to have solved our problem. I would like to thank you for the quick response and effort put into it.

@detro
Owner
detro commented Jun 15, 2013

Very glad!!!
On 14 Jun 2013 03:29, "Stefan van Wouw" notifications@github.com wrote:

It took a while for me to verify that this bugfix also solves the issue I
encountered. I had to use blackbox testing (since the website we accessed
was not made by us). Before this fix the issue would arise at least once
after 5 test iterations. With the fix, it did not occur at all during 100
iterations of blackbox testing. The fix seems to have solved our problem. I
would like to thank you for the quick response and effort put into it.


Reply to this email directly or view it on GitHubhttps://github.com/detro/ghostdriver/issues/202#issuecomment-19443105
.

@kuahyeow kuahyeow added a commit to kuahyeow/ghostdriver that referenced this issue Jun 15, 2013
@detro Ignore page load failures initiated by Click action.
If the click finishes, it's finished.
The fact that the expected destination page didn't load it's irrelevant.

This implies that, in case a "onLoadFinished" occurred
but resulting "status === 'fail'" we have to ignore it.

This is how Chrome and Firefox Drivers seem to behave…

Fixes #202.
Conflicts:
	test/java/src/test/java/ghostdriver/ElementMethodsTest.java

(cherry-picked from d0615a5)
31fe2c7
@torinaki

Sorry for this kind of question, but how I can compile Phantom with GhostDriver from master. I follow this tutorial, but seems like "ghostdriver-dev" branch doesn't contains latest updates. Maybe I must copy latest source to ./src/ghostdriver/ by my self? If is it so than please update documentation.

@stefanvanwouw

That's how I did it @torinaki . Copy the ghostdriver src dir over the one in the ghostdriver-dev branch of phantomjs (make sure to copy over, instead of deleting and then moving, since there are some files in the ghostdriver-dev ./src/ghostdriver/ dir that are needed for compilation, but are not in the ghost driver src dir.)

@torinaki

Compiled. Bug disappear. Thanks a lot. 👍

@detro
Owner
detro commented Jun 21, 2013

There is a faster way.

You can pass via Capabilities the location to a local repo with GhostDriver
source in it. You need that capability to point at the "src/main.js" file.
PhantomJS will NOT use the built in GhostDriver, but it will use the one
you give to it.

On 19 June 2013 14:36, Dmitry Balabka notifications@github.com wrote:

Compiled. Bug disappear. Thanks a lot. [image: 👍]


Reply to this email directly or view it on GitHubhttps://github.com/detro/ghostdriver/issues/202#issuecomment-19684065
.

Ivan De Marino
Coder, Technologist, Cook, Italian

blog.ivandemarino.me | www.linkedin.com/in/ivandemarino |
twitter.com/detronizator

@yoshi95
yoshi95 commented Jun 26, 2013

Hi, sorry to resurrect this, i am unable to find the capability that allows me to override the default embed ghost driver location. I search through the src code, as well as the documentation.

And by capabilities I assume it s not command line arguments right?

is it as simple as:
browser = Selenium::Browser.new(:phantomjs,:args => 'ghostdriver=path/to/gohstdriver/main.js')

@kamenlitchev

I also have related issues. On a website of ours there is Link/Button that brings a dialog in all browsers - in PhantomJS, upon clicking, exhibits the described "Load failed" behaviour. I compiled from source and error disappeared BUT it turned out that the dialog is not being shown. So, unlike all browsers (WebKit based), even clicking the Link/Button still has wrong behaviour - that is, the DIV dialog is not shown at all. The link looks like:

<a href="#" data-action="show_dialog" data-target="confirm-exit">Exit</a>
      $(@form).find('[data-action="show_dialog"]').each ()->
        $(this).live "click", (event)->
          $('#' + $(this).attr('data-target')).modal('toggle')
@ericgross

What is the name of the capability that needs to point to my ghostdriver's src/main.js?

@dutchb
dutchb commented Jul 2, 2013

Detro - tested with the fix and not getting the failure. The "error" logging it gives in its place is interesting to see though. A little impatience on ghostdriver/phantomjs's end, a good deal javascript notes to be taken on ours. Thanks for your time on this.

@user0989

Spent the last couple of hours trying to set the capability in C#

I know this doesn't work :)

var opts = new PhantomJSOptions();
opts.AddAdditionalCapability("phantomjs.ghostdriver.path.property", "c:\path\to\src\main.js");

Have been searching for some documentation on what capabilities can be used. I am sure I found it a few days ago, but cannot for the life of me find it now.

Any pointers greatly appreciated

@user0989

So the above isn't possible in the .net bindings (yet). You'll need the latest source, info here
https://code.google.com/p/selenium/source/detail?r=93acf0798e5b8a93e22fc9d20cc84c7faeef38f9

Anyone else have difficult sending a request through a proxy when specifying the path to the src.js file

Passing args as:
c:\path\to\src\main.js --port=55480 --proxy=1123.456.789:8800
ignores the proxy

Passing like this and everything is good.
--webdriver=55501 --proxy=1123.456.789:8800

@detro
Owner
detro commented Jul 22, 2013

@user0989 Please note that, while the --port is a parameter that GhostDriver script accepts, the --proxy one is for PhantomJS. This means that you should try something like:
phantomjs --proxy=IP:PORT c:\path\to\src\main.js --port=55840

The second example you provide is of PhantomJS parameters only (--webdriver= is for PhantomJS, that runs the internal GhostDriver).

I understand that this can be confusing, and that's why, usually, you should use PhantomJS only, leaving GhostDriver for development or when you need access to unstable/latest code.

@user0989

@detro Thanks for explaining that, you are right it is confusing :-) I will run some tests and see if I can get my head around it.

you should use PhantomJS only, leaving GhostDriver for development or when you need access to
unstable/latest code
Do you have any idea when phantomjs will update to include the fix from this thread: d0615a5

Thanks for all your work in this, it really is quite a brilliant software

@detro
Owner
detro commented Jul 24, 2013

I'm working towards GhostDriver 1.0.4, that will be part of PhantomJS 1.9.2 release.
See ariya/phantomjs#11452

@user0989

Just incase anyone else is having the issue,
detro was right, specifying the args as
" --proxy=123.456.789:80 D:\path\to\src\main.js --port=58967 "
fixed the issue. It is a problem with the .Net bindings, have submitted the issue there, so best to follow it there
https://code.google.com/p/selenium/issues/detail?id=5999&thanks=5999&ts=1374783226

@detro
Owner
detro commented Jul 25, 2013

Well, I wrote the bloody thing :)

Glad you have solved your issue now...

@venkaa
venkaa commented Jul 31, 2013

Hi all

I'm new to phantomjs /ghostdriver and have been following this thread to address a issue i'm facing. I have a question about this and they way headless testing works.

i have phantomjs1.9.1 , ghost driver 1.3 and using selenium webdriver to run my tests. While i'm able to run the tests locally on a 2 of my CI machines, they fail on 2 other machines.

I'm running the same tests and test suite. [reason: regression picks a random box and runs on them]. Is there a reason why this would happen. I donot have the fix for ghost driver yet.

any thoughts or leads would really help.

cheers.

@jspartan
jspartan commented Aug 2, 2013

I am also attempting to resolve issue #202 by using Ghostdriver 1.0.4.

At the moment I am in the process of following @stefanvanwouw and @torinaki example. . .

That's how I did it @torinaki . Copy the ghostdriver src dir over the one in the ghostdriver-dev branch of phantomjs (make sure to copy over, instead of deleting and then moving, since there are some files in the ghostdriver-dev ./src/ghostdriver/ dir that are needed for compilation, but are not in the ghost driver src dir.)

With the amount of time described to compile PhantomJS and my server resources I expect this to go on for many hours. Being new my confidence level is not high that I will be successful on my first attempt. I am also fully prepared to have fubared my entire working Ubuntu 12.04 / Python 2.7.3 / Selenium 2.33.0 / PhantomJS 1.9.1 / Ghostdriver 1.0.3 stack in the process. This accomplishment I am not so new with.

Attempting to first use @detro's "faster way" . . .

detro commented a month ago
There is a faster way. You can pass via Capabilities the location to a local repo with GhostDriver source in it. You need that capability to point at the "src/main.js" file. PhantomJS will NOT use the built in GhostDriver, but it will use the one you give to it.

has met with failure after ironically spending most of the day trying. I take full responsibility due to my current level of noobyness and not having an adequate understanding of the principals involved.

However I can't help to think that if I were able to discover the answer to the below question this delightful day would have been even more enjoyable.

*Hi, sorry to resurrect this, i am unable to find the capability that allows me to override the default embed ghost driver location . . . *

and

What is the name of the capability that needs to point to my ghostdriver's src/main.js?

My best attempt so far has been using the following lack of logic . . .

dcap = dict(DesiredCapabilities.PHANTOMJS)           
dcap["driverName"] = ("/path/to/ghostdriver-master-v1.0.4"
                    "/src/main.js --port=58967")

and by best attempt I mean it did not crash the script. I don't think it ever referenced the GD 1.0.4. instead using the internal v1.0.3. It had no affect on the issue #202 problems I am having. The path has been checked many times and copy pasted in. I think my problem is related to the above two questions. What should I really be using in place of "driverName"?

The answer may well be in this post . . .
#202 (comment)
and I have spent much time with it. However I just can't get there from here.

Thanks for any consideration.

@luksch
luksch commented Aug 2, 2013

@ jspartan - the following is for JAva, not python, but maybe it helps you anyway?

You may look into the issue that is references above #243

This works like a charm now for me. Remember to update to the latest selenium bindings!

DesiredCapabilities caps = DesiredCapabilities.phantomjs();
caps.setCapability(
    PhantomJSDriverService.PHANTOMJS_EXECUTABLE_PATH_PROPERTY,
    "/xxx/phantomjs-1.9.1-linux-x86_64/bin/phantomjs" );
caps.setCapability(
    PhantomJSDriverService.PHANTOMJS_GHOSTDRIVER_PATH_PROPERTY,
    "/xxx/ghostdriver/src/main.js");
WebDriver driver = new PhantomJSDriver(caps);
@jspartan
jspartan commented Aug 2, 2013

@luksch thanks for the reply. #243 and I are old friends. I think we first met this past Wednesday. It was that post that had me immediately check and confirm I was on the latest Selenium 2.33.0 version. Much appreciated.

I attempted to convert your Java bindings to Python. I did learn a lot. Mostly that my translation skills are not yet good enough. I am still researching and can't think of a better way to spend the weekend.

Speaking of incompetence. My effort at compiling PhantomJS with GD 1.0.4 has been right on par with other recent experiences. Good times.

Thank you for your help.

@kevinusa1987

Now I use PhantomJS 1.9.8 version under windows. Still click succeded but load failed. So can you help me solve this problem?

Thanks.

@audax audax added a commit to audax/pypo that referenced this issue Dec 8, 2014
@audax audax Fixed asset loading
 * Updated config for django-pipeline
 * disabled PhantomJS testing because of
   detro/ghostdriver#202
21bd72d
@audax audax added a commit to audax/pypo that referenced this issue Dec 8, 2014
@audax audax Fixed asset loading
 * Updated config for django-pipeline
 * disabled PhantomJS testing because of
   detro/ghostdriver#202

Enabled debug mode in functional tests to fix django-pipeline
a3c8bbd
@alfsb
alfsb commented Jun 16, 2016

For anyone having this exception, a workaround:

public static void ClickAndWaitStale( this IWebElement element , DateTime limit = default(DateTime) , TimeSpan sleepBetween = default(TimeSpan) )
{
    if ( limit == default(DateTime) )
        limit = DateTime.Now.AddSeconds( 300 );
    if ( sleepBetween == default(TimeSpan ) )
        sleepBetween = TimeSpan.FromSeconds( 1 );

    try
    {
        element.Click();
    }
    catch ( System.InvalidOperationException ) // Click succeeded but Load Failed
    {
    }

    while ( DateTime.Now < limit )
    {
        try
        {
            element.GetAttribute( "id" );
            Thread.Sleep( sleepBetween );
        }
        catch ( StaleElementReferenceException )
        {
            return;
        }
    }
    throw new TimeoutException( "Timeout waiting for stale object." );
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment