Chapter 8. Deploying an Application on OpenShift
This section describes how to use OpenShift to create containerized applications and deploy them on an OpenShift cluster. The examples in this section use only basic features of the OpenShift service and are for demonstration purposes only. See the CDK Developer Guide (to be published) for more in-depth descriptions.
8.1. Deploying an InstantApp Template as a New Application
In this example, an InstantApp template available from the default openshift project is used to create and deploy a web application. The definition of the template sets all necessary configuration options. A good way to experiment with OpenShift deployments is to clone the example’s repository and modify different parts of the defined template.
8.1.1. Creating a New OpenShift Application from a Template
To use a template to directly create a new application, run the oc new-app
command with the --template
option specifying the template you want to use as the basis for your application. For example, to use the nodejs-example
InstantApp template, run the following command:
~]$ oc new-app --template=nodejs-example
--> Deploying template nodejs-example in project openshift for "nodejs-example"
With parameters:
Memory Limit=512Mi
Git Repository URL=https://github.com/openshift/nodejs-ex.git
Git Reference=
Context Directory=
Application Hostname=
GitHub Webhook Secret=UKWP4bVymgjXcNMVnHIdaVeaORt3NMPuyqAEHhLv # generated
Generic Webhook Secret=wabGtSM7g5eSykRuH5aCskWKdFOXB0UxyNNrnQyr # generated
Database Service Name=
MongoDB Username=
MongoDB Password=
Database Name=
Database Administrator Password=
--> Creating resources with label app=nodejs-example ...
Service "nodejs-example" created
Route "nodejs-example" created
ImageStream "nodejs-example" created
BuildConfig "nodejs-example" created
DeploymentConfig "nodejs-example" created
--> Success
Build scheduled for "nodejs-example" - use the logs command to track its progress.
Run 'oc status' to view your app.
8.1.2. Monitoring Deployment Progress
To monitor the progress of the deployment, use the oc status
command, optionally with the -v
(--verbose
) parameter to display information about potential warnings:
~]$ oc status -v
In project OpenShift sample project (sample-project) on server https://127.0.0.1:8443
svc/nodejs-example - 172.30.142.222:8080
dc/nodejs-example deploys imagestreamtag/nodejs-example:latest <-
bc/nodejs-example builds https://github.com/openshift/nodejs-ex.git with openshift/nodejs:0.10
#1 build running for 27 seconds
#1 deployment waiting on image or update
exposed by route/nodejs-example
Warnings:
* The image trigger for dc/nodejs-example will have no effect until imagestreamtag/nodejs-example:latest is imported or created by a build.
View details with 'oc describe <resource>/<name>' or list everything with 'oc get all'.
8.1.3. Displaying Information about a Deployed Service
The application is automatically deployed when the build completes. Use the oc describe
command to display information about different parts of the application (or use the oc get all
command to display all information at once).
To see summary information about the service, use:
~]$ oc describe svc/nodejs-example
Name: nodejs-example
Namespace: sample-project
Labels: app=nodejs-example,template=nodejs-example
Selector: name=nodejs-example
Type: ClusterIP
IP: 172.30.142.222
Port: web 8080/TCP
Endpoints: 172.17.0.2:8080
Session Affinity: None
No events.
To display information about the route established for the application, use:
~]$ oc describe route/nodejs-example
Name: nodejs-example
Created: 46 minutes ago
Labels: app=nodejs-example,template=nodejs-example
Annotations: openshift.io/generated-by=OpenShiftNewApp
openshift.io/host.generated=true
Host: nodejs-example-sample-project.rhel-cdk.10.1.2.2.xip.io
Path: <none>
Service: nodejs-example
TLS Termination: <none>
Insecure Policy: <none>
The above command shows that the deployed application can be accessed at nodejs-example-sample-project.rhel-cdk.10.1.2.2.xip.io (the URL is made available through the external xip.io DNS service).
You can point a web browser from your host system at this address to see the page generated by the application. To check whether the application is running properly from the command line, either use a text-mode browser like lynx or download the page using curl
:
~]$ curl nodejs-example-sample-project.rhel-cdk.10.1.2.2.xip.io 2> /dev/null | grep '<h1>'
<h1>Welcome to your Node.js application on OpenShift</h1>
8.1.4. Learning about Service Images and Containers
To check the Docker images and containers that form the application, use the docker images
and docker ps
commands:
~]$ docker images REPOSITORY TAG IMAGE ID CREATED VIRTUAL SIZE 172.30.254.28:5000/sample-project/nodejs-example latest bc19f3f7dd86 2 hours ago 432.6 MB 172.30.254.28:5000/sample-project/nodejs-example <none> bc19f3f7dd86 2 hours ago 432.6 MB [...] ~]$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS NAMES bcafafb013ce 172.30.254.28:5000/sample-project/nodejs-example@sha256:... "container-entrypoint" 2 hours ago Up 2 hours k8s_nodejs-example.27445d76_nodejs-example-1-hdq11_sample-project_e5c69b57-0496-11e6-907d-525400806d1b_3e6e6b39 d4f52a47cb10 openshift3/ose-pod:v3.1.1.6 "/pod" 2 hours ago Up 2 hours k8s_POD.5983fd1a_nodejs-example-1-hdq11_sample-project_e5c69b57-0496-11e6-907d-525400806d1b_b3dee3ea [...]
8.2. Deploying a 'Hello World' Application Using Node.js
In this example, a very simple Node.js web application is created. The application is defined using a minimalistic build strategy that is automatically downloaded from a Git repository (in this case, GitHub is used). The built application is deployed on top of a Node.js container pulled from the Red Hat Atomic Registry.
8.2.1. Preparing the Application Source Code
Create a new repository on GitHub. For the purposes of this example, we will assume that the created repository has the following URL: http://github.com/example/nodejs-hello-world.git
. Then upload a basic Node.js application to the root directory of the repository. Name the file helloworld.js
.
var http = require('http'); var server = http.createServer(function(req, res) { res.writeHead(200); res.end('Hello World'); }); server.listen(8080);
The application creates an HTTP server listening on port 8080 and prints Hello World
when accessed. Download the helloword.js
file.
8.2.2. Preparing the Definition of an OpenShift Application
Upload the following minimal definition of a Node.js OpenShift application to the GitHub repository. Name the file package.json
. Based on the name of the file, OpenShift automatically selects the appropriate builder (nodejs
, in this case).
{ "name": "nodejs-hello-world", "version": "0.0.1", "description": "Node.js Hello World for OpenShift 3", "main": "helloworld.js", 1 "dependencies": { "ejs": "^2.4.1", 2 "express": "^4.13.4" }, "scripts": { "start": "node helloworld.js" 3 }, "repository": { "type": "git", "url": "http://github.com/rkratky/nodejs-hello-world.git" } }
Download the package.json
file.
8.2.3. Creating a New OpenShift Application
To create a new application in OpenShift, use the oc new-app
command. OpenShift automatically performs the following steps:
- downloads required dependencies, including specified Docker-formatted container images,
- pulls latest source code and application definition from the specified location (a Git repository, in this case),
- builds the application source code,
- builds a container with the resulting application,
- deploys the application container.
In this example, the required Node.js container image from the Red Hat Atomic Registry is specified along with the URL of the Git repository:
~]$ oc new-app registry.access.redhat.com/openshift3/nodejs-010-rhel7~https://github.com/example/nodejs-hello-world.git
--> Found Docker image 92eee82 (6 weeks old) from registry.access.redhat.com for "registry.access.redhat.com/openshift3/nodejs-010-rhel7"
* An image stream will be created as "nodejs-010-rhel7:latest" that will track the source image
* A source build using source code from https://github.com/example/nodejs-hello-world.git will be created
* The resulting image will be pushed to image stream "nodejs-hello-world:latest"
* Every time "nodejs-010-rhel7:latest" changes a new build will be triggered
* This image will be deployed in deployment config "nodejs-hello-world"
* Port 8080/tcp will be load balanced by service "nodejs-hello-world"
--> Creating resources with label app=nodejs-hello-world ...
ImageStream "nodejs-010-rhel7" created
ImageStream "nodejs-hello-world" created
BuildConfig "nodejs-hello-world" created
DeploymentConfig "nodejs-hello-world" created
Service "nodejs-hello-world" created
--> Success
Build scheduled for "nodejs-hello-world" - use the logs command to track its progress.
Run 'oc status' to view your app.
8.2.4. Monitoring Build Progress
Use the oc describe build
command to display information about the build currently in progress:
~]$ oc describe build
Name: nodejs-hello-world-1
Created: 35 seconds ago
Labels: app=nodejs-hello-world,buildconfig=nodejs-hello-world,openshift.io/build-config.name=nodejs-hello-world
Annotations: openshift.io/build.number=1
openshift.io/build.pod-name=nodejs-hello-world-1-build
Build Config: nodejs-hello-world
Started: 2016-04-18 07:05:25 -0400 EDT
Duration: running for 25s
Build Pod: nodejs-hello-world-1-build
Strategy: Source
URL: https://github.com/rkratky/nodejs-hello-world.git
From Image: DockerImage registry.access.redhat.com/openshift3/nodejs-010-rhel7:latest
Output to: ImageStreamTag nodejs-hello-world:latest
Push Secret: builder-dockercfg-9000s
Status: Running
Events:
FirstSeen LastSeen Count From SubobjectPath Reason Message
───────── ──────── ───── ──── ───────────── ────── ───────
34s 34s 1 {scheduler } Scheduled Successfully assigned nodejs-hello-world-1-build to rhel-cdk
32s 32s 1 {kubelet rhel-cdk} implicitly required container POD Pulled Container image "openshift3/ose-pod:v3.1.1.6" already present on machine
30s 30s 1 {kubelet rhel-cdk} implicitly required container POD Created Created with docker id 462325c7c721
29s 29s 1 {kubelet rhel-cdk} implicitly required container POD Started Started with docker id 462325c7c721
29s 29s 1 {kubelet rhel-cdk} spec.containers{sti-build} Pulled Container image "openshift3/ose-sti-builder:v3.1.1.6" already present on machine
27s 27s 1 {kubelet rhel-cdk} spec.containers{sti-build} Created Created with docker id f5bcba8891c3
26s 26s 1 {kubelet rhel-cdk} spec.containers{sti-build} Started Started with docker id f5bcba8891c3
To see the build logs, use the oc logs
command and specify the build you are interested in:
~]$ oc logs build/nodejs-hello-world-1
---> Installing application source
---> Building your Node application from source
E0418 09:17:59.264104 1 util.go:91] npm info it worked if it ends with ok
E0418 09:17:59.265357 1 util.go:91] npm info using npm@2.14.13
E0418 09:17:59.265366 1 util.go:91] npm info using node@v0.10.40
E0418 09:18:00.697173 1 util.go:91] npm WARN package.json nodejs-hello-world@0.0.1 No license field.
E0418 09:18:00.720236 1 util.go:91] npm info preinstall nodejs-hello-world@0.0.1
E0418 09:18:00.828498 1 util.go:91] npm info attempt registry request try #1 at 09:18:00
[...]
8.2.5. Displaying Information about the Deployed Service
Use the oc describe
command and specify the service you are interested in to show summary information about the created service:
]$ oc describe svc/nodejs-hello-world
Name: nodejs-hello-world
Namespace: sample-project
Labels: app=nodejs-hello-world
Selector: app=nodejs-hello-world,deploymentconfig=nodejs-hello-world
Type: ClusterIP
IP: 172.30.166.144
Port: 8080-tcp 8080/TCP
Endpoints: 172.17.0.4:8080
Session Affinity: None
No events.
Similarly, you can specify the deployment to show information about it, including the containers that have been created and deployed for the application:
~]$ oc describe dc
Name: nodejs-hello-world
Created: 2 minutes ago
Labels: app=nodejs-hello-world
Annotations: openshift.io/generated-by=OpenShiftNewApp
Latest Version: 1
Triggers: Config, Image(nodejs-hello-world@latest, auto=true)
Strategy: Rolling
Template:
Selector: app=nodejs-hello-world,deploymentconfig=nodejs-hello-world
Replicas: 1
Containers:
NAME IMAGE ENV
nodejs-hello-world 172.30.91.119:5000/sample-project/nodejs-hello-world@sha256:d97a0c44759c93b4231691813c12b5d2975c78fbee028f6c0091d97ed3816678
Deployment #1 (latest):
Name: nodejs-hello-world-1
Created: 2 minutes ago
Status: Complete
Replicas: 1 current / 1 desired
Selector: app=nodejs-hello-world,deployment=nodejs-hello-world-1,deploymentconfig=nodejs-hello-world
Labels: app=nodejs-hello-world,openshift.io/deployment-config.name=nodejs-hello-world
Pods Status: 1 Running / 0 Waiting / 0 Succeeded / 0 Failed
No events.
8.2.6. Testing the Running Application
To verify that the deployed HTTP server works correctly and serves the message specified in the application source code, you can use, for example, the curl
tool:
~]$ curl 172.17.0.4:8080
Hello World
The IP address is shown, for example, in the description of the deployed service or pod. Use the oc get pods
to list all pods:
~]$ oc get pods
NAME READY STATUS RESTARTS AGE
nodejs-hello-world-1-1b5xi 1/1 Running 0 2m
nodejs-hello-world-1-build 0/1 Completed 0 2m
Use the name of the pod to display its description and grep for its IP address:
~]$ oc describe pod/nodejs-hello-world-1-1b5xi | grep IP
IP: 172.17.0.4
8.3. Additional Resources
- See the definition of InstantApp OpenShift templates at https://github.com/openshift for inspiration.
- See the OpenShift Container Platform Developer Guide for detailed instructions on how to prepare, build, and deploy containerized applications on OpenShift.
- See the video tutorials and demonstration for developers at the OpenShift YouTube channel.