# Guided Exercise: Scale and Expose Applications to External Access

Deploy one web server and access it through a Kubernetes ingress; and deploy another web server and access it through an OpenShift route.

**Outcomes**

In this exercise, you deploy two web applications to access them through an ingress object and a route, and scale them to verify the load-balance between the pods.

* Deploy two web applications.
    
* Create a route and an ingress object to access the web applications.
    
* Enable the sticky sessions for the web applications.
    
* Scale the web applications to load-balance the service.
    

As the `student` user on the `workstation` machine, use the `lab` command to prepare your system for this exercise. This command ensures that the cluster is accessible.

```plaintext
[student@workstation ~]$ lab start deploy-routes
```

**Procedure 4.4. Instructions**

1. Create two web application deployments, named `satir-app` and `sakila-app`. Use the [`registry.ocp4.example.com:8443/httpd-app:v1`](http://registry.ocp4.example.com:8443/httpd-app:v1) container image for both deployments.
    
    1. Log in to the OpenShift cluster as the `developer` user with the `developer` password.
        
        ```plaintext
        [student@workstation ~]$ oc login -u developer -p developer \
          https://api.ocp4.example.com:6443
        Login successful
        ...output omitted...
        ```
        
    2. Change to the `web-applications` project.
        
        ```plaintext
        [student@workstation ~]$ oc project web-applications
        Now using project "web-applications" on server "https://api.ocp4.example.com:6443".
        ...output omitted...
        ```
        
    3. Create the `satir-app` web application deployment by using the [`registry.ocp4.example.com:8443/redhattraining/do180-httpd-app:v1`](http://registry.ocp4.example.com:8443/redhattraining/do180-httpd-app:v1) container image. Ignore the warning message.
        
        ```plaintext
        [student@workstation ~]$ oc create deployment satir-app \
          --image registry.ocp4.example.com:8443/redhattraining/do180-httpd-app:v1
        Warning: would violate PodSecurity "restricted:v1.24":
        ...output omitted...
        deployment.apps/satir-app created
        ```
        
    4. After a few moments, verify that the deployment is successful.
        
        ```plaintext
        [student@workstation ~]$ oc get pods
        NAME                         READY   STATUS    RESTARTS   ...
        satir-app-787b7d7858-5dfsh   1/1     Running   0          ...
        ```
        
        ```plaintext
        [student@workstation ~]$ oc status
        ...output omitted...
        deployment/satir-app deploys registry.ocp4.example.com:8443/redhattraining/do180-httpd-app:v1
          deployment #1 running for 20 seconds - 1 pod
        ...output omitted...
        ```
        
    5. Create the `sakila-app` web application deployment by using the [`registry.ocp4.example.com:8443/redhattraining/do180-httpd-app:v1`](http://registry.ocp4.example.com:8443/redhattraining/do180-httpd-app:v1) image. Ignore the warning message.
        
        ```plaintext
        [student@workstation ~]$ oc create deployment sakila-app \
          --image registry.ocp4.example.com:8443/redhattraining/do180-httpd-app:v1
        Warning: would violate PodSecurity "restricted:v1.24":
        ...output omitted...
        deployment.apps/sakila-app created
        ```
        
    6. Wait a few moments and then verify that the deployment is successful.
        
        ```plaintext
        [student@workstation ~]$ oc get pods
        NAME                     READY   STATUS    RESTARTS   ...
        sakila-app-6694...5kpd   1/1     Running   0          ...
        satir-app-787b7...dfsh   1/1     Running   0          ...
        ```
        
        ```plaintext
        [student@workstation ~]$ oc status
        ...output omitted...
        deployment/satir-app deploys registry.ocp4.example.com:8443/redhattraining/do180-httpd-app:v1
          deployment #1 running for 5 minutes - 1 pod
        
        deployment/sakila-app deploys registry.ocp4.example.com:8443/redhattraining/do180-httpd-app:v1
          deployment #1 running for 2 minutes - 1 pod
        ...output omitted...
        ```
        
2. Create services for the web application deployments. Then, use the services to create a route for the `satir-app` application and an ingress object for the `sakila-app` application.
    
    1. Expose the `satir-app` deployment. Name the service `satir-svc`, and specify port `8080` as the port and target port.
        
        ```plaintext
        [student@workstation ~]$ oc expose deployment satir-app --name satir-svc \
          --port 8080 --target-port 8080
        service/satir-svc exposed
        ```
        
    2. Expose the `sakila-app` deployment to create the `sakila-svc` service.
        
        ```plaintext
        [student@workstation ~]$ oc expose deployment sakila-app --name sakila-svc \
          --port 8080 --target-port 8080
        service/sakila-svc exposed
        ```
        
    3. Verify the status of the services.
        
        ```plaintext
        [student@workstation ~]$ oc get services
        NAME         TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)    ...
        sakila-svc   ClusterIP   172.30.230.41   <none>        8080/TCP   ...
        satir-svc    ClusterIP   172.30.143.15   <none>        8080/TCP   ...
        ```
        
        ```plaintext
        [student@workstation ~]$ oc get endpoints
        NAME         ENDPOINTS        ...
        sakila-svc   10.8.0.66:8080   ...
        satir-svc    10.8.0.65:8080   ...
        ```
        
        ```plaintext
        [student@workstation ~]$ oc get pods -o wide
        NAME                    READY  STATUS   RESTARTS  AGE   IP        ...
        sakila-app-6694...5kpd  1/1    Running  0         92s   10.8.0.66 ...
        satir-app-787b7...dfsh  1/1    Running  0         2m49s 10.8.0.65 ...
        ```
        
    4. Create a route named `satir` for the `satir-app` web application by exposing the `satir-svc` service.
        
        ```plaintext
        [student@workstation ~]$ oc expose service satir-svc --name satir
        route.route.openshift.io/satir exposed
        ```
        
        ```plaintext
        [student@workstation ~]$ oc get routes
        NAME    HOST/PORT                                    ... SERVICES    PORT   ...
        satir   satir-web-applications.apps.ocp4.example.com ... satir-svc   8080   ...
        ```
        
    5. Create an ingress object named `ingr-sakila` for the `sakila-svc` service. Configure the `--rule` option with the following values:
        
        | Field | Value |
        | --- | --- |
        | Host | [`ingr-sakila.apps.ocp4.example.com`](http://ingr-sakila.apps.ocp4.example.com) |
        | Service name | `sakila-svc` |
        | Port number | `8080` |
        
        ```plaintext
        [student@workstation ~]$ oc create ingress ingr-sakila \
          --rule "ingr-sakila.apps.ocp4.example.com/*=sakila-svc:8080"
        ingress.networking.k8s.io/ingr-sakila created
        ```
        
        ```plaintext
        [student@workstation ~]$ oc get ingress
        NAME        ... HOSTS                              ADDRESS       PORTS ...
        ingr-sakila ... ingr-sakila.apps.ocp4.example.com  router...com  80    ...
        ```
        
    6. Confirm that a route exists for the `ingr-sakila` ingress object.
        
        ```plaintext
        [student@workstation ~]$ oc get routes
        NAME           HOST/PORT                                    ... SERVICES   PORT
        ingr-sakila... ingr-sakila.apps.ocp4.example.com            ... sakila-svc <all>
        satir          satir-web-applications.apps.ocp4.example.com ... satir-svc  8080
        ```
        
        A specific port is not assigned to routes that ingress objects created. By contrast, a route that an exposed service created is assigned the same ports as the service.
        
    7. Use the `curl` command to access the `ingr-sakila` ingress object and the `satir` route. The output states the name of the pod that is servicing the request.
        
        ```plaintext
        [student@workstation ~]$ curl ingr-sakila.apps.ocp4.example.com
        Welcome to Red Hat Training, from sakila-app-66947cdd78-x5kpd
        ```
        
        ```plaintext
        [student@workstation ~]$ curl satir-web-applications.apps.ocp4.example.com
        Welcome to Red Hat Training, from satir-app-787b7d7858-bdfsh
        ```
        
3. Scale the web application deployments to load-balance their services. Scale the `sakila-app` to two replicas, and the `satir-app` to three replicas.
    
    1. Scale the `sakila-app` deployment with two replicas.
        
        ```plaintext
        [student@workstation ~]$ oc scale deployment sakila-app --replicas 2
        deployment.apps/sakila-app scaled
        ```
        
    2. Wait a few moments and then verify the status of the replica pods.
        
        ```plaintext
        [student@workstation ~]$ oc get pods
        NAME                     READY   STATUS    RESTARTS   ...
        sakila-app-6694...5kpd   1/1     Running   0          ...
        sakila-app-6694...rfzg   1/1     Running   0          ...
        satir-app-787b...dfsh    1/1     Running   0          ...
        ```
        
    3. Scale the `satir-app` deployment with three replicas.
        
        ```plaintext
        [student@workstation ~]$ oc scale deployment satir-app --replicas 3
        deployment.apps/satir-app scaled
        ```
        
    4. Wait a few moments and then verify the status of the replica pods.
        
        ```plaintext
        [student@workstation ~]$ oc get pods -o wide
        NAME                    READY  STATUS   RESTARTS  ... IP        ...
        sakila-app-6694...5kpd  1/1    Running  0         ... 10.8.0.66 ...
        sakila-app-6694...rfzg  1/1    Running  0         ... 10.8.0.67 ...
        satir-app-787b...dfsh   1/1    Running  0         ... 10.8.0.65 ...
        satir-app-787b...z8xm   1/1    Running  0         ... 10.8.0.69 ...
        satir-app-787b...7bhj   1/1    Running  0         ... 10.8.0.70 ...
        ```
        
    5. Retrieve the service endpoints to confirm that the services are load-balanced between the additional replica pods.
        
        ```plaintext
        [student@workstation ~]$ oc get endpoints
        NAME         ENDPOINTS                                     ...
        sakila-svc   10.8.0.66:8080,10.8.0.67:8080                 ...
        satir-svc    10.8.0.65:8080,10.8.0.69:8080,10.8.0.70:8080  ...
        ```
        
4. Enable the sticky sessions for the `sakila-app` web application. Then, use the `curl` command to confirm that the sticky sessions are working for the `ingr-sakila` object.
    
    1. Configure a cookie for the `ingr-sakila` ingress object.
        
        ```plaintext
        [student@workstation ~]$ oc annotate ingress ingr-sakila \
          ingress.kubernetes.io/affinity=cookie
        ingress.networking.k8s.io/ingr-sakila annotated
        ```
        
    2. Use the `curl` command to access the `ingr-sakila` ingress object. The output states the name of the pod that is servicing the request. Notice that the connection is load-balanced between the replicas.
        
        ```plaintext
        [student@workstation ~]$ for i in {1..3}; do \
          curl ingr-sakila.apps.ocp4.example.com ; done
        Welcome to Red Hat Training, from sakila-app-66947cdd78-x5kpd
        Welcome to Red Hat Training, from sakila-app-66947cdd78-xrfzg
        Welcome to Red Hat Training, from sakila-app-66947cdd78-x5kpd
        ```
        
    3. Use the `curl` command to save the `ingr-sakila` ingress object cookie to the `/tmp/cookie_jar` file. Confirm that the cookie exists in the `/tmp/cookie_jar` file.
        
        ```plaintext
        [student@workstation ~]$ curl ingr-sakila.apps.ocp4.example.com \
          -c /tmp/cookie_jar
        Welcome to Red Hat Training, from sakila-app-66947cdd78-xrfzg
        ```
        
        ```plaintext
        [student@workstation ~]$ cat /tmp/cookie_jar
        ...output omitted...
        #HttpOnly_ingr-sakila.apps.ocp4.example.com	FALSE	/	FALSE	0	b9b484110526b4b1b3159860d3aebe04	921e139c5145950d00424bf3b0a46d22
        ```
        
    4. The cookie provides session stickiness for connections to the `ingr-sakila` route. Use the `curl` command and the cookie in the `/tmp/cookie_jar` file to connect to the `ingr-sakila` route again. Confirm that you are connected to the same pod that handled the request in the previous step.
        
        ```plaintext
        [student@workstation ~]$ for i in {1..3}; do \
          curl ingr-sakila.apps.ocp4.example.com -b /tmp/cookie_jar; done
        Welcome to Red Hat Training, from sakila-app-66947cdd78-xrfzg
        Welcome to Red Hat Training, from sakila-app-66947cdd78-xrfzg
        Welcome to Red Hat Training, from sakila-app-66947cdd78-xrfzg
        ```
        
    5. Use the `curl` command to connect to the `ingr-sakila` route without the cookie. Observe that session stickiness occurs only with the cookie.
        
        ```plaintext
        [student@workstation ~]$ for i in {1..3}; do \
          curl ingr-sakila.apps.ocp4.example.com ; done
        Welcome to Red Hat Training, from sakila-app-66947cdd78-x5kpd
        Welcome to Red Hat Training, from sakila-app-66947cdd78-xrfzg
        Welcome to Red Hat Training, from sakila-app-66947cdd78-x5kpd
        ```
        
5. Enable the sticky sessions for the `satir-app` web application. Then, use the `curl` command to confirm that sticky sessions are active for the `satir` route.
    
    1. Configure a cookie with a `hello` value for the `satir` route.
        
        ```plaintext
        [student@workstation ~]$ oc annotate route satir \
          router.openshift.io/cookie_name="hello"
        route.route.openshift.io/satir annotated
        ```
        
    2. Use the `curl` command to access the `satir` route. The output states the name of the pod that is servicing the request. Notice that the connection is load-balanced between the three replica pods.
        
        ```plaintext
        [student@workstation ~]$ for i in {1..3}; do \
          curl satir-web-applications.apps.ocp4.example.com; done
        Welcome to Red Hat Training, from satir-app-787b7d7858-bdfsh
        Welcome to Red Hat Training, from satir-app-787b7d7858-gz8xm
        Welcome to Red Hat Training, from satir-app-787b7d7858-q7bhj
        ```
        
    3. Use the `curl` command to save the `hello` cookie to the `/tmp/cookie_jar` file. Afterward, confirm that the `hello` cookie exists in the `/tmp/cookie_jar` file.
        
        ```plaintext
        [student@workstation ~]$ curl satir-web-applications.apps.ocp4.example.com \
          -c /tmp/cookie_jar
        Welcome to Red Hat Training, from satir-app-787b7d7858-q7bhj
        ```
        
        ```plaintext
        [student@workstation ~]$ cat /tmp/cookie_jar
        ...output omitted...
        #HttpOnly_satir-web-applications.apps.ocp4.example.com	FALSE	/	FALSE	0	hello	b7dd73d32003e513a072e25a32b6c881
        ```
        
    4. The `hello` cookie provides session stickiness for connections to the `satir` route. Use the `curl` command and the `hello` cookie in the `/tmp/cookie_jar` file to connect to the `satir` route again. Confirm that you are connected to the same pod that handled the request in the previous step.
        
        ```plaintext
        [student@workstation ~]$ for i in {1..3}; do \
          curl satir-web-applications.apps.ocp4.example.com -b /tmp/cookie_jar; done
        Welcome to Red Hat Training, from satir-app-787b7d7858-q7bhj
        Welcome to Red Hat Training, from satir-app-787b7d7858-q7bhj
        Welcome to Red Hat Training, from satir-app-787b7d7858-q7bhj
        ```
        
    5. Use the `curl` command to connect to the `satir` route without the `hello` cookie. Observe that session stickiness occurs only with the cookie.
        
        ```plaintext
        [student@workstation ~]$ for i in {1..3}; do \
          curl satir-web-applications.apps.ocp4.example.com; done
        Welcome to Red Hat Training, from satir-app-787b7d7858-gz8xm
        Welcome to Red Hat Training, from satir-app-787b7d7858-q7bhj
        Welcome to Red Hat Training, from satir-app-787b7d7858-bdfsh
        ```
        

**Finish**

On the `workstation` machine, use the `lab` command to complete this exercise. This step is important to ensure that resources from previous exercises do not impact upcoming exercises.

```plaintext
[student@workstation ~]$ lab finish deploy-routes
```
