title | parent | tags | thumbnail | date | description | redirect_from | mrm | xredirect | slug | |||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
How to Deploy a Python Flask Application in a Kubernetes cluster |
tutorials |
|
assets/flask-shell-diagram.png |
2021-10-11 01:00 |
Setting up a Kubernetes cluster using Oracle Cloud, and deploying a Python application with Flask framework using Cloud Shell. |
/collections/tutorials/deploy-flask-app-cloud-shell/ |
WWMK210625P00048 |
deploy-flask-app-cloud-shell |
{% slides %}
In this tutorial, you use an Oracle Cloud Infrastructure (OCI) account to set up a Kubernetes cluster. Then, you create a Python application with a Flask framework. Finally, you'll deploy your application to your cluster using Cloud Shell.
Key tasks include how to:
- Create a Compartment
- Set up a Kubernetes cluster on OCI
- Build a Python application in a Flask framework
- Create a Docker image
- Push your image to OCI Container Registry
- Use Cloud Shell to deploy your Docker application to your cluster
- Connect to your application from the internet
For additional information, see:
To successfully perform this tutorial, you'll need the following:
- A Free trial or a paid OCI account. You can sign up here.
- Cloud Shell or the following
- JDK 8+
- Python 3.6.8+
- Kubectl 1.18.10+
- Apache Maven 3.5+
- Docker 19.0.11+
The advantage of using Cloud Shell is all the required tools to manage your application are already installed and ready to use. {:.notice}
Prepare your environment to create and deploy your application.
- Log in to the Oracle Cloud Infrastructure Console.
- Open the navigation menu, and click Governance and Administration. Under Governance, click Limits, Quotas and Usage.
- Find your service limit for Regions:
- Filter for the following options:
- Service: Regions
- Scope: Tenancy
- Resource: Subscribed region count
- Compartment:
<tenancy-name>
(root)
- Find service limit:
- Limit Name:
subscribed-region-count
- Service Limit: minimum 2
- Limit Name:
- Filter for the following options:
- Find your available Compute core count for the VM.Standard.E2.1 shape:
- Filter for the following options:
- Service: Compute
- Scope:
<first-availability-domain>
. Example:EMlr:US-ASHBURN-AD-1
- Resource: Cores for Standard.E2 based VM and BM Instances
- Compartment:
<tenancy-name>
(root)
- Find available core count:
- Limit Name:
standard-e2-core-count
- Available: minimum 1
- Limit Name:
- Repeat for Scope:
<second-availability-domain>
and<third-availability-domain>
. Each region must have at least one core available for this shape.
- Filter for the following options:
- Find out if you have 50 GB of Block Volume available:
- Filter for the following options:
- Service: Block Volume
- Scope:
<first-availability-domain>
. Example:EMlr:US-ASHBURN-AD-1
- Resource Volume Size (GB)
- Compartment:
<tenancy-name>
(root)
- Find available core count:
- Limit Name:
total-storage-gb
- Available: minimum 50
- Limit Name:
- Repeat for Scope:
<second-availability-domain>
and<third-availability-domain>
. Each region must have at least 50 GB of block volume available.
- Filter for the following options:
- Find out how many Flexible Load Balancers are available:
- Filter for the following options:
- Service: LBaaS
- Scope:
<your-region>
. Example:us-ashburn-1
- Resource:
- Compartment:
<tenancy-name>
(root)
- Find the count for the following shapes
- Limit Name:
lb-flexible-bandwidth-count
- Available: minimum 1
- Limit Name:
- Filter for the following options:
This tutorial creates three compute instances with a VM.Standard.E2.1 shape for the cluster nodes. To use another shape, filter for its core count. For example, filter VM.Standard2.4 for Cores for Standard2 based VM and BM Instances, and get the count.
- For a list of all shapes, see VM Standard Shapes. {:.notice}
This tutorial creates a load balancer with a flexible shape. To use another bandwidth, filter its count. For example 100-Mbps bandwidth or 400-Mbps bandwidth. {:.notice}
-
In the Console's top navigation bar, click the Profile menu (your avatar).
-
Click your username.
-
Click Auth Tokens.
-
Click Generate Token.
-
Give it a description.
-
Click Generate Token.
-
Copy the token and save it.
-
Click Close.
Ensure that you save your token right after you create it. You have no access to it later. {:.notice}
-
Collect the following credential information from the Oracle Cloud Infrastructure Console:
- Tenancy name:
<tenancy-name>
- Click your Profile menu (your avatar) and find your Tenancy:.
- Tenancy namespace:
<tenancy-namespace>
- Click your Profile menu (your avatar).
- Click Tenancy: .
- Copy the value for Object Storage Namespace.
For some accounts, the tenancy name and namespace values differ. Ensure that you use namespace in this tutorial. {:.notice}
- Tenancy OCID:
<tenancy-ocid>
- Click your Profile menu (your avatar), then click Tenancy:, and copy OCID.
- Username:
<user-name>
- Click your Profile menu (your avatar).
- User OCID:
<user-ocid>
- Click your Profile menu (your avatar), then click User Settings, and copy OCID.
- Tenancy name:
-
Find your region information.
- Region:
<region-identifier>
- In the Console's top navigation bar, find your region. Example: US East (Ashburn).
- Find your Region Identifier from the table in Regions and Availability Domains.
- Example:
us-ashburn-1
.
- Region Key:
<region-key>
- Find your Region Key from the table in Regions and Availability Domains.
- Example:
iad
- Region:
-
Copy your authentication token from the Create an Authentication Token section.
- Auth Token:
<auth-token>
- Auth Token:
Install and configure management options for your Kubernetes cluster. Later, deploy your application to this cluster.
If your username is in the Administrators group, then skip this section. Otherwise, have your administrator add the following policy to your tenancy:
allow group <the-group-your-username-belongs> to manage compartments in tenancy
With this privilege, you can create a compartment for all the resources in your tutorial.
-
In the Console's top navigation bar, open the Profile menu (your avatar).
-
Click your username.
-
In the left pane, click Groups.
-
In a notepad, copy the Group Name that your username belongs.
-
Open the navigation menu and click Identity & Security. Under Identity, click Policies.
-
Click Create Policy.
-
Fill in the following information:
- Name:
manage-compartments
- Description:
Allow the group <the-group-your-username-belongs> to list, create, update, delete and recover compartments in the tenancy.
- Compartment:
<your-tenancy>(root)
- Name:
-
For Policy Builder, click Show Manual Editor.
-
Paste in the following policy:
allow group <the-group-your-username-belongs> to manage compartments in tenancy
- Click Create.
Reference
The compartments
resource-type in Verbs + Resource-Type Combinations for IAM
Create a compartment for the resources that you'll create in this tutorial.
- Log in to the Oracle Cloud Infrastructure Console.
- Open the navigation menu and click Identity & Security. Under Identity, click Compartments.
- Click Create Compartment.
- Fill in the following information:
- Name:
<your-compartment-name>
- Description:
Compartment for <your-description>.
- Parent Compartment:
<your-tenancy>(root)
- Name:
- Click Create Compartment.
Reference: Create a compartment
If your username is in the Administrators group, then skip this section. Otherwise, have your administrator add the following policy to your tenancy:
allow group <the-group-your-username-belongs> to manage all-resources in compartment <your-compartment-name>
With this privilege, you can manage all the resources in your compartment, essentially giving you administrative rights in that compartment.
-
Open the navigation menu and click Identity & Security. Under Identity, click Policies.
-
Select your compartment from the Compartment list.
-
Click Create Policy.
-
Fill in the following information:
- Name:
manage-<your-compartment-name>-resources
- Description:
Allow users to list, create, update, and delete resources in <your-compartment-name>.
- Compartment:
<your-tenancy>(root)
- Name:
-
For Policy Builder, select the following choices:
- Policy use cases:
Compartment Management
- Common policy templates:
Let compartment admins manage the compartment
- Groups:
<the-group-your-username-belongs>
- Location:
<your-tenancy>(root)
- Policy use cases:
-
Click Create.
Reference
Create a cluster with default settings and new network resources through the 'Quick Create' workflow.
-
Sign in to the Oracle Cloud Infrastructure Console.
-
Open the navigation menu and click Developer Services. Under Containers & Artifacts, clickKubernetes Clusters (OKE).
-
Click Create Cluster.
-
Select Quick Create.
-
Click Launch Workflow.
-
The Create Cluster dialog is displayed. Fill in the following information.
-
Name:
<your-cluster-name>
-
Compartment:
<your-compartment-name>
-
Kubernetes Version:
<take-default>
-
Kubernetes API Endpoint: Public Endpoint The Kubernetes cluster is hosted in a public subnet with an auto-assigned public IP address.
-
Kubernetes Worker Nodes: Private Workers The Kubernetes worker nodes are hosted in a private subnet.
-
Shape: VM.Standard.E2.1
-
Number of Nodes: 3
-
Specify a custom boot volume size: Clear the check box.
-
-
Click Next. All your choices are displayed. Review them to ensure that everything is configured correctly.
-
Click Create Cluster. The services set up for your cluster are displayed.
-
Click Close.
-
Get a cup of coffee. It takes a few minutes for the cluster to be created.
You have successfully created a Kubernetes cluster.
After you create a Kubernetes cluster, set up your local system to access the cluster.
- Sign in to the Oracle Cloud Infrastructure Console.
- Open the navigation menu and click Developer Services. Under Containers & Artifacts, clickKubernetes Clusters (OKE).
- Click the link to
<your-cluster>
.
The information about your cluster is displayed.
-
Click Access Cluster.
-
Click Cloud Shell Access. Follow the steps in the dialog. The following steps are provided for your reference.
-
From the main menu, click the Cloud Shell icon () and start a session.
-
Check your
oci
CLI version and verify that Cloud Shell is working.oci -v
-
Create your
.kube
directory if it doesn't exist.mkdir -p $HOME/.kube
-
Create kubeconfig file for your setup. Use the information from the Access Your Cluster dialog.
oci ce cluster create-kubeconfig <use data from dialog>
-
Test your cluster configuration with the following command.
kubectl get service
If the
config
file is not stored in its default location (~/.kube/config
), you must export theKUBECONFIG
environment variable to point to the location.export KUBECONFIG=$HOME//config {:.notice}
When working with more than one cluster, you specify a specific config file on the command line. Example: kubectl --kubeconfig=</path/to/config/file> {:.notice}
With your cluster access setup, you are now ready to prepare your application for deployment.
Next, set up the Flask framework on Cloud Shell. Then, create and run a Python application.
Create your Flask application.
-
Install Flask.
pip3 install --user Flask
-
Create a directory for your application.
mkdir python-hello-app
-
Change to the
python-hello-app
directory.cd python-hello-app
-
Create a "Hello, World!" application.
- Create the file:
vi hello.py
In the file, input the following text:
```python
from flask import Flask
app = Flask(__name__)
@app.route('/')
def hello_world():
return '<h1>Hello World from Flask!</h1>'
if __name__ == "__main__":
app.run(host="0.0.0.0", port=int("5000"), debug=True)
```
- Save the file.
Run your Flask application.
-
Run the Python program.
export FLASK_APP=hello.py export FLASK_ENV=development python3 hello.py
This produces the following output:
- Serving Flask app 'hello' (lazy loading)
- Environment: development
- Debug mode: on
- Running on all addresses. WARNING: This is a development server. Do not use it in a production deployment.
- Running on http://x.x.x.x:5000/ (Press CTRL+C to quit)
- Restarting with stat
- Debugger is active!
- Debugger PIN: xxx-xxx-xxx
-
Move the app to the background.
- Input ctrl-z.
- Enter the following command:
bg
-
Test the app using
curl
.In the Cloud Shell terminal, enter the following code:
curl -X GET http://localhost:5000
Output:
<h1>Hello World from Flask!</h1>
-
Stop the running application.
When you're done testing, get the process ID for your application.
ps -ef
Stop the process.
kill <your-pid>
You have successfully created a local Python application with the Flask framework.
References:
For more information on Flask, check out the Flask Documentation.
Next, you'll need to create a Docker image for your Flask application.
-
First, ensure you're in the
python-hello-app
directory. -
Create the configuration file
Dockerfile
:vi Dockerfile
In the file, input the following text and save the file:
FROM python:3.9-slim-buster ADD hello.py / COPY . /app WORKDIR /app RUN pip3 install Flask EXPOSE 5000 CMD [ "python3", "./hello.py" ]
-
Build a Docker image:
docker build -t python-hello-app .
You get a success message.
[INFO] BUILD SUCCESS Successfully tagged python-hello-app:latest
-
Run the Docker image:
docker run --rm -p 5000:5000 python-hello-app:latest &
-
Test the application using the
curl
command:curl -X GET http://localhost:5000
If you see
<h1>Hello World from Flask!</h1>
, then the Docker image is running. You can now push the image to Container Registry. -
Stop the running application. When you are done testing, get the process ID for your application.
ps -ef
Stop the process.
kill <your-pid>
Congratulations! You have successfully created a Python Flask Docker image.
With your Python image created, now you can deploy it.
-
Open the navigation menu and click Developer Services. Under Containers & Artifacts, clickContainer Registry.
-
In the left navigation, select
<your-compartment-name>
. -
Click Create Repository.
-
Create a private repository with your choice of repo name:
<repo-name> = <image-path-name>/<image-name>
Example:
flask-apps/python-hello-app
You are now ready to push your local image to Container Registry.
Before you can push a Docker image into a registry repository, the repository must exist in your compartment. If the repository does not exist, the Docker push command does not work correctly. The slash in a repository name does not represent a hierarchical directory structure. The optional
<image-path-name>
helps to organize your repositories. {:.notice}
With your local Docker image created, push the image to the Container Registry.
Follow these steps.
-
Open a terminal window.
-
Log in to Container Registry:
docker login <region-key>.ocir.io
You are prompted for your login name and password.
- Username:
<tenancy-namespace>/<user-name>
- Password:
<auth-token>
- Username:
-
List your local Docker images:
docker images
The Docker images on your system are displayed. Identify the image you created in the last section:
python-hello-app
-
Tag your local image with the URL for the registry plus the repo name, so you can push it to that repo.
docker tag <your-local-image> <repo-url>/<repo-name>
Replace
<repo-url>
with:<region-key>.ocir.io/<tenancy-namespace>/
Replace
<repo-name>
with<image-folder-name>/<image-name>
from the Create a Docker Repository section.Here is an example after combining both:
docker tag python-hello-app iad.ocir.io/my-namespace/flask-apps/python-hello-app
In this example, the components are:
- Repo URL:
iad.ocir.io/my-namespace/
- Repo name:
flask-apps/python-hello-app
OCI Container Registry now supports creating a registry repo in any compartment rather than only in the root compartment (tenancy). To push the image to the repo you created, combine the registry URL with the exact repo name. OCI Container Registry matches based on the unique repo name and pushes your image. {:.notice}
- Repo URL:
-
Check your Docker images to ensure that the image is copied.
docker images
- The tagged or the copied image has the same image ID as your local image.
- The copied image name is:
<region-key>.ocir.io/<tenancy-namespace>/<image-folder-name>/<image-name>
-
Push the image to Container Registry.
docker push **<copied-image-name>**:latest
Example:
docker push iad.ocir.io/my-namespace/flask-apps/python-hello-app:latest
-
Open the navigation menu and click Developer Services. Under Containers & Artifacts, then clickContainer Registry.
Find your image in Container Registry after the push command is complete.
With your image in Container Registry, you can now deploy your image and app.
-
Create a registry secret for your application. This secret authenticates your image when you deploy it to your cluster.
To create your secret, fill in the information in this template .
kubectl create secret docker-registry ocirsecret \ --docker-server=<region-key>.ocir.io \ --docker-username='<tenancy-namespace>/<user-name>' \ --docker-password='<auth-token>' \ --docker-email='<email-address>'
After the command runs, you get a message similar to:
secret/ocirsecret created
. -
Verify that the secret is created. Issue the following command:
kubectl get secret ocirsecret --output=yaml
The output includes information about your secret in the yaml format.
-
Determine the host URL to your registry image using the following template:
<region-code>.ocir.io/<tenancy-namespace>/<repo-name>/<image-name>:<tag>
Example:
iad.ocir.io/my-namespace/flask-apps/python-hello-app:latest
-
On your system, create a file called
app.yaml
with the following text:Replace the following place holders: *
<your-image-url>
*<your-secret-name>
apiVersion: apps/v1 kind: Deployment metadata: name: app spec: selector: matchLabels: app: app replicas: 3 template: metadata: labels: app: app spec: containers: - name: app image: <your-image-url> imagePullPolicy: Always ports: - name: app containerPort: 5000 protocol: TCP imagePullSecrets: - name: <your-secret-name> --- apiVersion: v1 kind: Service metadata: name: app-lb labels: app: app annotations: service.beta.kubernetes.io/oci-load-balancer-shape: "flexible" service.beta.kubernetes.io/oci-load-balancer-shape-flex-min: "10" service.beta.kubernetes.io/oci-load-balancer-shape-flex-max: "100" spec: type: LoadBalancer ports: - port: 5000 selector: app: app
-
Deploy your application with the following command.
kubectl create -f app.yaml
Output:
deployment.apps/app created
In the
app.yaml
file, the code after the dashes adds a flexible load balancer. {:.notice}
After you deploy your app, it might take the load balancer a few seconds to load.
-
Check if the load balancer is live:
kubectl get service
Repeat the command until the load balancer is assigned an IP address.
While waiting for the load balancer to deploy, you can check the status of your cluster with these commands:
- Get each pods status:
kubectl get pods
- Get app status:
kubectl get deployment
{:.notice}
- Get each pods status:
-
Use the load balancer IP address to connect to your app in a browser:
http://<load-balancer-IP-address>:5000
The browser displays:
<h1>Hello World from Flask!</h1>
-
Undeploy your application from the cluster. (Optional) To remove your application run this command:
kubectl delete -f app.yaml
Output:
deployment.apps/python-hello-app deleted service "python-hello-app-lb" deleted
Your application is now removed from your cluster.
You have successfully created a Hello World Python application, deployed it to a Kubernetes cluster, and made it accessible on the internet using the Flask framework.
Check out these resources to explore more information about development with Oracle products:
{% endslides %}