How to Run TestNG Tests on Jenkins - java

I'm trying to run TestNG tests (in a contained Java project) from Jenkins but having no luck.
It appears as though the TestNG plugin for Jenkins (https://wiki.jenkins-ci.org/display/JENKINS/testng-plugin) only publishes the results of TestNG tests, but doesn't actually run test classes... or am I wrong?
In any case, how do I actually run TestNG tests in a TestNG project with Jenkins, or is that even possible? Do I have to use a command line statement or batch file (on Windows Server 2008), for example?
Any help much appreciated.
Note I tried entering a post-build command line in Jenkins for the project to run TestNG tests but had a hard time with class paths not being found for TestNG. I posted an earlier question about running TestNG from the command line which I couldn't get working, so I've given up on that route:
How to run TestNG from command line

There are two steps to accomplished this task:-
Step 1:-
Go to localhost:8080/configure (Jenkins configure section)
Now go to JDK section and uncheck Install automatically (If you don't uncheck that then it will download latest java every time whenever it is available, and can cause for build failed)
put JAVA_HOME in name section and jdk home path in JAVA_HOME section
Apply and save
Step 2:-
Go to Jenkins and add new Item, also select "Free Style Project" and click on Ok.
Click on "Advanced in "Advanced Project Options"
Now check option: - "Use custom workspace" and specify your project absolute path in Directory section
Apply
Now to go "Build" and select "Execute windows batch command"
Here in command column give the file name of your batch file
Apply and save
Now go to the Jenkins and select your Jenkins project and click on Build :)

I use gradle to run my testNG tests from Jenkins.
Take a look at the gradle docs.
I run the testNG tests using configuration xml files.
Take a look at the testNG docs.
There is quite a lot to cover so I suggest reading these sources but I'll provide some relevant pieces from one of my configurations.
The relevant parts from my build.gradle
tasks.withType(Test) {
useTestNG {
useDefaultListeners = true
}
options {
outputDirectory = file('test-report')
listeners << 'org.uncommons.reportng.JUnitXMLReporter'
}
testLogging.showStandardStreams = true
systemProperties System.getProperties()
systemProperty "org.uncommons.reportng.escape-output", "false"
systemProperty "org.uncommons.reportng.title", "Test Report"
ignoreFailures = true
}
task Smoke_Test(type: Test) {
description "SmokeTest"
options.suites("resources/testng-smoketest.xml")
ignoreFailures = false
}
My testNG xml as referenced above 'testng-smoketest.xml'
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd" >
<suite name="Smoke Tests" >
<test name="BootCheck" parallel="false" thread-count="1">
<classes>
<class name="com.x.automation.y.tests.smoke.BootCheck" />
</classes>
</test>
</suite>
And from Jenkins, as an 'execute shell' build step run the gradle task, I use gradle wrapper for convenience.
./gradlew clean Smoke_Test
Ensure you're in the correct directory, 'Smoke_Test' is the name specified in the build.gradle.
You can use the testNG Jenkins plugin for saving your results.
I also recommend using reportng for nice formatting of your test reports which can also be shown and saved in Jenkins using the HTML Publisher plugin.
Try getting this to run from a CLI on your local machine first, trying to debug when running from Jenkins will drive you crazy.

As commented above, please use the following ant script to run TestNG unit tests. Please tweak the below code to meet your requirements.
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<project basedir="." default="build" name="Ant Play">
<property name="classes.dir" value="bin" />
<property name="report.dir" value="test-output" />
<path id="classpath">
<fileset dir="lib">
<include name="**/*.jar"/>
</fileset>
<pathelement path="${basedir}\${classes.dir}"/>
</path>
<target name="init">
<mkdir dir="${classes.dir}"/>
<copy includeemptydirs="false" todir="${classes.dir}">
<fileset dir="src">
<exclude name="**/*.java"/>
</fileset>
</copy>
</target>
<target name="clean">
<delete dir="${classes.dir}"/>
</target>
<target depends="clean" name="cleanall"/>
<target depends="build-project" name="build"/>
<target depends="init" name="build-project">
<echo message="${ant.project.name}: ${ant.file}"/>
<javac debug="true" includeantruntime="false" destdir="${classes.dir}">
<src path="src"/>
<classpath refid="classpath"/>
</javac>
</target>
<target depends="build" name="runTests" description="Running tests" >
<echo>Running Tests...</echo>
<taskdef resource="testngtasks" classpathref="classpath"/>
<testng outputDir="${report.dir}"
haltonfailure="true"
useDefaultListeners="false"
listeners="org.uncommons.reportng.HTMLReporter"
classpathref="classpath">
<xmlfileset dir="${basedir}" includes="testng.xml"/>
<!--<classfileset dir="${classes.dir}" includes="**/*.class" />-->
</testng>
</target>
</project>
Let me know if you encounter any issues. BTW, please use the Jenkins ant plugin/task to run this script

Related

Jacoco: unable to read execution data file, ant task

Info:
java version: 1.8.0_66
ant version: 1.9.6
What I want to do:
Provide a code coverage report for the server's code that is running on AWS windows 2k12 server.
What I did:
Stop the server completely.
Put jacocoagent.jar into server's bin folder. Note: this is inside Program Files folder
Append -javaagent settings to JAVA_OPTS that is used during server start up.
Start the server.
Run my sample test from my local laptop.
Stop the server completely. This produced a 184kb jacoco.exec.
Copied my build.xml to the same directory where the jacoco.exec is located. C:/path/to/exec/jacoco.exec
Copied jacocoant.jar to C:/path/to/jacocoant.jar
cd into C:/path/to/exec/ and run command "ant"
Result:
Got error unable to read execution data file C:/path/to/exec/jacoco.exec
Build.xml:
<project name="Example" default="rebuild" xmlns:jacoco="antlib:org.jacoco.ant">
<description>
Example Ant build file that demonstrates how a JaCoCo coverage report
can be itegrated into an existing build in three simple steps.
</description>
<property name="result.dir" location="." />
<property name="result.classes.dir" location="${result.dir}/path/to/classes" />
<property name="result.report.dir" location="${result.dir}/report" />
<property name="result.exec.file" location="${result.dir}/jacoco.exec" />
<!-- Step 1: Import JaCoCo Ant tasks -->
<taskdef uri="antlib:org.jacoco.ant" resource="org/jacoco/ant/antlib.xml">
<classpath path="../jacocoant.jar" />
</taskdef>
<target name="clean">
<delete dir="${result.report.dir}" />
</target>
<target name="report">
<!-- Step 3: Create coverage report -->
<jacoco:report>
<!-- This task needs the collected execution data and ... -->
<executiondata>
<file file="${result.exec.file}" />
</executiondata>
<!-- the class files and optional source files ... -->
<structure name="JaCoCo Code Coverage Report">
<classfiles>
<fileset dir="${result.classes.dir}" >
</fileset>
</classfiles>
<sourcefiles encoding="UTF-8">
<fileset dir="${src.dir}" />
</sourcefiles>
</structure>
<!-- to produce reports in different formats. -->
<html destdir="${result.report.dir}" />
<csv destfile="${result.report.dir}/report.csv" />
<xml destfile="${result.report.dir}/report.xml" />
</jacoco:report>
</target>
I am not sure if the problem is with exec file (it is corrupted maybe) or is with my entire setup.
Any help to identify and help solving the problem is appreciated!!!
Thanks!
I got this when using gradle and jaCoCo.
I deleted the build/ directory and reran ./gradlew jacocoTestReport, this time passing.
Similar to #sofia's solution but for gradle:
I removed the version after tool version. Instead of
allprojects {
jacoco {
toolVersion = '0.7.1.201405082137'
}
}
I used the following
allprojects {
jacoco {
toolVersion = '0.7.1'
}
}
I have the same problem recently, it took me long time to figure this out. I hope how I fix this will help you or someone else.
Use ant -verbose report to see the detailed information. I used "ant -verbose report" and got this message: "java.io.IOException: Incompatible version 1007".
As I am using maven, I added the following lines to my pom.xml. Note: version is the same as your javaagent's version.
<dependency> <groupId>org.jacoco</groupId> <artifactId>org.jacoco.ant</artifactId> <version>0.7.4.201502262128</version> </dependency>
In the end, the report is successfully generated.

System property, "java.class.path" does not contain classpath added from ant script

I added classpath to an ant script. Then, in a java file, I wrote "java.class.path" property to get the classpath. When I run a test suite in Eclipse, the classpath is in the property value. However, when I ran the test suite with ant script in terminal, the classpath is not in the property value. I couldn't find the reason.
Here is the ant script snippet. I added "target/class" and jar files to the classpath.
<target name="test">
<echo message="Running unit tests ..."/>
<junit printsummary="true"
showoutput="true"
haltonfailure="false">
<formatter type="plain" usefile="false"/>
<classpath>
<pathelement path="${result.classes.dir}"/>
<path refid="jmeter_cp"/>
</classpath>
<test name="test.JMeterTestSuite"/>
</junit>
</target>
And here is java code snippet. It retrieves "java.class.path" property value.
stPaths = new StringTokenizer(
System.getProperty("java.class.path"),
System.getProperty("path.separator"));
I looked at the "java.class.path" value, but it did not have "target/class" and the jar files...
FYI, I'm using an modified ant from a mutation tool(http://mutation-testing.org/). "java.class.path" value contains only libraries for the tool. The tool might delete the classpath that I added. But I'm not sure, so this is why I'm posting this question here.

Why is my Ant classpath ok in Eclipse but empty on Jenkins?

I am running my Ant build.xml file both locally and on a server running Jenkins.
Locally, inside Eclipse, the build works wonderfully. I set the classpath using:
<path id="classpath">
<fileset dir="${lib.dir}" includes="**/*.jar" />
</path>
and then I use the following when I run a target:
<javac srcdir="${src.dir}" destdir="${build.dir}" includeantruntime="false">
<classpath refid="classpath" />
</javac>
When I debug using echo the classpath shows all the available jars which are in my project/lib folder.
However, when I Jenkins fetches this build.xml file and runs it remotely, it prints an empty classpath (using the same echo target).
Why do my class paths differ based on Eclipse versus Jenkins?
Your build environment on you Jenkins server is going to look a bit different from your desktop dev env.
Sanity check: where/how is ${lib.dir} provided with a value?
Usually it is set with a property in the build file - can you maybe post that here also?

Classpath, Compile, and Run with Ant?

I'm completely new to Ant and need to add a couple jars to my classpath, compile a couple .java files, and run a junit test, all in Ant. I've been looking at a few online tutorials and manuals, but can't seem to wrap my head around the entire xml writing process.
All the previously-written code resides in a single directory called XXX.
In XXX there are two jars I need to add to my classpath with export CLASSPATH=$CLASSPATH:jar1:jar2, two java files I compile with javac *.java, one of which contains several junit tests that I run with java org.junit.runner.JUnitCore Tests. The build.xml would reside in XXX as well (I believe).
So far I have the following for just compiling, although I think there's a lot missing.
<?xml version="1.0"?>
<project name="EtlAutomation" default="compile" basedir=".">
<property name="src" value="${basedir}"/>
<target name="compile">
<!-- Compile .java files -->
<javac srcdir="${src}" destdir="${src}"/>
</target>
</project>
What else do I need to add to compile *.java in the current directory? How can I run the export CLASSPATH command, and finally the junit commend?
I'm not asking for anyone to write my code, but it would be appreciated. If anyone knows a good beginner tutorial for a unix environment, that would be awesome. I'm a total beginner with ant so I'll take what I can get.
Here is a previous question addressing this. And this may work for you:
<project name="EtlAutomation" default="compile" basedir=".">
<property name="src" value="${basedir}"/>
<path id="compile.classpath">
<fileset dir="./">
<include name="*.jar"/>
</fileset>
</path>
<target name="compile" >
<javac destdir="${src}" srcdir="${src}">
<classpath refid="compile.classpath"/>
</javac>
</target>
<target name="run" depends="compile">
<junit>
<classpath refid="compile.classpath" />
<test name="TestExample" />
</junit>
</target>
</project>

ant deploy problem

I am working on a spring project. I use ant to deploy application and STS (eclipse based) IDE to develop. I set the CATALINA_HOME environment variable
echo $CATALINA_HOME
/home/username/springsource/apache-tomcat
When I run the deploy ant task from IDE it deploys to a folder under
/home/username/workspace/myproject/${env.CATALINA_HOME}/webapp
but not
/home/username/springsource/apache-tomcat/webapp
Do you know any fix?
My build.properties file
src.dir=src
web.dir=web
build.dir=${web.dir}/WEB-INF/classes
name=myproject
appserver.home=${env.CATALINA_HOME}
deploy.path=${appserver.home}/webapps
appserver.lib=${appserver.home}/lib
and build.xml file
<?xml version="1.0" encoding="UTF-8"?>
<project name="kervan" basedir="." default="usage">
<property environment="env"/>
<property file="build.properties"/>
<path id="cp">
<fileset dir="${web.dir}/WEB-INF/lib">
<include name="*.jar"/>
</fileset>
<fileset dir="${appserver.lib}">
<include name="servlet-api.jar"/>
</fileset>
<pathelement path="${build.dir}"/>
</path>
<target name="usage">
<echo message=""/>
<echo message="${name} build file"/>
<echo message="-----------------------------------"/>
<echo message=""/>
<echo message="Available targets are:"/>
<echo message=""/>
<echo message="build --> Build the application"/>
<echo message="deploy --> Deploy application as a WAR file"/>
<echo message=""/>
</target>
<target name="build" description="Compile main source tree java files">
<mkdir dir="${build.dir}"/>
<javac destdir="${build.dir}" source="1.6" target="1.6"
debug="true" deprecation="false" optimize="false"
failonerror="true">
<src path="${src.dir}"/>
<classpath refid="cp"/>
</javac>
</target>
<target name="deploy" depends="build" description="Deploy application as a WAR file">
<war destfile="${name}.war"
webxml="${web.dir}/WEB-INF/web.xml">
<fileset dir="${web.dir}">
<include name="**/*.*"/>
</fileset>
</war>
<copy todir="${deploy.path}" overwrite="true">
<fileset dir=".">
<include name="*.war"/>
</fileset>
</copy>
</target>
</project>
Try putting the following after the two <property> lines:
<echo message="CATALINA_HOME=${env.CATALINA_HOME}" />
and see what it outputs. If it in fact outputs the correct value, then something strange may be happening. If it outputs the literal string
CATALINA_HOME=${env.CATALINA_HOME}
then somehow your ant script hasn't picked up the environment variable.
Note that when you set an environment variable for your system, only applications launched AFTER the variable is set will recognize the new variable. And variables set from the command line will only be recognized if the application being launched is being launched from that same command line session.
If you're running from within Eclipse or an Eclipse-like environment, Eclipse can be kind of weird in that depending on how you launch it, it's startup scripts won't make your environment natively available to your in-IDE Ant build process.
With my Eclipse-based Ant build, I had to manually set the environment. So for me, I right click on my project & go to "Properties". Then I click on the "Builders" section. I select my "Ant Builder" and click "Edit...". Under this section there's an "Environment" tab where you can specify environment variables and their corresponding values.
Even if you're not using Eclipse exactly like I was, poke around in the build properties and you should be able to find a way to specify environment variables and make them available to the build process.
Is CATALINA_HOME set in your environment?
e.g. Windows
echo %CATALINA_HOME%
Linux
echo $CATALINA_HOME
You could always hardcode the value in your properties file if it's not getting resolved correctly but provided it's in your environment then it should work.
The forum here discusses the same problem:
http://www.nabble.com/%3Cproperty-environment%3D%E2%80%9Denv%E2%80%9D%3E-doesn%27t-pick-up-an-environment-variable-td21481164.html
When run from eclipse, I don't believe the environment is passed to ant. You will have to specify each of the environment variables (and the values) that you want passed to ant in the configuration of the build file within eclipse.
if you are set your environmental variable in global
/etc/environment
thats the problem in Ubuntu. Ant does not pick the environment variable from here.
But the echo $CATALINA_HOME works fine in terminal. I am facing the same problem.
set your environment in .bashrc may fix your problem.
I recently suffered a similar issue.
The problem was in the CATALINA_HOME environment variable: I needed to close the path with a backslash ("/"):
$ export CATALINA_HOME=/home/username/springsource/apache-tomcat/
After fixing that I could deploy the application with ant.
Please make sure you end your path with a / and it shall solve your problem.
example: export JAVA_HOME=/opt/java/
instead of: export JAVA_HOME=/opt/java

Categories

Resources