Mastering GitLab CI/CD Pipeline Fundamentals: GitLab CI/CD Pipeline for Spring Boot 🚀 | Maven Deploy Job | JFrog Artifactory Integration
This chapter covers the integration of a Maven Deploy job into an existing GitLab CI/CD pipeline for a Spring Boot application. You will learn how to transition from local builds to automated pipeline deployments, configure Maven distribution management, securely mount settings.xml authentication templates on self-hosted runners, and publish build artifacts directly to a remote JFrog Artifactory repository.
1. Why Do We Need Automated Artifact Publishing?
In previous chapters, our GitLab CI/CD pipeline successfully handled building (mvn clean compile) and testing (mvn test) our Spring Boot application. However, leaving compiled artifacts trapped inside temporary runner build directories creates several operational bottlenecks:
- Manual Bottlenecks: Developers waste time manually packaging JAR/WAR files and uploading them to artifact repositories.
- Lack of Version Control & Traceability: Without a centralized artifact repository, tracking which commit generated which build version becomes impossible.
- Downstream Dependency Failures: Other microservices or deployment pipelines cannot consume our shared libraries or service packages without a reliable, automated publishing mechanism.
By adding a dedicated Maven Deploy job, every successful pipeline run automatically compiles, packages, and pushes our release or snapshot artifacts to a remote artifact manager like JFrog Artifactory.
2. Core Mental Model: The Pipeline-to-Artifact Architecture
To understand how GitLab CI/CD pushes artifacts to JFrog Artifactory, examine the underlying workflow between the self-hosted runner, local Maven configurations, and the remote repository:
3. Prerequisites & Architectural Setup
Before writing a single line of GitLab CI/CD YAML configuration for the deployment job, two foundational prerequisites must be satisfied:
- Active JFrog Artifactory Instance: A reachable JFrog Artifactory server must be up and running, with dedicated repositories created for snapshots and releases. (Refer to dedicated infrastructure setup guides for installation steps).
- Maven
pom.xmlDistribution Management: Your project'spom.xmlmust declare where Maven should ship artifacts.
Configuring pom.xml Distribution Management
Open your project's root pom.xml and ensure the <distributionManagement> block points to your JFrog Artifactory repository URLs and unique repository IDs:
<distributionManagement>
<snapshotRepository>
<id>central-snapshots</id>
<name>Central Snapshot Repository</name>
<url>http://<YOUR_JFROG_SERVER_IP>:8081/artifactory/libs-snapshot-local</url>
</snapshotRepository>
<repository>
<id>central-releases</id>
<name>Central Release Repository</name>
<url>http://<YOUR_JFROG_SERVER_IP>:8081/artifactory/libs-release-local</url>
</repository>
</distributionManagement>
Note: The IDs (
central-snapshotsandcentral-releases) defined insidepom.xmlact as binding keys that connect to authentication credentials stored securely inside Maven'ssettings.xmlfile.
4. Local vs. Pipeline Execution: The settings.xml Challenge
When running mvn deploy locally on your development machine, Maven looks for credentials inside your user profile's .m2 directory (~/.m2/settings.xml).
However, in a GitLab CI/CD pipeline running on a Self-Hosted Runner, the execution environment depends entirely on the user account that launches the runner daemon.
Identifying Runner User Context & Home Directory
- Connect via SSH to your self-hosted GitLab runner machine.
- Verify your current working directory and user identity:
BASH
pwd # Output: /home/ubuntu (Assuming the runner executes under the 'ubuntu' user) whoami # Output: ubuntu - Locate or create the Maven configuration directory inside the runner user's home directory:
BASH
cd ~ mkdir -p .m2 cd .m2
5. Configuring Maven Credentials on the Self-Hosted Runner
To grant the pipeline permission to upload artifacts to JFrog Artifactory, you must place an authenticated settings.xml file directly inside the .m2 directory of the runner's execution user.
Step-by-Step Configuration on the Runner Host
-
Open or create the
settings.xmlfile using your preferred text editor (e.g.,nano settings.xml):BASHnano settings.xml -
Populate the file with your JFrog Artifactory credentials matching the
<id>tags declared in yourpom.xml:
<settings xmlns="http://maven.apache.org/SETTINGS/1.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/SETTINGS/1.0.0
http://maven.apache.org/xsd/settings-1.0.0.xsd">
<servers>
<server>
<id>central-snapshots</id>
<username>admin</username>
<password>your_jfrog_secure_password</password>
</server>
<server>
<id>central-releases</id>
<username>admin</username>
<password>your_jfrog_secure_password</password>
</server>
</servers>
</settings>
- Save and close the file (
Ctrl + O,Enter, thenCtrl + Xin nano). - Verify the file placement:
BASH
ls -la ~/.m2/ # Expected output should show settings.xml present alongside your repository cache folder.
6. Updating .gitlab-ci.yml with the Maven Deploy Job
With the runner pre-configured with JFrog credentials and pom.xml pointing to our distribution targets, we can now update .gitlab-ci.yml to append a new publish stage and a maven-deploy job.
Pipeline Configuration Evolution
Below is the updated GitLab CI/CD pipeline script incorporating the deployment stage:
stages:
- build
- test
- publish
maven-build:
stage: build
script:
- mvn clean compile
tags:
- spring-runner
maven-test:
stage: test
script:
- mvn test
tags:
- spring-runner
maven-deploy:
stage: publish
script:
- mvn clean deploy -DskipTests
tags:
- spring-runner
Key Parameters Explained:
stage: publish: Declares a brand new sequential pipeline stage executing after tests pass.mvn clean deploy -DskipTests: Cleans previous target directories, packages the Spring Boot application, and deploys the resulting artifact directly to the remote repository without running tests a second time.tags: [spring-runner]: Directs GitLab to execute this job strictly on our self-hosted runner wheresettings.xmlis pre-configured.
7. Pipeline Execution & Real-World Verification
Once you commit and push the updated .gitlab-ci.yml file to your GitLab repository, the pipeline triggers automatically.
Step-by-Step Execution Flow
Verifying Logs in GitLab CI/CD
When you inspect the job logs for maven-deploy, look for successful upload indicators:
[INFO] Uploading to central-snapshots: http://<JFROG_IP>:8081/artifactory/libs-snapshot-local/com/example/demo/0.0.1-SNAPSHOT/demo-0.0.1-20231025.120000-1.jar
[INFO] Uploaded to central-snapshots: http://<JFROG_IP>:8081/artifactory/libs-snapshot-local/... (25 KB at 1200 KB/s)
[INFO] BUILD SUCCESS
8. Verifying Artifacts Inside JFrog Artifactory
To confirm everything landed correctly on the remote artifact manager:
- Open your browser and navigate to your JFrog Artifactory Web UI:
http://<YOUR_JFROG_SERVER_IP>:8081/artifactory/ - Log in using your administrator credentials.
- Navigate to Artifacts -> Tree Browse.
- Locate your repository (
libs-snapshot-localorlibs-release-local). - Verify that your group ID, artifact ID, version folder (e.g.,
0.0.1-SNAPSHOT), and packaged.jarfiles appear exactly as expected.
Summary and Key Takeaways
- Automated Publishing: Integrating a
maven-deployjob eliminates manual artifact handling, ensuring every successful pipeline run pushes production-ready packages directly to an artifact repository. - Prerequisite Harmony: Successful deployment requires a pre-configured JFrog Artifactory server and accurate
<distributionManagement>definitions inside your project'spom.xml. - Runner-Level Authentication: Self-hosted GitLab runners execute pipelines under specific OS user accounts (e.g.,
ubuntu); therefore, Maven credentials must be placed inside that specific user's~/.m2/settings.xmlfile. - Secure Server Mappings: Maven
settings.xmllinks repository IDs defined inpom.xml(central-snapshots,central-releases) with secure plaintext or encrypted administrator credentials. - Optimized CI Commands: Utilizing flags like
-DskipTestsinside the pipeline deploy job prevents redundant test execution since unit tests already completed successfully in earlier pipeline stages. - Traceability & Management: Centralizing artifacts in JFrog Artifactory empowers downstream services, continuous deployment pipelines, and team members to consume exact, version-controlled build outputs reliably.