I am trying to get some geb tests running in a Grails project within IntelliJ but am having trouble & after 2 days of web searching & trying different things am still stuck. We did have some Groovy tests running fine, previously, but no luck so far with geb. We're using cucumber-jvm.
Currently I am getting the following error:
Error Error executing script TestApp: groovy.lang.MissingMethodException:
No signature of method: GebConfig.environments() is applicable for argument types:
(GebConfig$_run_closure2) values: [GebConfig$_run_closure2#4ad3727e]
My GebConfig.groovy file is in test/functional, and contains:
import org.openqa.selenium.htmlunit.HtmlUnitDriver
import org.openqa.selenium.firefox.FirefoxDriver
import org.openqa.selenium.chrome.ChromeDriver
// Use htmlunit as the default
// See: http://code.google.com/p/selenium/wiki/HtmlUnitDriver
driver = {
def driver = new HtmlUnitDriver()
driver.javascriptEnabled = true
driver
}
environments {Not sure
chrome {-Dgeb.env=chrome
driver = { new ChromeDriver() }
}
firefox {
driver = { new FirefoxDriver() }
}
}
I have the .feature file also in test/functional. The step def's are in test/functional/steps & contains:
package steps
import geb.*
this.metaClass.mixin (cucumber.runtime.groovy.EN)
this.metaClass.mixin (cucumber.runtime.groovy.Hooks)
def browser = new Browser()
Given (~"I am on the front page") {
browser.go("http://localhost:8081/whereisOne")
}
There is also a shared_driver.groovy class in test/functional/setup that was created for the straight Groovy tests, & I'm not sure if this is still needed.
The run config command is: test-app --stacktrace, with VM options: -Dgeb.env=chrome
Any help appreciated, thank you!
Is the -Dgeb.env=chrome in the code? If so, you have to remove this line. Everything else looks fine.
Related
I'm trying to get Jenkins set up, with configuration, within a Docker environment. Per a variety of sources, it appears the suggested method is to insert scripts into JENKINS_HOME/init.groovy.d. I've taken scripts from places like the Jenkins wiki and made slight changes. They're only partially working. Here is one of them:
import java.util.logging.ConsoleHandler
import java.util.logging.FileHandler
import java.util.logging.SimpleFormatter
import java.util.logging.LogManager
import jenkins.model.Jenkins
// Log into a file
println("extralogging.groovy")
def RunLogger = LogManager.getLogManager().getLogger("hudson.model.Run")
def logsDir = new File("/var/log/jenkins")
if (!logsDir.exists()) { logsDir.mkdirs() }
FileHandler handler = new FileHandler(logsDir.absolutePath+"/jenkins-%g.log", 1024 * 1024, 10, true);
handler.setFormatter(new SimpleFormatter());
RunLogger.addHandler(handler)
This script fails on the last line, RunLogger.addHandler(handler).
2019-12-20 19:25:18.231+0000 [id=30] WARNING j.util.groovy.GroovyHookScript#execute: Failed to run script file:/var/lib/jenkins/init.groovy.d/02-extralogging.groovy
java.lang.NullPointerException: Cannot invoke method addHandler() on null object
I've had a number of other scripts return NULL objects from various gets similar to this one:
def RunLogger = LogManager.getLogManager().getLogger("hudson.model.Run")
My goal is to be able to develop (locally) a Jenkins implementation and then hand it to our sysops guys. Later, as I add pipelines and what not, I'd like to be able to also work on them in a local Jenkins configuration and then hand something for import into production Jenkins.
I'm not sure how to produce API documentation so I can chase this myself. Maybe I need to stop doing it this way and just grab the files that get modified when I do this via the GUI and just stuff the files into the right place.
Suggestions?
I am bumping into an issue in my integration test. My code uses a system property (System.getProperty(...) ) and I am not being able to set the system property when running the integration test. Any idea on how to define system properties that are visible inside code running in integration test?
I am using Grails 3.3.1.
Slimmed down example of integration test not seeing the system property:
package injecttest
import grails.testing.mixin.integration.Integration
import grails.transaction.*
import org.springframework.beans.factory.annotation.Autowired
import spock.lang.Specification
#Integration
#Rollback
class C1ITSpec extends Specification {
void "test system property readable inside test"() {
String val = System.getProperty("var1", "ERROR")
expect:"system variable to match value passed as '-Dvar1=OK' in command line"
"OK" == val
}
}
A new JVM is forked to run the test, so you have to pass the command-line system properties to the test's JVM.
In Grails 4, which uses gradle, you can pass the system properties in your gradle file:
integrationTest.doFirst {
systemProperties System.getProperties().subMap(["var1"])
}
I adapted this from the answers to this question for Grails 3: How to give System property to my test via Gradle and -D.
If I use cucumber.api.groovy.Hooks.World then tests are working fine. But I cannot open declaration in steps definition
World() {
def world = new LucieWorld()
world.metaClass.mixin Lucie
world
}
step definition:
Given(~/^User is (.+)$/) { def username ->
login(username) //I cannot open declaration here
}
When I am in a step definition file (groovy), Intellij can't seem to see variables and methods defined in the cucumber "World" object Lucie. So don't get IDE support (auto-complete, etc) for those which is a bit annoying. How can I fix that?
I try to use this.metaClass.mixin(Lucie) in step definition, but I think, that this is not a good solution.
I am running Spock tests with Gebish & HtmlUnitDriver. So far so good.
For reasons of speed I am changing the driver to PhantomJS: http://phantomjs.org/
my GebConfigs.groovy looks like this:
import org.openqa.selenium.phantomjs.PhantomJSDriver
import org.openqa.selenium.remote.DesiredCapabilities
import org.openqa.selenium.WebDriver
import org.openqa.selenium.Dimension
driver {
ArrayList cliArgsCap = new ArrayList();
cliArgsCap.add("--web-security=false");
cliArgsCap.add("--ssl-protocol=any");
cliArgsCap.add("--ignore-ssl-errors=true");
DesiredCapabilities desiredCapabilities = new DesiredCapabilities()
desiredCapabilities.setCapability(PhantomJSDriverService.PHANTOMJS_CLI_ARGS, cliArgsCap);
PhantomJSDriver d = new PhantomJSDriver(desiredCapabilities)
d
}
as you see, no matter what a PhantomJSDriver should be used for tests.
my BuildConfig.groovy
test "org.gebish:geb-spock:$gebVersion"
test "org.seleniumhq.selenium:selenium-chrome-driver:$seleniumVersion"
test "org.seleniumhq.selenium:selenium-remote-driver:$seleniumVersion"
test "org.seleniumhq.selenium:selenium-htmlunit-driver:$seleniumVersion"
test "org.seleniumhq.selenium:selenium-support:$seleniumVersion"
test "org.spockframework:spock-grails-support:0.7-groovy-2.0"
test "org.grails:grails-datastore-test-support:1.0-grails-2.4"
test( "com.github.detro.ghostdriver:phantomjsdriver:1.1.0" ) {
transitive = false
}
the phantomjs.exe is located in:
C:\Apps\selenium\phantomjs\phantomjs.exe
and C:\Apps\selenium\phantomjs is in my PATH. i can run it through cmd: phantomjs in interactive mode.
problem
for some unclear reason geb is still using a HtmlUnitDriver. see log:
Error |
2014-08-15 14:01:26,630 [JS executor for com.gargoylesoftware.htmlunit.WebClient#527a4013] ERROR
javascript.StrictErrorReporter - runtimeError: message=[The data necessary to complete this
operation is not yet available.] sourceName=[http://localhost:8080/myapp/aui/js/aui-all.js] line=
[1] lineSource=[null] lineOffset=[0]
any ideas why phantomjsdriver is not used in this case?
I have phantomjs up and running with a Grails 2.0.4 app. My buildConfig.groovy looks like this:
def gebVersion = "0.9.2"
def seleniumVersion = "2.35.0"
...
test "org.gebish:geb-spock:$gebVersion"
test "org.gebish:geb-junit4:$gebVersion"
test( "com.github.detro.ghostdriver:phantomjsdriver:1.0.1" ) {
transitive = false
exclude "xml-apis"
exclude "xercesImpl"
}
test ("org.seleniumhq.selenium:selenium-remote-driver:$seleniumVersion") { // Needed by phantomjsdriver
exclude "xerces"
exclude "xercesImpl"
}
hope that helps
Update: had to work a little bit on my own example, but the result is a working Grails 2.4.2 app with phantomjs: https://github.com/rdmueller/SO25324259 (sorry for the horrible formatting - only saw it after my checkin).
btw: I didn't get your DesiredCapabilities to work :-(
PS: did you know the report feature? https://github.com/rdmueller/SO25324259/blob/master/test/functional/DemoSpec.groovy#L14
It takes a screenshot with your headless phantomjs browser - really cool feature!
I just grabbed the latest version of the functional testing plugin and it's focus, at least from the docs, has changed a bit. This is not a bad thing. The HtmlUnit integration is nice. But now, there isn't anything in the docs about RESTful testing of web services. However, what I used to do with functionaltestplugin.FunctionalTestCase still works, which is great.
For example:
void testCertifyEmployerCertifierNotFound() {
post('/employerCertification/certifyEmployer') {
headers['Content-Type'] = 'application/json'
body {
"""
{
'employerName': 'ACME',
'certifierExteralId': '1234556',
'certifyingUserId': '123445'
}
"""
}
}
assertStatus 200
assertContentType "application/json"
def model = this.response.contentAsString
def map = JSON.parse(model)
assertFalse(map.success)
assertNotNull(map.errorCode)
assertTrue(map.errorCode == EmployerCertificationService.ERROR_RESPONSE.CERTIFIER_NOT_FOUND.toString())
}
Is this plugin still the "defacto" plugin to use for functional web service testing and is my approach above still valid?
if your target is testing REST request/response I suggest you to use rest client builder plugin. You don't need complex browser-simul plugins. Use it is very simple in just two steps after installing it:
add event to manage functional tests in scripts/_Events.groovy: this is a system grail file used to hook some events at runtime. Just copy and paste this snippet:
eventAllTestsStart = {
if (getBinding().variables.containsKey("functionalTests")) {
functionalTests << "functional"
}
}
Now you can create functional tests in test/functional folder, rememeber to ends filename with Spec, grails will not find any tests if you forget this.
This is an example:
import grails.plugins.rest.client.RestBuilder
import spock.lang.Specification
class AuthenticationSpec extends Specification {
String baseUrl = "http://localhost:8080/grouply-backend"
void "test login wrong credentials"() {
given:
RestBuilder restBuilder = new RestBuilder()
when: "sending wrong credential"
def response = restBuilder.post("${baseUrl}/auth/login") {
json {
username = 'foo'
password = 'bar'
}
}
then: "authentication http error should happen"
response.status == 401
}
}
run tests with $ grails test-app functional:
I have just tried to use both functional testing plugin and webtest plugin with almost-current Grails 2.4.2 and I am sad to report that they are both borked. :(
Functional testing plugin has been practically abandoned for at least 9 months now. On December 2013 a critical bug that makes all of tests written using this plugin not working has been reported. There was no response from plugin developer regarding it up to the day I am writing this. And as this developer, Marc Palmer has switched to iOS development and consultancy in August 2014 I don't believe this bug will ever be resolved.
Webtest plugin has been last updated more than 3 years ago and it "requires Grails 1.2.RC2+". I run into ugly error of missing webtest.jar when running it and it looks like this plugin just haven't been updated to current Grails version. Also its syntax is not very Groovy-like and not nice.
Fortunately Geb integration for Grails plugin is supposed to work with current Grails versions. :) In fact in does only work with Grails 2.3.1+, as of writing these words has been last time updated in June 2014 and it's example tests project have been updated to Grails 2.4.3, release just a few days ago already, so it is very up-to-date. However I haven't used this project yet. Also looking at is's example code I am not sure it the best choice for RESTful API testing - it's more of a GUI web application testing tool..
Although is probably not very "grails style" i guess it should be possible to start up the whole stack with the spring context and run integration rest tests using apache HttpClient.