Karate - How to terminate driver instance when mixed with robot? - karate

I have a test that combines the use of a driver and robot. However, I need to terminate the driver instance before invoking robot. Even if I use the explicit driver.close(), the instance remains active. Here's an example (create-input.feature invokes the driver):
Feature: mixing driver and robot
Background:
* call read('../../../../actions/workflow/general/create-input.feature') {sample-id: sampleId}
* configure afterScenario = function(){ karate.call('../../../../actions/auth/signout.feature'); }
Scenario: terminate driver before invoking robot
* print '>>>>>>>>>>>>>>>>>>>BEFORE CLOSE>>>>>>>>>>>>>>', driver
* driver.close()
* print '>>>>>>>>>>>>>>>>>>>AFTER CLOSE>>>>>>>>>>>>>>', driver
* robot { window: '#(windowName)', fork: '#(appPath)', retryCount: '#(retryCount)', autoClose: '#(autoClose)', highlight: '#(highlight)', highlightDuration: '#(highlightDuration)' }
* window(windowName)
* call read('../../../../actions/auth/signin.feature')
After the explicit close, the driver instance remains active:
INFO com.intuit.karate - [print] >>>>>>>>>>>>>>>>>>>BEFORE CLOSE>>>>>>>>>>>>>> com.intuit.karate.driver.chrome.Chrome#d3324b
09:47:24.064 [main] DEBUG c.intuit.karate.driver.DriverOptions - >> {"id":83,"method":"Page.close"}
09:47:24.069 [nioEventLoopGroup-2-1] DEBUG c.intuit.karate.driver.DriverOptions - << {"id":83,"result":{}}
09:47:24.072 [main] INFO com.intuit.karate - [print] >>>>>>>>>>>>>>>>>>>AFTER CLOSE>>>>>>>>>>>>>> com.intuit.karate.driver.chrome.Chrome#d3324b
And when the robot logic is reached, it throws an error:
* window(windowName)
>>>> js failed:
01: window(windowName)
<<<<
org.graalvm.polyglot.PolyglotException: ReferenceError: "window" is not defined
- <js>.:program(Unnamed:1)
09:47:27.917 [main] DEBUG c.intuit.karate.driver.DriverOptions - >> {"id":84,"method":"Page.captureScreenshot"}
09:47:57.919 [main] ERROR c.intuit.karate.driver.DriverOptions - << timed out after milliseconds: 30000 - [id: 84, method: Page.captureScreenshot]
* window(windowName)
scenario [run] failed
failed to get reply for: [id: 84, method: Page.captureScreenshot]
09:47:58.056 [main] WARN com.intuit.karate - 'driver' is active, use 'robot.' prefix for robot methods
I realize that I need to prepend the window() method with robot to make it work, but I'd prefer to just terminate the driver instance prior to invoking robot. Reason being is that I later call other features with assertions specific to robot and with the driver still being active, it causes further issues.
Any suggestions will be greatly appreciated.

Did you try driver.quit() ? https://github.com/intuit/karate/tree/master/karate-core#quit
If that doesn't work (it should !) you can submit an issue, but I insist that you provide a way to replicate: https://github.com/intuit/karate/wiki/How-to-Submit-an-Issue
As a workaround - you could experiment if using the Java API directly gives you the control you need: https://github.com/intuit/karate#java-api

As always, thanks Peter for a prompt response and turnaround. I tested it with your fix applied and it works as expected. Following is the simplified test I used:
Feature: mixing driver and robot
Background:
* configure driver = { type: 'chrome', showDriverLog: true }
Scenario: terminate driver before invoking robot
* driver 'https://google.com'
* input("input[name=q]", 'karate dsl')
* submit().click("input[name=btnI]")
* waitForUrl('https://github.com/intuit/karate')
* quit()
* robot { window: 'Calculator', fork: 'calc', highlight: true, highlightDuration: 500 }
* click('Clear')
* click('One')
* click('Plus')
* click('Two')
* click('Equals')
* match locate('#CalculatorResults').name == 'Display is 3'
* screenshot()
* click('Close Calculator')

Related

cannot start mozilla using custom profile in karateUI

