Java application
You can build and test a Java application using a Linux platform on Harness Cloud or a self-hosted Kubernetes cluster build infrastructure.
This guide assumes you've created a Harness CI pipeline. For more information about creating pipelines, go to:
If you don't have a Harness account yet, you can create one for free at app.harness.io.
Install dependencies
Use Run step to install dependencies in the build environment.
- step:
type: Run
name: build
identifier: build
spec:
connectorRef: account.harnessImage
image: maven:3.8-jdk-11
shell: Sh
command: |-
mvn clean package dependency:copy-dependencies
- step:
type: Run
name: check dependencies
identifier: check_dependencies
spec:
connectorRef: account.harnessImage
image: maven:3.8-jdk-11
shell: Sh
command: |-
mvn dependency-check:check -U -DskipTests
reports:
type: JUnit
spec:
paths:
- /harness/target/*.xml
In addition to Run steps, Plugin steps are also useful for installing dependencies.
You can use Background steps to run dependent services that are needed by multiple steps in the same stage.
Cache dependencies
- Harness Cloud
- Self-hosted
Cache your Java dependencies with Cache Intelligence. Add caching.enabled.true
to your stage.spec
.
- stage:
spec:
caching:
enabled: true
With self-hosted build infrastructures, you can:
If you're using Maven, you must reference pom.xml
in the key
value for your Save Cache and Restore Cache steps, for example:
spec:
key: cache-{{ checksum "pom.xml" }}
Additionally, you must include /root/.m2
in the sourcePaths
for your Save Cache step, for example:
spec:
sourcePaths:
- /root/.m2
Here's an example of a pipeline with Save Cache to S3 and Restore Cache from S3 steps.
steps:
- step:
type: RestoreCacheS3
name: Restore Cache From S3
identifier: Restore_Cache_From_S3
spec:
connectorRef: AWS_Connector
region: us-east-1
bucket: your-s3-bucket
key: cache-{{ checksum "pom.xml" }}
archiveFormat: Tar
- step:
type: Run
...
- step:
type: BuildAndPushDockerRegistry
...
- step:
type: SaveCacheS3
name: Save Cache to S3
identifier: Save_Cache_to_S3
spec:
connectorRef: AWS_Connector
region: us-east-1
bucket: your-s3-bucket
key: cache-{{ checksum "pom.xml" }}
sourcePaths:
- /root/.m2
archiveFormat: Tar
Build and run tests
- Harness cloud
- Self-hosted
You can use Run or Run Tests steps to run tests in CI pipelines.
- Run step
- Run Tests step (Test Intelligence)
This example uses two Run steps to build and test with Maven.
- step:
type: Run
name: build
identifier: build
spec:
shell: Sh
command: |
mvn clean package dependency:copy-dependencies
- step:
type: Run
name: run test
identifier: run_test
spec:
shell: Sh
command: |-
mvn test
reports:
type: JUnit
spec:
paths:
- target/surefire-reports/*.xml
You must use the Run Tests step for your unit tests if you want to leverage Harness' Test Intelligence feature.
Where Run steps use the command
field for all commands, the Run Tests step uses preCommand
, args
, and postCommand
to set up the environment before testing, pass arguments for the test tool, and run any post-test commands. For example, you could declare dependencies or install test tools in preCommand
.
The following example runs mvn test
(declared in args
), and then runs mvn package -DskipTests
as a postCommand
.
- step:
type: RunTests
name: Run Tests
identifier: Run_Tests
spec:
language: Java
buildTool: Maven
args: test
packages: io.harness.
runOnlySelectedTests: true
postCommand: mvn package -DskipTests
reports:
type: JUnit
spec:
paths:
- "target/surefire-reports/*.xml"
You can use Run or Run Tests steps to run tests in CI pipelines.
- Run step
- Run Tests step (Test Intelligence)
This example uses two Run steps to build and test with Maven.
- step:
type: Run
name: build
identifier: build
spec:
connectorRef: account.harnessImage
image: maven:3.8-jdk-11
shell: Sh
command: |
mvn clean package dependency:copy-dependencies
- step:
type: Run
name: run test
identifier: run_test
spec:
shell: Sh
command: |-
mvn test
reports:
type: JUnit
spec:
paths:
- target/surefire-reports/*.xml
You must use the Run Tests step for your unit tests if you want to leverage Harness' Test Intelligence feature.
Where Run steps use the command
field for all commands, the Run Tests step uses preCommand
, args
, and postCommand
to set up the environment before testing, pass arguments for the test tool, and run any post-test commands. For example, you could declare dependencies or install test tools in preCommand
.
The following example runs mvn test
(declared in args
), and then runs mvn package -DskipTests
as a postCommand
.
- step:
type: RunTests
name: Run Tests
identifier: Run_Tests
spec:
connectorRef: account.harnessImage
image: maven:3.8-jdk-11
language: Java
buildTool: Maven
args: test
packages: io.harness.
runOnlySelectedTests: true
postCommand: mvn package -DskipTests
reports:
type: JUnit
spec:
paths:
- "target/surefire-reports/*.xml"
Visualize test results
If you want to view test results in Harness, make sure your test commands produce reports in JUnit XML format and that your steps include the reports
specification.
reports:
type: JUnit
spec:
paths:
- target/surefire-reports/*.xml
Specify version
- Harness Cloud
- Self-hosted
Java is pre-installed on Hosted Cloud runners. For details about all available tools and versions, go to Platforms and image specifications.
If your application requires a specific version of Java, you can use a Run or Plugin step to install it.
This example uses the GitHub Action plugin step to run the setup-java
action.
- step:
type: Action
name: setup java
identifier: setup_java
spec:
uses: actions/setup-java@v3
with:
distribution: 'temurin'
java-version: '16'
You can use a Run or Plugin step to install Java versions that are not already installed on your host machine.
This example uses the Plugin step to run the GitHub Actions Drone plugin and run the setup-java
action.
- step:
identifier: setup_java
name: setup java
type: Plugin
spec:
connectorRef: account.harnessImage
image: plugins/github-actions
privileged: true
settings:
uses: actions/setup-java@v3
with:
distribution: 'temurin'
java-version: '17'
Full pipeline examples
Here's a YAML example of a pipeline that:
- Tests a Java code repo.
- Builds and pushes an image to Docker Hub.
This pipeline uses Harness Cloud build infrastructure, Cache Intelligence, and Test Intelligence.
If you copy this example, replace the placeholder values with appropriate values for your Harness project, connector IDs, account/user names, and repo names.
Pipeline YAML
pipeline:
name: Build java
identifier: Build_java
projectIdentifier: default
orgIdentifier: default
properties:
ci:
codebase:
connectorRef: YOUR_CODE_REPO_CONNECTOR_ID
repoName: YOUR_REPO_NAME
build: <+input>
stages:
- stage:
name: Build
identifier: Build
description: ""
type: CI
spec:
caching:
enabled: true
cloneCodebase: true
platform:
os: Linux
arch: Amd64
runtime:
type: Cloud
spec: {}
execution:
steps:
- step:
type: RunTests
name: RunTests_1
identifier: RunTests_1
spec:
language: Java
buildTool: Maven
args: test
packages: io.harness
runOnlySelectedTests: true
postCommand: mvn package -DskipTests
reports:
type: JUnit
spec:
paths:
- "target/surefire-reports/*.xml"
- step:
type: BuildAndPushDockerRegistry
name: BuildAndPushDockerRegistry_1
identifier: BuildAndPushDockerRegistry_1
spec:
connectorRef: YOUR_DOCKER_CONNECTOR_ID
repo: YOUR_DOCKER_HUB_USERNAME/DOCKER_REPO_NAME
tags:
- <+pipeline.sequenceId>
Next steps
Now that you have created a pipeline that builds and tests a Java app, you could:
- Create triggers to automatically run your pipeline.
- Add steps to build and upload artifacts.
- Add a step to build and push an image to a Docker registry.
- Explore other ways to optimize and enhance CI pipelines.