Hosting a ReactJS App on Oracle Kubernetes Engine with Travis and GitHub

Introduction

This article demonstrates steps required to host a NodeJS application to Oracle Kubernetes Engine (OKE) using Travis Continuous Integration Server. Travis CI is very tightly coupled with GitHub so any public repository created by you will be visible automatically in Travis. This articles gives the basic steps required to get started on OKE with Travis.

Prerequisite

  1. You should have account in Oracle Cloud Infrastructure (OCI) and should have access to Developer Services like Oracle Container Registry (OCIR) and Oracle Kubernetes Engine (OKE). Get an account from https://www.oracle.com/index.html if you don’t have one.
  2. You should have an OKE cluster configured and running (https://www.oracle.com/webfolder/technetwork/tutorials/obe/oci/oke-full/index.html)
  3. You should have OCI CLI installed (https://oracle.github.io/learning-library/oci-library/DevOps/OCI_CLI/OCI_CLI_HOL.html)
  4. You should have an account in GitHub (https://github.com/)
  5. You should have registered on Travis (http://travis-ci.org/)
  6. JavaScript runtime environment Node.js is installed in your development environment (https://nodejs.org/en/)

Pipeline Overview

Any check-in in the GitHub project code will trigger an automated build in Travis which will create the project image and push it to the OCIR. In the deployment step of the build, the image will be pulled from OCIR and deployment to OKE.

Pipeline Overview

Bootstrap the ReactJS project

Bootstrap ReactJS sample-travis-oke project.

$ npx create-react-app sample-travis-oke
$ cd sample-travis-oke
# Change src/App.js for any custom message
# Run optimized build

$ npm run build
$ npm install -g serve

# ReactJS Apps can be hosted by Nginx or lightweight "serve" Application. For this tutorial we will be using nginx server but to check the created application you can run "serve" command below to verify the application.
$ serve -s build

Containerize the Project

Project will be containerized along with following additional tools:

  • kubectl command
FROM oraclelinux:7-slim as builder
ARG NPM_REGISTRY
ARG HTTP_PROXY
ARG COMPARTMENT_ID
WORKDIR '/app'
COPY package.json .
# optional line below
COPY ol7_developer_nodejs8.repo /etc/yum.repos.d/
RUN echo proxy=${HTTP_PROXY} >>/etc/yum.conf
RUN yum -y update && \
rm -rf /var/cache/yum && \
yum -y install nodejs
RUN yum -y install python3
RUN npm config set registry ${NPM_REGISTRY}
RUN npm install
COPY . .
RUN npm run build
RUN curl -LO https://storage.googleapis.com/kubernetes-release/release/v1.16.0/bin/linux/amd64/kubectl \
&& chmod +x ./kubectl \
&& rm -rf /tmp/*
ENV PATH="/app:/bin:/root/bin:${PATH}"
ENV KUBECONFIG="/root/.kube/oci_config"
ENV LC_ALL="en_US.utf8"
ENV C ${COMPARTMENT_ID}
RUN curl -LO https://raw.githubusercontent.com/oracle/oci-cli/master/scripts/install/install.sh \
&& chmod +x ./install.sh \
&& ./install.sh --accept-all-defaults
EXPOSE 5000
ENTRYPOINT ["/bin/bash"]
CMD []
#create the docker image
$ docker build --build-arg http_proxy=<proxy> --build-arg NPM_REGISTRY="https://registry.npmjs.org/" --build-arg COMPARTMENT_ID="$COMPARTMENT_ID" -t sample-travis-oke:travis
#Run the container
$ docker run -v "<local_oci_config_path>/.oci":"/root/.oci" -v "<local_kube_config_path>/.kube":"/root/.kube" -p 5000:3000 sample-travis-oke:travis /bin/serve -s build

Push to GitHub

This step is required to integrate the project with Travis CI. Create the project repository “sample-travis-oke” in GitHub and push the existing code this repository.

$ cd sample-travis-oke
$ git init
$ git remote add origin https://github.com/<your_account>/sample-travis-oke.git
$ git add .
$ git commit -m "First Commit"
$ git push origin master

Setup Travis CI

Lets setup Continuous Integration in CI for this project. Here is what we require from Travis:

  1. Build should create the Docker image and push the Docker image to OCI container registry (OCIR).
  2. Pull the image from OCIR and push to OCI OKE (Oracle Kubernetes Engine)
Webhoook configuration on GitHub
Project settings page in Travis
language: generic
sudo: required
services:
- docker
before_install:
- docker build --build-arg NPM_REGISTRY=${NPM_REGISTRY} --build-arg COMPARTMENT_ID=$C
-t ${OCIR_URL}/sample-travis-oke:travis .
- docker login ${OCIR_URL} -p ${OCIR_PASSWORD} -u ${OCIR_USER}
- docker push ${OCIR_URL}/sample-travis-oke:travis
script:
- docker run ${OCIR_URL}/sample-travis-oke:travis -c /bin/serve -s build
deploy:
- kubectl cluster-info
- kubectl apply -f k8s
- kubectl get pods
- kubectl get services
$ sudo gem install travis
$ tar cvf secrets.tar .oci/* .kube/*
$ travis encrypt-file secrets.tar --add
Encryption Keys Settings

Configure OKE Deployment

Create pod creation and service creation files for the project for OKE. These are just like any other Kubernetes files and there is nothing OKE specific here. However, make sure that you have OCI config setup, your private key setup or authentication token and Kubernetes config setup for OKE. Steps to do that are already given above . Sample Kubernetes files for this project will like below:

apiVersion: v1
kind: Pod
metadata:
name: app-oci-oke-pod
labels:
component: web
spec:
containers:
- name: app-oci-oke
image: [OCIR_URL]/sample-travis-oke:travis
command: ["/bin/serve -s build"]
ports:
- containerPort: 5000
------------------------------------
apiVersion: v1
kind: Service
metadata:
name: oci-oke-app-service
spec:
type: LoadBalancer
selector:
component: web
ports:
- port: 3000
targetPort: 5000

Deploy on OKE

As part of the Deploy step of Travis build, following steps are executed within the container:

kubectl cluster-info
kubectl apply -f k8s
kubectl get pods
kubectl get services
NAME                  TYPE           CLUSTER-IP      EXTERNAL-IP     PORT(S)    AGE
oci-oke-app-service LoadBalancer 1x.x.x4.x 1x.x.x.198 3000:31305/TCP 110m
Running Application on OKE

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store