I'm using karate 1.3.0 and I'm stuck trying to launch mozilla Firefox v105.0.2 using a specific SSL client certificate.
As a mention, I developed this scenario before, successfuly using Java + Selenium, but now I need to integrate UI functional tests in my API test suite that is using Karate.
I wrote this code:
Scenario:
* def session = {'capabilities': {'alwaysMatch': {'acceptInsecureCerts':true, 'moz:firefoxOptions': {'profile': 'classpath:FFProfile/ste7rob0.zip.b64','log': {'level': 'debug'}}}}}
* def driverConfig = { type: 'geckodriver', showBrowserLog: true, showProcessLog: true, showDriverLog: true, executable: './src/test/resources/driver/mozilla/win64/geckodriver.exe'}
* driverConfig.webDriverSession = session
* configure driver = driverConfig
Given driver monitorUrl
And I was expecting to get a webdriver to access monitorUrl using the profile specified. The profile folder was customized manually, zipped and encoded to base64 on the development machine.
But the result was:
18:20:16.267 [main] WARN com.intuit.karate - http response code: 500, response: {"value":{"error":"unknown error","message":"Invalid byte 58, offset 9.","stacktrace":""}}, request: POST http://localhost:4444/session
18:20:16.268 [main] ERROR c.intuit.karate.driver.DriverOptions - webdriver session create status 500, {"value":{"error":"unknown error","message":"Invalid byte 58, offset 9.","stacktrace":""}}
18:20:16.269 [main] ERROR com.intuit.karate - driver config / start failed: webdriver session create status 500, {"value":{"error":"unknown error","message":"Invalid byte 58, offset 9.","stacktrace":""}}, options: {type=geckodriver, showBrowserLog=true, showProcessLog=true, showDriverLog=true, executable=./src/test/resources/driver/mozilla/win64/geckodriver.exe, webDriverSession={capabilities={alwaysMatch={acceptInsecureCerts=true, moz:firefoxOptions={profile=classpath:FFProfile/ste7rob0.zip.b64, log={level=debug}}}}}, target=null}
java.lang.RuntimeException: webdriver session create status 500, {"value":{"error":"unknown error","message":"Invalid byte 58, offset 9.","stacktrace":""}}
at com.intuit.karate.driver.WebDriver.<init>(WebDriver.java:67)
at com.intuit.karate.driver.firefox.GeckoWebDriver.<init>(GeckoWebDriver.java:42)
at com.intuit.karate.driver.firefox.GeckoWebDriver.start(GeckoWebDriver.java:48)
at com.intuit.karate.driver.DriverOptions.start(DriverOptions.java:316)
at com.intuit.karate.core.ScenarioEngine.driver(ScenarioEngine.java:881)
at com.intuit.karate.ScenarioActions.driver(ScenarioActions.java:426)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:568)
at com.intuit.karate.core.StepRuntime.execute(StepRuntime.java:296)
at com.intuit.karate.core.ScenarioRuntime.execute(ScenarioRuntime.java:449)
at com.intuit.karate.core.ScenarioRuntime.run(ScenarioRuntime.java:400)
at com.intuit.karate.core.FeatureRuntime.processScenario(FeatureRuntime.java:199)
at java.base/java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:179)
at com.intuit.karate.core.ScenarioIterator.tryAdvance(ScenarioIterator.java:162)
at java.base/java.util.Spliterator.forEachRemaining(Spliterator.java:332)
at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:509)
at java.base/java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:499)
at java.base/java.util.stream.StreamSpliterators$WrappingSpliterator.forEachRemaining(StreamSpliterators.java:310)
at java.base/java.util.Spliterators$1Adapter.forEachRemaining(Spliterators.java:706)
at com.intuit.karate.core.FeatureRuntime.run(FeatureRuntime.java:182)
at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:539)
at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
at com.intuit.karate.core.SyncExecutorService.execute(SyncExecutorService.java:70)
at java.base/java.util.concurrent.AbstractExecutorService.submit(AbstractExecutorService.java:123)
at com.intuit.karate.Suite.run(Suite.java:237)
at com.intuit.karate.Runner$Builder.parallel(Runner.java:496)
at com.intuit.karate.cli.IdeMain.main(IdeMain.java:60)
at cucumber.api.cli.Main.main(Main.java:34)
18:20:16.270 [main] ERROR com.intuit.karate - src/test/java/splmonitor/TC3.acces_autorizat.feature:12
Given driver monitorUrl
driver config / start failed: webdriver session create status 500, {"value":{"error":"unknown error","message":"Invalid byte 58, offset 9.","stacktrace":""}}, options: {type=geckodriver, showBrowserLog=true, showProcessLog=true, showDriverLog=true, executable=./src/test/resources/driver/mozilla/win64/geckodriver.exe, webDriverSession={capabilities={alwaysMatch={acceptInsecureCerts=true, moz:firefoxOptions={profile=classpath:FFProfile/ste7rob0.zip.b64, log={level=debug}}}}}, target=null}
src/test/java/splmonitor/TC3.acces_autorizat.feature:12
18:20:16.270 [geckodriver_1674836415732] WARN com.intuit.karate.shell.Command - exit code was non-zero: 1 - [C:\QA\workspace2022\aliaspay-test-engine\.\src\test\resources\driver\mozilla\win64\geckodriver.exe, --port=4444] working dir: target\geckodriver_1674836415732

