Docker

and

Kubernetes

#0

Who am I?

Piotr Stapp

  • Unique name - just sing a song: "Don't Stapp me know" ;)
  • ex-architect team member @mBank
  • ex-Head architect @FinAi
  • "Top secret" @ Allegro (Pay)
  • M.Sc (distinction) Oxford Brooks University in Web Tech
  • M.Sc. Warsaw University of Technology in Computer Science
  • And ......

#1

History

(or architecture)

If you can’t feed a team with two pizzas, it’s too large. That limits a task force to five to seven people, depending on their appetites 

 

Jeff Bezos

Why two pizza rule?

\Huge\tfrac{n*(n-1)}{2}
%n = # of people

n = # of people

How many links are in your group?

 => 15 links

 => 66 links

=> 1225 links

\tfrac{n*(n-1)}{2}

Two-pizza team (n=6) 

2x two-pizza team

My company (~50 ppl)

Important dates

  • 2007.02 -> RabbitMQ initial release -(1.0.0-alpha)
  • 2010.10 -> AngularJS initial release
  • 2011.05-> "microservice" term in Venice
  • 2012.05 -> James Lewis - Micro services - Java, the Unix Way at Kraków
  • 2013.03 -> Docker debuted at PyCon
  • 2013.05 -> React initial release
  • 2014.02 -> Vue.js initial release
  • 2014.03 -> Docker 0.9 released
  • 2014.06 -> Kubernetes initial release
  • 2014.11 -> Docker annouced for AWS EC2

#2

Arch VS. release

???

From spaghetti to ...

(simple one)

Repeat & repeat

A bit lasagna and ravioli

"IKEA" release

Modern one

and ....

"crazy" release

Title Text

Who runs the world?

Who runs the world?

The new kingmakers

The new kingmakers

#3

To Docker or not to Docker

that is the question

Why use Docker?

What is docker?

  • Tools, a lot of tools for managing containers
  • Company
  • Common language

What is a "container"?

Wikipedia

"refers to an operating system feature in which the kernel allows the existence of multiple isolated user-space instances"

What about Windows Container?

"Linux and Windows Server Containers are similar -- both implement similar technologies within their kernel and core operating system. The difference comes from the platform and workloads that run within the containers."

VM versus docker

VM versus docker

What & why?

  • easy hosting for our solution
  • isolation
  • faster deployment with containers
  • portability
  • security (hmm.....)
  • easy CI/CD integration

What for?

  • Solving problem: "works on my pc"*
  • Deployment
  • Learning
  • Using for example SDK "outside" & "packed"

* create problem: works in my container ;)

Which container?

Docker & databases ...

Docker 

Nomenclature

Image

Container

image vs container

exe

running exe

Images and Repositories

Commands

# get images
docker images

# get images with aspnet
docker images | grep aspnet

# get running containers
docker ps

# create image of name Name and tag Tag
docker build -t name:tag .

# tagging (many tags)
docker tag name newname:tag
docker tag newname:tag newname:tag2

# running container and mapping port 80 on local computer to 8080 on container
docker run --rm -it -p 8000:8080 name:tag
open http://127.0.0.1:8000/

Language

# creates image from base image
FROM image:tag AS name

# adds labels to image
LABEL version="1.0"

# creates if no exists and sets PWD to /app folder
WORKDIR /app

# copy from local computer to image (second . is app folder, first . is our docker context)
COPY . .

# similar, but we can use url or tar file as a source (first .)
ADD . .  

# executes command
RUN command

# sets env variables
ENV application=test

# informs docke that container listens on specific port
EXPOSE 8080

# default paremeters, easy to override
CMD [ "node", "index.js" ]
# default application, harder to override
ENTRYPOINT ["", ""]

It's not rocket science

Tooling...

DEMO

Dev containers in VS Code

+

Plant UML

Demo

- Dev containers in VS Code

- PlantUML

# run plant UML server

docker run -d -p 8080:8080 \
  plantuml/plantuml-server:jetty

Deployment...

Demo

  • docker
  • localtunnel or ngrok or ...
# Run PKAD container
docker run -d -p 8080:8080 poznajkubernetes/pkad


# install local tunnel
npm install -g localtunnel

# run localtunnel
lt --port 8080 --subdomain secure

# open
open https://secure.loca.lt

# use 
https://secure.loca.lt/ready

Scaling ???

How to scale Docker?

  • Swarm

  • Compose

  • External hosting

  • K8s

How to scale Docker?

  • Swarm -> is dying

  • Compose

  • External hosting

  • K8s

How to scale Docker?

  • Swarm -> is dying

  • Compose -> is tool for devs

  • External hosting

  • K8s

Demo

Deploy to

Azure web app

# Create resouce group
az group create \
    --name $group \
    -l westeurope

# Create app plan
az appservice plan create \
   -n appPlan \
   -g $group \
   --sku B1 --is-linux
   
# Deploy
az webapp create --plan appPlan \
   -n $app_name -g $group \
   --deployment-container-image-name \
     poznajkubernetes/pkad
     
