Jenkins LTS Installation, Java 21/25 Runtime Planning, Packages, Containers, and Initial Setup: Guided Hands-On Workflow and Core Operations
Install Jenkins 2.568.3 LTS in a disposable local container, compare native package ownership, capture version/runtime/image/storage evidence, and prove persistent state across replacement.
Learning objectives
- Compare a host-package installation with an official-container installation without mixing their state ownership models.
- Preflight Java, Docker, port availability, storage, and network binding before launching a controller.
- Run Jenkins 2.568.3 LTS locally with persistent storage and collect version/runtime/image evidence.
- Complete the setup wizard without retaining the initial admin password and capture the installed plugin baseline safely.
- Replace the controller container and prove that the named volume preserves configured state.
1. Lab scenario and safety boundary
You are creating a disposable training controller named
jenkins-ch02-controller. It must be reachable only from
the local machine on port 8080, store state in a named volume called
jenkins-ch02-home, run the official Jenkins 2.568.3 LTS
Java 21 image, and survive container deletion/recreation.
2. First compare the two common installation ownership models
| Concern | Native package | Official container |
|---|---|---|
| Jenkins bytes | Package repository/version installed on host | Image tag plus resolved digest |
| Java | Host Java installation | Java included in selected Jenkins image variant |
| Service lifecycle | systemd / Windows Service | Container runtime |
| Persistent home | Host directory, commonly package-defined |
Explicit volume/bind mount to /var/jenkins_home
|
| Upgrade action | Package upgrade with host/service considerations | Pull/test new image then replace container against same validated home copy |
| Rollback | Package/version + data compatibility plan | Previous image is easy; data rollback is not automatically safe |
| Best lab fit | Changes host package/service state | Easy disposal; clearer separation of process vs data |
3. Native-package path: inspect before you install
On Debian/Ubuntu, current Jenkins documentation recommends
installing Java first, adding the stable Jenkins repository, then
installing the jenkins package. These commands are
shown for understanding; the mandatory lab continues with Docker so
it does not alter your host package database.
java -version
# Current official Debian/Ubuntu baseline uses OpenJDK 21.
sudo apt update
sudo apt install fontconfig openjdk-21-jre
# Stable Jenkins repository key and source (re-check before use):
sudo wget -O /etc/apt/keyrings/jenkins-keyring.asc \
https://pkg.jenkins.io/debian-stable/jenkins.io-2026.key
echo "deb [signed-by=/etc/apt/keyrings/jenkins-keyring.asc] https://pkg.jenkins.io/debian-stable binary/" | \
sudo tee /etc/apt/sources.list.d/jenkins.list >/dev/null
sudo apt update
apt-cache policy jenkins
Notice the final command: inspect the candidate version before mutating the host. If you later install the package, also record the systemd service user, home directory, listener configuration, and package version.
4. Container-lab preflight: prove prerequisites before launch
docker version
docker info --format 'Server={{.ServerVersion}} OS={{.OperatingSystem}}'
# Port 8080 should not already be owned by another service.
# PowerShell: Get-NetTCPConnection -LocalPort 8080 -ErrorAction SilentlyContinue
# Linux: ss -ltnp | grep ':8080 ' || true
docker pull jenkins/jenkins:2.568.3-jdk21
docker image inspect jenkins/jenkins:2.568.3-jdk21 \
--format 'Id={{.Id}} RepoDigests={{json .RepoDigests}}'
docker run --rm jenkins/jenkins:2.568.3-jdk21 java -version
RepoDigests is
recorded, and the container reports Java 21. Stop here if any
prerequisite is not true.
5. Create persistent state and start the controller safely
docker volume create jenkins-ch02-home
docker run --name jenkins-ch02-controller --detach \
--publish 127.0.0.1:8080:8080 \
--volume jenkins-ch02-home:/var/jenkins_home \
jenkins/jenkins:2.568.3-jdk21
docker ps --filter name=jenkins-ch02-controller
docker inspect jenkins-ch02-controller \
--format 'Image={{.Image}} User={{.Config.User}} Mounts={{json .Mounts}} Ports={{json .HostConfig.PortBindings}}'
Do not publish port 50000 for this chapter. Later agent lessons can choose inbound/WebSocket/SSH connectivity deliberately. Opening extra ports “because tutorials do” obscures the network boundary.
6. Read startup evidence before opening the UI
docker logs --tail 120 jenkins-ch02-controller
# Confirm the controller responds locally.
curl -I http://127.0.0.1:8080/login
Startup logs should show normal initialization and the one-time unlock instructions. Do not copy the generated password into retained logs, issue trackers, screenshots, or course evidence. If you need the password, obtain it directly from the local container and paste it only into the local setup form:
docker exec jenkins-ch02-controller \
cat /var/jenkins_home/secrets/initialAdminPassword
7. Complete the setup wizard without turning it into an unreviewed plugin baseline
- Browse to
http://127.0.0.1:8080. - Enter the locally retrieved unlock value.
- For this beginner lab, choose Install suggested plugins. This is convenience, not a fixed production baseline.
- Create a disposable administrator account with a unique lab password. Do not reuse a real password.
- Keep the Jenkins URL local for this exercise.
After setup, go to Manage Jenkins → Plugins → Installed plugins and record plugin names and versions in your notes. The exact suggested set evolves, so the evidence packet records what was actually installed rather than pretending the recommendation is immutable.
8. Verify controller identity and state after setup
docker exec jenkins-ch02-controller java -version
docker inspect jenkins-ch02-controller --format 'Image={{.Image}}'
docker volume inspect jenkins-ch02-home
curl -s -D - -o /dev/null http://127.0.0.1:8080/login | head
In the Jenkins UI, record the exact Jenkins version shown in system/about information; expected 2.568.3.
Record Java 21 from inside the controller container.
Record image ID and pulled RepoDigest.
Record named volume and mount to /var/jenkins_home.
Record host binding 127.0.0.1:8080 only.
Record installed plugin names/versions, not credentials or configuration secrets.
9. The proof: replace the process, keep the state
# Stop and remove only the lab container. Keep the named volume.
docker stop jenkins-ch02-controller
docker rm jenkins-ch02-controller
# Recreate a new container using the same exact image tag and volume.
docker run --name jenkins-ch02-controller --detach \
--publish 127.0.0.1:8080:8080 \
--volume jenkins-ch02-home:/var/jenkins_home \
jenkins/jenkins:2.568.3-jdk21
docker logs --tail 80 jenkins-ch02-controller
Reload the UI. Your administrator and completed setup state should still exist because they were stored in the named volume. This is the chapter’s central before/after observation: container identity changed, durable controller state did not.
10. Challenge: choose the failed layer
Suppose a teammate reports “Jenkins disappeared after I upgraded the container.” You inspect Docker and find a brand-new container using the right image, but it was started without the old volume. Which layer failed?
The Jenkins core and Java runtime may be perfectly healthy. The failure is persistent-state attachment. The least destructive correction is to stop the new disposable container and reattach the known correct home volume—after verifying its identity—rather than reinstalling plugins or recreating users.
11. Cleanup options
# Keep the lab for Lesson 3/4 if you want continuity.
# Otherwise remove the container first:
docker stop jenkins-ch02-controller
docker rm jenkins-ch02-controller
# Destructive: remove ONLY the known disposable training volume when you no longer need the state.
docker volume rm jenkins-ch02-home
jenkins-ch02-home before removal. Never substitute an
ambiguous “latest” volume or wildcard.
12. Summary
- Preflight Java/runtime, port, storage, and distribution identity before launch.
- The mandatory lab uses a loopback-only Jenkins 2.568.3/JDK21 controller with an explicit named home volume.
- Setup credentials stay local; retained evidence records versions and state, not passwords.
- Plugin recommendations are not a frozen bill of materials—capture the versions actually installed.
- Container replacement proves process ephemerality and volume persistence independently.
Knowledge check
Why inspect RepoDigests immediately after pulling
the Jenkins image?
It records the immutable registry content identity resolved for the human-readable tag, improving reproducibility and auditability.
What should remain after
docker rm jenkins-ch02-controller if persistence
was configured correctly?
The named volume jenkins-ch02-home and its
controller state should remain until explicitly deleted.
Why is “Install suggested plugins” not a reproducible plugin baseline by itself?
The suggested set and plugin versions evolve. Record the exact installed plugin inventory after setup.
Why does the lab publish
127.0.0.1:8080:8080 instead of
8080:8080?
Loopback binding limits access to the host during the bootstrap exercise, reducing unintended network exposure.
A recreated container shows the setup wizard again. What should you inspect before reconfiguring anything?
Inspect whether the correct JENKINS_HOME volume was
attached and whether it contains the expected prior state. Do
not overwrite or reinitialize first.
Official references and version notes
- Installing Jenkins — official entry point for supported installation methods and new-installation scope.
-
Docker installation
— official Jenkins container image, persistent
/var/jenkins_home, ports, and setup-wizard workflow. - Linux installation — current Debian/Ubuntu, Fedora, and RHEL-family package instructions and service management.
- Windows installation — MSI/service-account guidance, Java selection, port configuration, and setup.
-
WAR-file installation
— standalone Java launch, port selection, and
JENKINS_HOMEoverride. - Java Support Policy — authoritative controller/agent/CLI Java runtime matrix.
- Jenkins LTS changelog — exact LTS release dates, fixes, and tested JDKs.
- Jenkins LTS Upgrade Guide — mandatory reading before upgrades or skipped LTS lines.
- Jenkins Security Advisories — current core/plugin security fixes and affected versions.
Version-sensitive statements in this lesson were rechecked on
2026-09-14. The lab baseline is
Jenkins 2.568.3 LTS on Java 21;
Jenkins 2.568.3 is also tested with Java 25. Current Jenkins LTS
releases in this line require Java 21 or 25. The disposable
container examples pin the human-readable image tag
jenkins/jenkins:2.568.3-jdk21 and require learners to
record the locally resolved RepoDigest after pulling
it. Re-check the LTS changelog, Java policy, image tags/digests,
package signing key, and security advisories when regenerating
this lesson.
Keep the academy open
Support free, practical DevOps education.
Every lesson is designed to remain readable in a browser, downloadable from GitHub, and usable without a paid learning platform. Contributions help expand and maintain the curriculum.
0x716c4Ab160C4B66F31a28AE2448BfF68fc3a2ef0Send only Ethereum/ERC-20 compatible assets to this
address.