Disable Chrome Password Manager through Karate framework

Trying to pick up the right combination of chrome options to disable annoying Password Manager popup after passing login form.
Here is how I create a driver:
Feature: Driver initialization
Background:
* configure retry = { count: 5, interval: 3000 }
Scenario Outline: using <config>
* def config = <config>
* set config.showDriverLog = true
* configure driver = config
* driver 'https://google.com'
* maximize()
* retry().waitUntil("document.readyState == 'complete'")
Examples:
| config |
| {type: 'chrome', executable: '/Applications/Google Chrome.app/Contents/MacOS/Google Chrome', webDriverSession: { desiredCapabilities: { browserName: 'chrome', 'goog:chromeOptions': { credentials_enable_service: false, profile.password_manager_enabled: false }}}} |
Also I tried some other combinations with addOptions: [ ... ] and so on but nothing helps. Any ideas?
I had a similar issue but I found a workaround. Instead of using driver type to be chrome and pointing to the google chrome application installed locally download the chromedriver and use that. I used this on Windows and placed the chromedriver under C:/Windows/ folder. This did not bring up the password manager popup when executing the tests.
I've heard that using incognito mode can solve this.

Ui Automation - java.net.SocketTimeoutException: Read timed out for "driver url"

My web page is very slow and taking approx 1 minute to load page. Hence causing below line to fail.
* configure driver = { type: 'chromedriver', executable: '/Users/vikas/Apps/chromedriver', showDriverLog: true }
* driver 'http://XXXX.XXX'
I configured readTimeout in karate-config.js but no help:
karate.configure('readTimeout', 60000);
Error Message:
ERROR com.intuit.karate - java.net.SocketTimeoutException: Read timed out, http call failed after 30003 milliseconds for URL: http://localhost:9515/session/c7c09b611f294b8d13ef7d63668b2677/url
ERROR com.intuit.karate - http request failed:
java.net.SocketTimeoutException: Read timed out
For Selenium WebDriver there is infinite timeout for driver.get(url) which can be changed by pageLoadTimeout() .
Is there anything with Karate Core to handle such long page loading.
Yes, the config for the HTTP client used for the UI driver is separate. So you do something like this:
* configure driver = { httpConfig: { readTimeout: 120000 } }
Just add httpConfig to your existing driver configuration.
Refer: https://github.com/intuit/karate/tree/master/karate-core#configure-driver

Selenium Chrom driver : failed to parse value of getElementRegion

