mirror of https://gerrit.hackerspace.pl/hscloud
docs: update CRLF to more based LF to remove hsdocs bad render
Change-Id: I8ccb44a6e659f8d280849f780700b322de7bdc12 Reviewed-on: https://gerrit.hackerspace.pl/c/hscloud/+/1824 Reviewed-by: radex <radex@hackerspace.pl>changes/24/1824/2
parent
c370e44c23
commit
dccfc0d3f4
|
@ -1,125 +1,125 @@
|
|||
# Building your own Flask web service
|
||||
|
||||
In this chapter, we will build our own web service using the Flask framework, dockerize it and register it in the registry.
|
||||
|
||||
## Requirements
|
||||
|
||||
You will require `docker` in this example. You can find installation instructions [here](https://docs.docker.com/engine/install/). For example, on Ubuntu you can install it with:
|
||||
|
||||
```bash
|
||||
curl -fsSL https://get.docker.com -o get-docker.sh
|
||||
sudo sh get-docker.sh
|
||||
```
|
||||
|
||||
To create, build and register docker image you don't need a compiled hscloud environment, howerver you will need it to deploy the image to kubernetes.
|
||||
|
||||
## Steps
|
||||
|
||||
We create a simple Flask application:
|
||||
|
||||
```py
|
||||
# app.py
|
||||
|
||||
from flask import Flask
|
||||
|
||||
app = Flask(__name__)
|
||||
|
||||
@app.route('/')
|
||||
|
||||
def hello_world():
|
||||
return 'Hello, World!'
|
||||
|
||||
if __name__ == '__main__':
|
||||
app.run()
|
||||
```
|
||||
|
||||
We can check if the application works by running it. First we start the virtual environment and install Flask:
|
||||
|
||||
```bash
|
||||
# for Linux and macOS environments
|
||||
python3 -m venv .venv
|
||||
source .venv/bin/activate
|
||||
```
|
||||
|
||||
```bash
|
||||
# for Windows environments
|
||||
py -m venv .venv
|
||||
.venv\bin\Activate.bat
|
||||
```
|
||||
|
||||
After that:
|
||||
```bash
|
||||
pip3 install flask
|
||||
python3 app.py
|
||||
```
|
||||
|
||||
Now we create `Dockerfile` file for our application:
|
||||
|
||||
```Dockerfile
|
||||
# Use an official Python runtime as a base image
|
||||
FROM python:3.12.0-bullseye
|
||||
|
||||
# Set the working directory in docker
|
||||
WORKDIR /app
|
||||
|
||||
# Copy the current directory contents into the container at /app
|
||||
COPY . /app
|
||||
|
||||
# Install any needed packages specified in requirements.txt
|
||||
RUN pip install --upgrade pip && \
|
||||
pip install flask gunicorn
|
||||
|
||||
# Set environment variables
|
||||
ENV FLASK_APP=app.py
|
||||
ENV FLASK_RUN_HOST=0.0.0.0
|
||||
|
||||
# Expose port 5000 for the Flask app to listen on
|
||||
EXPOSE 5000
|
||||
|
||||
# Define command to run the application using gunicorn
|
||||
CMD ["gunicorn", "-w", "4", "-b", ":5000", "app:app"]
|
||||
```
|
||||
|
||||
We can test if the application works in Docker:
|
||||
|
||||
```bash
|
||||
docker build -t myflask:2137 . # Build the image
|
||||
docker run -p 5000:5000 myflask:2137 # Run the container
|
||||
```
|
||||
|
||||
We can check if the application works by opening the browser at `http://localhost:5000`.
|
||||
|
||||
## Pushing the image to the registry
|
||||
|
||||
First, we need to authenticate to the registry. That will require visiting the link in a web browser:
|
||||
|
||||
```
|
||||
https://registry.k0.hswaw.net
|
||||
```
|
||||
|
||||
You should get command similar to:
|
||||
|
||||
```
|
||||
docker login -u $hs_username -p *************** https://registry.k0.hswaw.net
|
||||
```
|
||||
|
||||
Run it in your environment.
|
||||
|
||||
Now we need to create local server for our docker image:
|
||||
|
||||
```bash
|
||||
# create local server for our docker image. Replace $hs_username with your sso username
|
||||
docker tag myflask:2137 registry.k0.hswaw.net/$hs_username/myflask:2137
|
||||
docker push registry.k0.hswaw.net/$hs_username/myflask:2137
|
||||
```
|
||||
|
||||
To remove the image from the registry, you can use:
|
||||
|
||||
```bash
|
||||
# remove image from registry. Replace $hs_username with your sso username
|
||||
docker rmi registry.k0.hswaw.net/$hs_username/myflask:2137
|
||||
```
|
||||
|
||||
## Next step
|
||||
|
||||
# Building your own Flask web service
|
||||
|
||||
In this chapter, we will build our own web service using the Flask framework, dockerize it and register it in the registry.
|
||||
|
||||
## Requirements
|
||||
|
||||
You will require `docker` in this example. You can find installation instructions [here](https://docs.docker.com/engine/install/). For example, on Ubuntu you can install it with:
|
||||
|
||||
```bash
|
||||
curl -fsSL https://get.docker.com -o get-docker.sh
|
||||
sudo sh get-docker.sh
|
||||
```
|
||||
|
||||
To create, build and register docker image you don't need a compiled hscloud environment, howerver you will need it to deploy the image to kubernetes.
|
||||
|
||||
## Steps
|
||||
|
||||
We create a simple Flask application:
|
||||
|
||||
```py
|
||||
# app.py
|
||||
|
||||
from flask import Flask
|
||||
|
||||
app = Flask(__name__)
|
||||
|
||||
@app.route('/')
|
||||
|
||||
def hello_world():
|
||||
return 'Hello, World!'
|
||||
|
||||
if __name__ == '__main__':
|
||||
app.run()
|
||||
```
|
||||
|
||||
We can check if the application works by running it. First we start the virtual environment and install Flask:
|
||||
|
||||
```bash
|
||||
# for Linux and macOS environments
|
||||
python3 -m venv .venv
|
||||
source .venv/bin/activate
|
||||
```
|
||||
|
||||
```bash
|
||||
# for Windows environments
|
||||
py -m venv .venv
|
||||
.venv\bin\Activate.bat
|
||||
```
|
||||
|
||||
After that:
|
||||
```bash
|
||||
pip3 install flask
|
||||
python3 app.py
|
||||
```
|
||||
|
||||
Now we create `Dockerfile` file for our application:
|
||||
|
||||
```Dockerfile
|
||||
# Use an official Python runtime as a base image
|
||||
FROM python:3.12.0-bullseye
|
||||
|
||||
# Set the working directory in docker
|
||||
WORKDIR /app
|
||||
|
||||
# Copy the current directory contents into the container at /app
|
||||
COPY . /app
|
||||
|
||||
# Install any needed packages specified in requirements.txt
|
||||
RUN pip install --upgrade pip && \
|
||||
pip install flask gunicorn
|
||||
|
||||
# Set environment variables
|
||||
ENV FLASK_APP=app.py
|
||||
ENV FLASK_RUN_HOST=0.0.0.0
|
||||
|
||||
# Expose port 5000 for the Flask app to listen on
|
||||
EXPOSE 5000
|
||||
|
||||
# Define command to run the application using gunicorn
|
||||
CMD ["gunicorn", "-w", "4", "-b", ":5000", "app:app"]
|
||||
```
|
||||
|
||||
We can test if the application works in Docker:
|
||||
|
||||
```bash
|
||||
docker build -t myflask:2137 . # Build the image
|
||||
docker run -p 5000:5000 myflask:2137 # Run the container
|
||||
```
|
||||
|
||||
We can check if the application works by opening the browser at `http://localhost:5000`.
|
||||
|
||||
## Pushing the image to the registry
|
||||
|
||||
First, we need to authenticate to the registry. That will require visiting the link in a web browser:
|
||||
|
||||
```
|
||||
https://registry.k0.hswaw.net
|
||||
```
|
||||
|
||||
You should get command similar to:
|
||||
|
||||
```
|
||||
docker login -u $hs_username -p *************** https://registry.k0.hswaw.net
|
||||
```
|
||||
|
||||
Run it in your environment.
|
||||
|
||||
Now we need to create local server for our docker image:
|
||||
|
||||
```bash
|
||||
# create local server for our docker image. Replace $hs_username with your sso username
|
||||
docker tag myflask:2137 registry.k0.hswaw.net/$hs_username/myflask:2137
|
||||
docker push registry.k0.hswaw.net/$hs_username/myflask:2137
|
||||
```
|
||||
|
||||
To remove the image from the registry, you can use:
|
||||
|
||||
```bash
|
||||
# remove image from registry. Replace $hs_username with your sso username
|
||||
docker rmi registry.k0.hswaw.net/$hs_username/myflask:2137
|
||||
```
|
||||
|
||||
## Next step
|
||||
|
||||
[Deploying Flask web app](deploying-flask-web-app.md)
|
|
@ -1,119 +1,119 @@
|
|||
# Deploying docker image on hscloud
|
||||
|
||||
In this chapter, we will deploy our registered docker image on `hscloud` as a simple HTTP kube service with HTTPS from Let's Encrypt.
|
||||
|
||||
## Requirements
|
||||
|
||||
Registered image from [Building web app](building-web-app.md). Also, built `hscloud` environment from [Building an environment](prepare-environment.md) section.
|
||||
|
||||
## Steps
|
||||
|
||||
We create a `prod.jsonnet` file in location `//personal/$hs_username/myflask/prod.jsonnet`.
|
||||
The format of `jsonnet` is very similar to `json`, but allows the use of variables, functions, and the import of other files.
|
||||
For further reference on `jsonnet` see [jsonnet.org](https://jsonnet.org/learning/tutorial.html).
|
||||
|
||||
|
||||
```jsonnet
|
||||
# Remember to replace $hs_username with your SSO username!
|
||||
|
||||
# The import is done from the `kube.libsonnet` file in the `kube` folder in the `hscloud` folder.
|
||||
local kube = import "../../../kube/kube.libsonnet";
|
||||
|
||||
{
|
||||
local top = self,
|
||||
local cfg = self.cfg,
|
||||
|
||||
cfg:: {
|
||||
name: 'web-app',
|
||||
# The hscloud configuration only allows the namespace in `personal-$hs_username` format.
|
||||
namespace: 'personal-$hs_username',
|
||||
# The hscloud configuration only allows the domain in `*.$hs_username.hscloud.ovh` format.
|
||||
domain: 'web-app.$hs_username.hscloud.ovh',
|
||||
image: 'registry.k0.hswaw.net/$hs_username/myflask:2137',
|
||||
},
|
||||
|
||||
ns: kube.Namespace(cfg.namespace),
|
||||
|
||||
deployment: top.ns.Contain(kube.Deployment(cfg.name)) {
|
||||
spec+: {
|
||||
replicas: 1,
|
||||
template+: {
|
||||
spec+: {
|
||||
containers_: {
|
||||
default: kube.Container("default") {
|
||||
image: cfg.image,
|
||||
ports_: {
|
||||
http: { containerPort: 5000 },
|
||||
}
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
|
||||
service: top.ns.Contain(kube.Service(cfg.name)) {
|
||||
target_pod:: top.deployment.spec.template,
|
||||
},
|
||||
|
||||
ingress: top.ns.Contain(kube.Ingress(cfg.name)) {
|
||||
metadata+: {
|
||||
annotations+: {
|
||||
"kubernetes.io/tls-acme": "true",
|
||||
"cert-manager.io/cluster-issuer": "letsencrypt-prod",
|
||||
"nginx.ingress.kubernetes.io/proxy-body-size": "0",
|
||||
},
|
||||
},
|
||||
spec+: {
|
||||
tls: [ { hosts: [ cfg.domain ], secretName: cfg.name + "-tls" } ],
|
||||
rules: [
|
||||
{
|
||||
host: cfg.domain,
|
||||
http: {
|
||||
paths: [
|
||||
{ path: "/", backend: top.service.name_port },
|
||||
],
|
||||
},
|
||||
},
|
||||
],
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
We log into the cluster:
|
||||
|
||||
```bash
|
||||
hs_username=$USER # if your username is the same as your SSO username
|
||||
prodaccess -username $hs_username
|
||||
```
|
||||
|
||||
We can now deploy our application:
|
||||
|
||||
```bash
|
||||
kubecfg update prod.jsonnet
|
||||
```
|
||||
|
||||
The application should be available at `http://web-app.$hs_username.hscloud.ovh`. You will have to wait a few minutes for a working HTTPS service.
|
||||
|
||||
You can also list the pods:
|
||||
|
||||
```bash
|
||||
# List pods in the namespace. Replace $hs_username with your SSO username!
|
||||
kubectl get pods --namespace personal-$hs_username
|
||||
```
|
||||
|
||||
You should see something like this:
|
||||
|
||||
```bash
|
||||
NAME READY STATUS RESTARTS AGE
|
||||
...
|
||||
web-app-569996b8d8-lfl68 1/1 Running 0 18m
|
||||
```
|
||||
|
||||
To remove the application, execute following command, taking your pod name from the previous command, in this case `web-app-569996b8d8-lfl68`:
|
||||
|
||||
```bash
|
||||
# Delete the pod. Replace $hs_username with your SSO username!
|
||||
kubectl delete pod web-app-569996b8d8-lfl68 --namespace personal-$hs_username
|
||||
# Deploying docker image on hscloud
|
||||
|
||||
In this chapter, we will deploy our registered docker image on `hscloud` as a simple HTTP kube service with HTTPS from Let's Encrypt.
|
||||
|
||||
## Requirements
|
||||
|
||||
Registered image from [Building web app](building-web-app.md). Also, built `hscloud` environment from [Building an environment](prepare-environment.md) section.
|
||||
|
||||
## Steps
|
||||
|
||||
We create a `prod.jsonnet` file in location `//personal/$hs_username/myflask/prod.jsonnet`.
|
||||
The format of `jsonnet` is very similar to `json`, but allows the use of variables, functions, and the import of other files.
|
||||
For further reference on `jsonnet` see [jsonnet.org](https://jsonnet.org/learning/tutorial.html).
|
||||
|
||||
|
||||
```jsonnet
|
||||
# Remember to replace $hs_username with your SSO username!
|
||||
|
||||
# The import is done from the `kube.libsonnet` file in the `kube` folder in the `hscloud` folder.
|
||||
local kube = import "../../../kube/kube.libsonnet";
|
||||
|
||||
{
|
||||
local top = self,
|
||||
local cfg = self.cfg,
|
||||
|
||||
cfg:: {
|
||||
name: 'web-app',
|
||||
# The hscloud configuration only allows the namespace in `personal-$hs_username` format.
|
||||
namespace: 'personal-$hs_username',
|
||||
# The hscloud configuration only allows the domain in `*.$hs_username.hscloud.ovh` format.
|
||||
domain: 'web-app.$hs_username.hscloud.ovh',
|
||||
image: 'registry.k0.hswaw.net/$hs_username/myflask:2137',
|
||||
},
|
||||
|
||||
ns: kube.Namespace(cfg.namespace),
|
||||
|
||||
deployment: top.ns.Contain(kube.Deployment(cfg.name)) {
|
||||
spec+: {
|
||||
replicas: 1,
|
||||
template+: {
|
||||
spec+: {
|
||||
containers_: {
|
||||
default: kube.Container("default") {
|
||||
image: cfg.image,
|
||||
ports_: {
|
||||
http: { containerPort: 5000 },
|
||||
}
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
|
||||
service: top.ns.Contain(kube.Service(cfg.name)) {
|
||||
target_pod:: top.deployment.spec.template,
|
||||
},
|
||||
|
||||
ingress: top.ns.Contain(kube.Ingress(cfg.name)) {
|
||||
metadata+: {
|
||||
annotations+: {
|
||||
"kubernetes.io/tls-acme": "true",
|
||||
"cert-manager.io/cluster-issuer": "letsencrypt-prod",
|
||||
"nginx.ingress.kubernetes.io/proxy-body-size": "0",
|
||||
},
|
||||
},
|
||||
spec+: {
|
||||
tls: [ { hosts: [ cfg.domain ], secretName: cfg.name + "-tls" } ],
|
||||
rules: [
|
||||
{
|
||||
host: cfg.domain,
|
||||
http: {
|
||||
paths: [
|
||||
{ path: "/", backend: top.service.name_port },
|
||||
],
|
||||
},
|
||||
},
|
||||
],
|
||||
},
|
||||
},
|
||||
}
|
||||
```
|
||||
|
||||
We log into the cluster:
|
||||
|
||||
```bash
|
||||
hs_username=$USER # if your username is the same as your SSO username
|
||||
prodaccess -username $hs_username
|
||||
```
|
||||
|
||||
We can now deploy our application:
|
||||
|
||||
```bash
|
||||
kubecfg update prod.jsonnet
|
||||
```
|
||||
|
||||
The application should be available at `http://web-app.$hs_username.hscloud.ovh`. You will have to wait a few minutes for a working HTTPS service.
|
||||
|
||||
You can also list the pods:
|
||||
|
||||
```bash
|
||||
# List pods in the namespace. Replace $hs_username with your SSO username!
|
||||
kubectl get pods --namespace personal-$hs_username
|
||||
```
|
||||
|
||||
You should see something like this:
|
||||
|
||||
```bash
|
||||
NAME READY STATUS RESTARTS AGE
|
||||
...
|
||||
web-app-569996b8d8-lfl68 1/1 Running 0 18m
|
||||
```
|
||||
|
||||
To remove the application, execute following command, taking your pod name from the previous command, in this case `web-app-569996b8d8-lfl68`:
|
||||
|
||||
```bash
|
||||
# Delete the pod. Replace $hs_username with your SSO username!
|
||||
kubectl delete pod web-app-569996b8d8-lfl68 --namespace personal-$hs_username
|
||||
```
|
|
@ -1,77 +1,85 @@
|
|||
# Building an environment
|
||||
|
||||
In this chapter, I will describe how to build an environment in which we will build hscloud services.
|
||||
|
||||
## Requirements
|
||||
|
||||
You need `git` and `curl`. On Ubuntu you can install them with:
|
||||
|
||||
```bash
|
||||
sudo apt install git curl
|
||||
```
|
||||
|
||||
Clone the repository with the source code of the cloud services:
|
||||
|
||||
```bash
|
||||
git clone "https://gerrit.hackerspace.pl/hscloud"
|
||||
cd hscloud
|
||||
```
|
||||
|
||||
## Steps
|
||||
|
||||
We can configure the environment using nix-shell. To do this, we install `nix`:
|
||||
|
||||
```bash
|
||||
sh <(curl -L https://nixos.org/nix/install) --daemon
|
||||
```
|
||||
|
||||
And we start it (from inside the `hscloud` folder):
|
||||
|
||||
```bash
|
||||
nix-shell
|
||||
```
|
||||
|
||||
We now use the `bazel` tool to build and run the necessary services, including `prodaccess` and `kubecfg`:
|
||||
|
||||
```bash
|
||||
bazel build //tools:install
|
||||
bazel run //tools:install
|
||||
```
|
||||
|
||||
Now we can request to grant us access to the hscloud cluster through the [prodaccess](https://pkg.go.dev/code.hackerspace.pl/hscloud/cluster/prodaccess#section-readme) tool.
|
||||
In place of `$hs_username` insert the username in SSO hackerspace:
|
||||
|
||||
```bash
|
||||
hs_username=$USER # if your username is the same as your SSO username
|
||||
prodaccess -username $hs_username
|
||||
```
|
||||
|
||||
If you do not have access to the cluster, contact someone within [Matrix #infra channel](https://matrix.to/#/#infra:hackerspace.pl).
|
||||
|
||||
To check if we have access to the cluster, we can run the command:
|
||||
|
||||
```bash
|
||||
# shows the Kubernetes version
|
||||
kubectl version
|
||||
|
||||
# shows the statistics of the cluster
|
||||
kubectl top nodes
|
||||
```
|
||||
|
||||
We can also call the public Docker image (again, in place of `$hs_username`, insert the username in SSO hackerspace):
|
||||
|
||||
```bash
|
||||
# to create an instance of (sub) alpine
|
||||
kubectl -n personal-$hs_username run --image=alpine:latest -it foo
|
||||
```
|
||||
|
||||
If you want to delete the instance, run:
|
||||
|
||||
```bash
|
||||
# to delete an instance (sub) of alpine
|
||||
kubectl -n personal-$hs_username delete pod foo
|
||||
```
|
||||
|
||||
## Next step
|
||||
|
||||
# Building an environment
|
||||
|
||||
In this chapter, I will describe how to build an environment in which we will build hscloud services.
|
||||
|
||||
## Requirements
|
||||
|
||||
You need `git` and `curl`. On Ubuntu you can install them with:
|
||||
|
||||
```bash
|
||||
sudo apt install git curl
|
||||
```
|
||||
|
||||
Clone the repository with the source code of the cloud services:
|
||||
|
||||
```bash
|
||||
git clone "https://gerrit.hackerspace.pl/hscloud"
|
||||
cd hscloud
|
||||
```
|
||||
|
||||
## Steps
|
||||
|
||||
We can configure the environment using nix-shell. To do this, we install `nix`:
|
||||
|
||||
```bash
|
||||
sh <(curl -L https://nixos.org/nix/install) --daemon
|
||||
```
|
||||
|
||||
And we start it (from inside the `hscloud` folder):
|
||||
|
||||
```bash
|
||||
nix-shell
|
||||
```
|
||||
|
||||
(alternatively, you can skip whole `nix shell` config and just install dependencies):
|
||||
|
||||
```bash
|
||||
sudo apt-get -y install default-jre default-jdk python3-dev build-essential clang wget libpq-dev zip git
|
||||
wget https://github.com/bazelbuild/bazelisk/releases/download/v1.18.0/bazelisk-linux-amd64 -O /usr/bin/bazel
|
||||
chmod +x /usr/bin/bazel
|
||||
```
|
||||
|
||||
We now use the `bazel` tool to build and run the necessary services, including `prodaccess` and `kubecfg`:
|
||||
|
||||
```bash
|
||||
bazel build //tools:install
|
||||
bazel run //tools:install
|
||||
```
|
||||
|
||||
Now we can request to grant us access to the hscloud cluster through the [prodaccess](https://pkg.go.dev/code.hackerspace.pl/hscloud/cluster/prodaccess#section-readme) tool.
|
||||
In place of `$hs_username` insert the username in SSO hackerspace:
|
||||
|
||||
```bash
|
||||
hs_username=$USER # if your username is the same as your SSO username
|
||||
prodaccess -username $hs_username
|
||||
```
|
||||
|
||||
If you do not have access to the cluster, contact someone within [Matrix #infra channel](https://matrix.to/#/#infra:hackerspace.pl).
|
||||
|
||||
To check if we have access to the cluster, we can run the command:
|
||||
|
||||
```bash
|
||||
# shows the Kubernetes version
|
||||
kubectl version
|
||||
|
||||
# shows the statistics of the cluster
|
||||
kubectl top nodes
|
||||
```
|
||||
|
||||
We can also call the public Docker image (again, in place of `$hs_username`, insert the username in SSO hackerspace):
|
||||
|
||||
```bash
|
||||
# to create an instance of (sub) alpine
|
||||
kubectl -n personal-$hs_username run --image=alpine:latest -it foo
|
||||
```
|
||||
|
||||
If you want to delete the instance, run:
|
||||
|
||||
```bash
|
||||
# to delete an instance (sub) of alpine
|
||||
kubectl -n personal-$hs_username delete pod foo
|
||||
```
|
||||
|
||||
## Next step
|
||||
|
||||
Next step: [Building Flask web app](building-flask-web-app.md)
|
Loading…
Reference in New Issue