az webapp config appsettings set \
   -n $app_name -g $group \
   --settings WEBSITES_PORT=8080

open https://$app_name.azurewebsites.net

How to scale Docker?

  • Swarm -> is dying

  • Compose -> is tool for devs

  • External hosting -> hmm....

  • K8s

Kubernetes in action

#4

Kubernetes

or K8S (k12345678s)

From standard

to K8S pods

 

ATTENTION:

DANGER! DANGER! DANGER!

to K8S

1000 words

YAML

apiVersion: apps/v1
kind: Deployment
metadata:
  name: #{ApplicationName}#
spec:
  selector:
    matchLabels:
      app: #{ApplicationName}#
  replicas: 2
  template:
    metadata:
      labels:
        app: #{ApplicationName}#
    spec:
      containers:
      - name: #{ApplicationName}#
        image: #{image}#
        ports:
        - containerPort: 80
---
kind: Service
apiVersion: v1
metadata:
  name: #{ApplicationName}#
spec:
  selector:
    app: #{ApplicationName}#
  ports:
  - protocol: TCP
    port: 80
    targetPort: 80
  type: ClusterIP
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: #{ApplicationName}#
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /
    kubernetes.io/ingress.class: internal
spec:
  rules:
  - http:
      paths:
      - path: /
        backend:
          serviceName: #{ApplicationName}#
          servicePort: 80
    host: #{ApplicationName}#-app-#{EnvironmentName}#.internal.comapny.com
  tls:
    - secretName: internal.comapny.com
      hosts:
        - #{ApplicationName}#-app-#{EnvironmentName}#..internal.comapny.com

Create cluster

In cloud it is easy ;)

# create AKS

az aks create \
  -g $group -n $aks_name \
  --node-vm-size Standard_DS2_v2 \
  --node-count 2 \
  --generate-ssh-keys
  

Get kubectl credentials

- use it as any other Kubernetes cluster



# Get kubectl credentials 
az aks get-credentials \
   -n $aks_name \
   -g $group --admin

Fast deploy

Explanation in next slides


# apply == create or update :)

kubectl apply -f yaml/basic.yaml

# get public IP

kubectl get svc -w

Deploy

Deploy PKAD

apiVersion: apps/v1
kind: Deployment
metadata:
  name: pkad-dep
spec:
  replicas: 1
  selector:
    matchLabels:
      app: pkad-dep-app
  template:
    metadata:
      labels:
        app: pkad-dep-app
    spec:
      containers:
      - name: pkad-dep
        image: poznajkubernetes/pkad:blue
        resources: {}
        ports:
        - containerPort: 8080

Deploy service

LoadBalancer (skip for now)

apiVersion: v1
kind: Service
metadata:
  name: pkad-service
spec:
  type: LoadBalancer
  selector:
    app: pkad-dep-app
  ports:
  - port: 80
    targetPort: 8080

Pod are ephemeral

ReplicaSet

Scale up

Scale to 3 replicas


# scale up
k scale deployment \
  --replicas 3 pkad-dep

Services

Services

Demo

We already have it :)




# open website

Deployment

probes

Demo

- liveness

- readiness

# deploy

k apply -f yaml/probes.yaml

Deployment

RollingUpdate

RollingUpdate

RollingUpdate

RollingUpdate

RollingUpdate

RollingUpdate

Deployment

Full stuff :)

# deploy

k apply -f yaml/deployment.yaml

# watch
k get po -w

Deployment strategies

#5

CI/CD

7 magic steps

7 steps

  1. Prepare environment variables
  2. Replace variables in template
  3. Validate YAML
  4. Run 'apply'
  5. Check rollout status
  6. If status fail then do rollback
  7. Check rollback status

Demo - Validation 

# validation
kubeval yaml/deployment-notvalid.yaml

#validation with strict
kubeval --strict yaml/deployment-notvalid.yaml

#validation with version
kubeval -v 1.10.6 --strict yaml/deployment-future.yaml

kubeval -v 1.18.0 --strict yaml/deployment-future.yaml

current=$(kubectl version --short | grep "Server" | \
           awk '{split($0,a,": v"); print a[2]}')
kubeval -v $current --strict yaml/deployment-future.yaml

Demo - 7 steps

# prepare variables
export IMAGE=poznajkubernetes/pkad:red
# replace variables
envsubst < yaml/template.yaml > yaml/dep-ready.yaml
# validate
kubeval --strict yaml/dep-ready.yaml
# apply
kubectl apply -f yaml/dep-ready.yaml

# check rollout status
if ! kubectl rollout status deployment pkad-dep; then
  # rollback
  kubectl rollout undo deployment pkad-dep;
  # rollback status
  kubectl rollout status deployment pkad-dep;
  echo "ERROR - should exit ;)"
fi

#6

Q&A

From Docker to K8s the "hard" way

By Piotr Stapp

From Docker to K8s the "hard" way

  • 351