I try to implement some Automated User Test with Behat/Mink on Selenium in a Docker.
However, I received a "failed to parse value of getElementRegion" for some Element.
Do you have any clue where I should look to solve this problem ?
I try to launch this test with docker, on a Selenium's Container.
The Behat test try to access to a div inside a modal.
I can confirm that the text is visible on the screen, it's one of my previous line in the behat's file.
I wanted to try the solution describe here, however I don't have any conf.js in my project.
I try to see during the test if the id change (With a sleep juste before trying to click), however, I can manually see it.
I don't see any other solution that the one I linked before on Google.
My Script
#javascript #second
Feature: Builder Features
In Order to use the website as an Builder
I should be able to modify the roadmap
Scenario: I can do click on the modal
When I am on "/thispage"
Then I should see "The Title who open the Modal"
Then I click on ".form-check-label"
Then I wait "1"
Then I wait until "#generic-modal" load
Then I should see "The title of the modal"
Then I should see "The description of the modal"
Then I click on "#check47"
Then I press "Close the modal"
The PHP behind I click on :
/**
* #Then /^I click on "([^"]*)"$/
*/
public function iClickOn($selector)
{
$page = $this->getSession()->getPage();
$element = $page->find('css', $selector);
if (empty($element)) {
throw new Exception("No html element found for the selector ('$selector')");
}
$element->click();
}
The docker-compose's Selenium part
selenium:
image: selenium/standalone-chrome-debug:latest
networks:
app_tier:
ipv4_address: 172.11.1.4
environment:
- SCREEN_WIDTH=1920
- SCREEN_HEIGHT=1080
ports:
- "5900:5900"
volumes:
- "/dev/shm:/dev/shm"
- "../features/file:/usr/share/tag/file/"
The Behat's Extension in behat.yml
extensions:
Behat\MinkExtension:
base_url: "http://172.11.1.3"
sessions:
javascript:
selenium2:
capabilities: {"browserName": "chrome", "browser": "chrome", 'chrome': {'switches': ['--whitelisted-ips']}, "marionette": true, "extra_capabilities": {"goog:chromeOptions":{"w3c":false,"args":["start-maximized", 'disable-dev-shm-usage', 'disable-extensions']}}}
wd_host: 'http://172.11.1.4:4444/wd/hub'
Behat\Symfony2Extension: ~
I should pass all the behat's script without any error.
However, this message appears :
Then I click on "#check27" # FeatureContext::iClickOn()
unknown error: failed to parse value of getElementRegion
(Session info: chrome=77.0.3865.75)
(Driver info: chromedriver=77.0.3865.40 (f484704e052e0b556f8030b65b953dce96503217-refs/branch-heads/3865#{#442}),platform=Linux 4.19.23-coreos-r1 x86_64) (WebDriver\Exception\UnknownError)

It shows error after using geck V0.16.1

It shows error after using geckodriver V0.16.1 Browser is getting opened and also URL is opened, but shows below error while opening browser:
1496729301597 geckodriver INFO Listening on 127.0.0.1:26189
1496729302267 geckodriver::marionette INFO Starting browser
\?\C:\Program Files\Mozilla Firefox\firefox.exe with args
["-marionette"]
1496729302562 addons.manager ERROR startup failed: [ExceptioJavaScript
error: resource://gre/modules/AddonManager.jsm, line 1657:
NS_ERROR_NOT_INITIALIZED: AddonManager is not initialized
n... "Component returned failure code: 0x80070057
(NS_ERROR_ILLEGAL_VALUE) [nsIFile.create]" nsresult: "0x80070057
(NS_ERROR_ILLEGAL_VALUE)" location: "JS frame ::
resource://gre/modules/FileUtils.jsm :: FileUtils_getDir :: line 70"
data: no] Stack trace:
FileUtils_getDir()#resource://gre/modules/FileUtils.jsm:70 <
FileUtils_getFile()#resource://gre/modules/FileUtils.jsm:42 <
validateBlocklist()#resource://gre/modules/AddonManager.jsm:671 <
startup()#resource://gre/modules/AddonManager.jsm:834 <
startup()#resource://gre/modules/AddonManager.jsm:3129 <
observe()#resource://gre/components/addonManager.js:65
JavaScript error: resource://gre/components/SanityTest.js, line 65:
NS_ERROR_FILE_ACCESS_DENIED: Component returned failure code:
0x80520015 (NS_ERROR_FILE_ACCESS_DENIED) [nsIPrefService.savePrefFile]
JavaScript error: resource://gre/modules/AddonManager.jsm, line 2570:
NS_ERROR_NOT_INITIALIZED: AddonManager is not initialized
1496729310139 Marionette INFO Listening on port 50194
Jun 06, 2017 11:38:30 AM org.openqa.selenium.remote.ProtocolHandshake
createSession
INFO: Detected dialect: W3C
My code is as given below:
public static void main(String[] args) throws InterruptedException {
// TODO Auto-generated method stub
WebDriver driver ;
System.setProperty("webdriver.gecko.driver","D:\\geckodriver-v0.16.1-win64\\geckodriver.exe");
driver = new FirefoxDriver();
driver.get("http://google.co.in");
}
May I know which selenium standalone server version you are using? It should work fine with 3.4.0