DEV Community

Cover image for CI/CD pipeline using Jenkins and Docker
pankaj892
pankaj892

Posted on

CI/CD pipeline using Jenkins and Docker

Today we will be creating a CI/CD pipeline in Jenkins which fetches code from github and creates an image from Dockerfile and runs our app in a docker container and terminates automatically after scheduled time

1. Creating EC2 instances

I have used AWS EC2 to launch an ubuntu instance which comes under free tier you can try it on your local machine or use a VM from any public cloud provider

EC2 Instance Image

Now connect to the instance

2. Setting up Jenkins & Docker

We need to update our installation package manager

$ sudo apt update
Enter fullscreen mode Exit fullscreen mode

Jenkins needs java to run so we'll proceed with installing Java first

$ sudo apt install openjdk-11-jre
Enter fullscreen mode Exit fullscreen mode

Check if java is installed correctly
Check java

Now we download Jenkins using curl command

$ curl -fsSL https://pkg.jenkins.io/debian/jenkins.io.key | sudo tee \   /usr/share/keyrings/jenkins-keyring.asc > /dev/null
Enter fullscreen mode Exit fullscreen mode

We add it to our package manager

$ echo deb [signed-by=/usr/share/keyrings/jenkins-keyring.asc] \   https://pkg.jenkins.io/debian binary/ | sudo tee \   /etc/apt/sources.list.d/jenkins.list > /dev/null
Enter fullscreen mode Exit fullscreen mode

Lets update our package manager once

$ sudo apt-get update
Enter fullscreen mode Exit fullscreen mode

Now install jenkins

$ sudo apt-get install jenkins
Enter fullscreen mode Exit fullscreen mode

Before we can use jenkins we need to enable it first

$ sudo systemctl enable jenkins
Enter fullscreen mode Exit fullscreen mode

Start jenkins server

$ sudo systemctl start jenkins
Enter fullscreen mode Exit fullscreen mode

Check status of jenkins

$ sudo systemctl status jenkins
Enter fullscreen mode Exit fullscreen mode

You would get a response like this
jenkins status

Jenkins runs on port 8080 by default go to localhost:8080 to access it.
Since I have a VM provisioned in the cloud I need to open port 8080 to allow connections
I went to Network security groups and added the port number I want to access.

NSG in AWS

Since I don't want everyone to able to access jenkins I have limited the port to only a single host

Now when I login to port 8080 I am greeted with a login screen of jenkins

Jenkins login

Now to login we need credentials
Username is admin
password can be found through the following command

$ sudo cat /var/lib/jenkins/secrets/initialAdminPassword
Enter fullscreen mode Exit fullscreen mode

After logging into jenkins change your password and jenkins would ask to install plugins let it install them

Now we are greeted with a screen like this click on new item
Jenkins Dashboard

Since I plan to keep it simple click on freestyle project
Setting up

After adding the name for you app add your github repo you want to connect
Git repo adding

After adding a repo we need to tell jenkins how to access the repo and give it required permission so it can fetch the code from repo
To achieve this I have used SSH keys simple generate a ssh key and add the public key in github

Credentials for Github

Now we need to add private key in jenkins so that it can authenticate with github and pull code from our repo.
Click on add below credentials and choose Jenkins

SSH Private key adding image

Give a name to you credential and add the private key
Naming credential

Before we move to next step install a plugin called Github Integration available in Jenkins you can do this by going to manage jenkins and selecting plugins and search for the extension

Now add the steps to build the app and run it. Since our app runs on node.js I will be using a docker container. I have created a Dockerfile
to do this.
I am using shell scripting to run the container in a shell and exit it
Shell Script

The commands in above image do the following things:

  • Build the docker image
  • Run the app in a container on port 8000
  • The app will be live for 5 minutes
  • After that the container is stopped and removed from the machine

The Build ID with a $ is an environment variable which changes according to build of jenkins so we get a new container on every run and there won't be any problems as we won't be running same container everytime

Click Save when done

We need docker to run the app if you don't have install it on your machine

$ sudo apt install docker.io 
Enter fullscreen mode Exit fullscreen mode

We also need a Dockerfile
You can find it on my repository here

Dockerfile does the following:

  • It pulls the latest node image from DockerHub
  • The work directory is set as app
  • It runs npm install and all libraries and packages are downloaded
  • It exposes port 8000 for our app
  • It runs the command node app.js in a shell

Lets move on to next stage

3. Configuring Github

We need to make sure that when a change is detected in our repo jenkins runs the pipeline automatically we use webhooks to achieve this

Go to Settings > Webhooks for your repo not your account
Webhook Tab

Now add url of your jenkins where it is hosted followed by /github-webhook/ and click on save
Webhook details

4. Testing our app

Now lets do a dry run and see if our pipeline works as expected

Click on build now to run the pipeline
Dry Run

Build has started
Pipeline status

I expect the container name to end with build number let's check
Container name checking
It is working as expected

And pipeline is successful since we can see our app
Pipeline success

Now lets change something in repo and see if jenkins picks it up and runs the pipeline
I changed the background and some text

Pipeline with changes
It is working as expected

We have completed this project successfully

If you have any questions comment down below I'll be happy to help

Top comments (0)