Script
Some checks failed
Gitea Actions Demo / Explore-Gitea-Actions (push) Failing after 2s

This commit is contained in:
2023-04-19 08:04:53 +02:00
parent def2924f0e
commit 497cad20ee
20 changed files with 980 additions and 1125 deletions

View File

@@ -12,8 +12,9 @@ jobs:
uses: actions/checkout@v3
- run: echo "💡 The ${{ github.repository }} repository has been cloned to the runner."
- run: echo "🖥️ The workflow is now ready to test your code on the runner."
- name: List files in the repository
- name: Execute a shell script
run: |
set -x
ls ${{ github.workspace }}
df
env | sort

1
shpod Submodule

Submodule shpod added at 61e2aabbd7

View File

@@ -1,18 +0,0 @@
name: Gitea Actions Demo
run-name: ${{ github.actor }} is testing out Gitea Actions 🚀
on: [push]
jobs:
Explore-Gitea-Actions:
runs-on: ubuntu-latest
steps:
- run: echo "🎉 The job was automatically triggered by a ${{ github.event_name }} event."
- run: echo "🐧 This job is now running on a ${{ runner.os }} server hosted by Gitea!"
- run: echo "🔎 The name of your branch is ${{ github.ref }} and your repository is ${{ github.repository }}."
- name: Check out repository code
uses: actions/checkout@v3
- run: echo "💡 The ${{ github.repository }} repository has been cloned to the runner."
- run: echo "🖥️ The workflow is now ready to test your code on the runner."
- name: List files in the repository
run: |
ls ${{ github.workspace }}
- run: echo "🍏 This job's status is ${{ job.status }}."

View File

@@ -29,29 +29,31 @@ Introduction to Kubernetes<br/>
.debug[
```
M slides/index.yaml
M slides/intro-bd-k8s.yml
?? k8s/
D slides/.gitea/workflows/build.yaml
M slides/build.sh
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-helm.yml
?? slides/intro-container-security.yml
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/marco/
?? slides/secure-containers/
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ff70d3a
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]
@@ -80,17 +82,9 @@ Password: **Something**
---
## Introductions
<!--
⚠️ This slide should be customized by the tutorial instructor(s).
-->
- Hello! I am:
- 👴 Marco Verleun (marco.verleun@i-share.nl)
- This training is based on the excellent work of Jérôme Petazzo.
<!--
<!--
- Hello! We are:
@@ -124,20 +118,28 @@ Password: **Something**
-->
<!--
- Feel free to interrupt for questions at any time
- *Especially when you see full screen container pictures!*
<!--
- Live feedback, questions, help:
-->
<!--
- You ~~should~~ must ask questions! Lots of questions!
(especially when you see full screen container pictures)
- Use to ask questions, get help, etc.
-->
<!-- -->
[@alexbuisine]: https://twitter.com/alexbuisine
[EphemeraSearch]: https://ephemerasearch.com/
[@jpetazzo]: https://twitter.com/jpetazzo
@@ -149,13 +151,17 @@ Password: **Something**
## Exercises
- At the end of each topic, there is a series of exercises.
- At the end of each day, there is a series of exercises
- To make the most out of the training, please try the exercises!
(it will help to practice and memorize the content of the chapter).
(it will help to practice and memorize the content of the day)
You can also do them later if you have your own machine(s).
- We recommend to take at least one hour to work on the exercises
(if you understood the content of the day, it will be much faster)
- Each day will start with a quick review of the exercises of the previous day
.debug[[logistics-v2.md](file:///repo/slides/logistics-v2.md)]
---
@@ -181,8 +187,7 @@ class: in-person
- They'll remain up for the duration of the workshop
- You should have a (virtual) little card with login+password+IP addresses
(https://training.verleun.org/ips.html)
- You should have a little card with login+password+IP addresses
- You can automatically SSH from one VM to another
@@ -507,7 +512,6 @@ class: extra-details
- you want only the most essential information
- You can review these slides another time if you want, they'll be waiting for you ☺
.debug[[shared/about-slides-v2.md](file:///repo/slides/shared/about-slides-v2.md)]
---
@@ -515,8 +519,6 @@ name: toc-part-1
## Part 1
- [Kubernetes concepts](#toc-kubernetes-concepts)
- [Declarative vs imperative](#toc-declarative-vs-imperative)
- [Kubernetes network model](#toc-kubernetes-network-model)
@@ -592,6 +594,11 @@ Invalid content: None
]
.debug[[shared/composedown.md](file:///repo/slides/shared/composedown.md)]
---
```
Invalid content: k8s/concepts-k8s-v2.md
```
---
class: pic
@@ -600,509 +607,13 @@ class: pic
---
name: toc-kubernetes-concepts
class: title
Kubernetes concepts
.nav[
[Previous part](#toc-)
|
[Back to table of contents](#toc-part-1)
|
[Next part](#toc-declarative-vs-imperative)
]
.debug[(automatically generated title slide)]
---
# Kubernetes concepts
- Kubernetes is a container management system
- It runs and manages containerized applications on a cluster
--
- What does that really mean?
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## What can we do with Kubernetes?
- Let's imagine that we have a 3-tier e-commerce app:
- web frontend
- API backend
- database (that we will keep out of Kubernetes for now)
- We have built images for our frontend and backend components
(e.g. with Dockerfiles and `docker build`)
- We are running them successfully with a local environment
(e.g. with Docker Compose)
- Let's see how we would deploy our app on Kubernetes!
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## Basic things we can ask Kubernetes to do
--
- Start 5 containers using image `atseashop/api:v1.3`
--
- Place an internal load balancer in front of these containers
--
- Start 10 containers using image `atseashop/webfront:v1.3`
--
- Place a public load balancer in front of these containers
--
- It's Black Friday (or Christmas), traffic spikes, grow our cluster and add containers
--
- New release! Replace my containers with the new image `atseashop/webfront:v1.4`
--
- Keep processing requests during the upgrade; update my containers one at a time
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## Other things that Kubernetes can do for us
- Autoscaling
(straightforward on CPU; more complex on other metrics)
- Resource management and scheduling
(reserve CPU/RAM for containers; placement constraints)
- Advanced rollout patterns
(blue/green deployment, canary deployment)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## More things that Kubernetes can do for us
- Batch jobs
(one-off; parallel; also cron-style periodic execution)
- Fine-grained access control
(defining *what* can be done by *whom* on *which* resources)
- Stateful services
(databases, message queues, etc.)
- Automating complex tasks with *operators*
(e.g. database replication, failover, etc.)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## Kubernetes architecture
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
![haha only kidding](images/k8s-arch1.png)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## Kubernetes architecture
- Ha ha ha ha
- OK, I was trying to scare you, it's much simpler than that ❤️
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
![that one is more like the real thing](images/k8s-arch2.png)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## Credits
- The first schema is a Kubernetes cluster with storage backed by multi-path iSCSI
(Courtesy of [Yongbok Kim](https://www.yongbok.net/blog/))
- The second one is a simplified representation of a Kubernetes cluster
(Courtesy of [Imesh Gunaratne](https://medium.com/containermind/a-reference-architecture-for-deploying-wso2-middleware-on-kubernetes-d4dee7601e8e))
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## Kubernetes architecture: the nodes
- The nodes executing our containers run a collection of services:
- a container Engine (containerd, cri-o, ...)
- kubelet (the "node agent")
- kube-proxy (a necessary but not sufficient network component)
- Nodes were formerly called "minions"
(You might see that word in older articles or documentation)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## Kubernetes architecture: the control plane
- The Kubernetes logic (its "brains") is a collection of services:
- the API server (our point of entry to everything!)
- core services like the scheduler and controller manager
- `etcd` (a highly available key/value store; the "database" of Kubernetes)
- Together, these services form the control plane of our cluster
- The control plane was also called the "master"
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
![One of the best Kubernetes architecture diagrams available](images/k8s-arch4-thanks-luxas.png)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: extra-details
## Running the control plane on special nodes
- It is common to reserve a dedicated node for the control plane
(Except for single-node development clusters, like when using minikube)
- This node used to be called a "master"
(Yes, this is ambiguous: is the "master" a node, or the whole control plane?)
- Normal applications are restricted from running on this node
(By using a mechanism called ["taints"](https://kubernetes.io/docs/concepts/configuration/taint-and-toleration/))
- When high availability is required, each service of the control plane must be resilient
- The control plane is then replicated on multiple nodes
(This is sometimes called a "multi-master" setup)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: extra-details
## Running the control plane outside containers
- The services of the control plane can run in or out of containers
- For instance: since `etcd` is a critical service, some people
deploy it directly on a dedicated cluster (without containers)
(This is illustrated on the first "super complicated" schema)
- In some hosted Kubernetes offerings (e.g. AKS, GKE, EKS), the control plane is invisible
(We only "see" a Kubernetes API endpoint)
- In that case, there is no "master node"
*For this reason, it is more accurate to say "control plane" rather than "master."*
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
![](images/control-planes/single-node-dev.svg)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
![](images/control-planes/managed-kubernetes.svg)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
![](images/control-planes/single-control-and-workers.svg)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
![](images/control-planes/stacked-control-plane.svg)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
![](images/control-planes/non-dedicated-stacked-nodes.svg)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
![](images/control-planes/advanced-control-plane.svg)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
![](images/control-planes/advanced-control-plane-split-events.svg)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: extra-details
## How many nodes should a cluster have?
- There is no particular constraint
(no need to have an odd number of nodes for quorum)
- A cluster can have zero node
(but then it won't be able to start any pods)
- For testing and development, having a single node is fine
- For production, make sure that you have extra capacity
(so that your workload still fits if you lose a node or a group of nodes)
- Kubernetes is tested with [up to 5000 nodes](https://kubernetes.io/docs/setup/best-practices/cluster-large/)
(however, running a cluster of that size requires a lot of tuning)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: extra-details
## Do we need to run Docker at all?
No!
--
- The Docker Engine used to be the default option to run containers with Kubernetes
- Support for Docker (specifically: dockershim) was removed in Kubernetes 1.24
- We can leverage other pluggable runtimes through the *Container Runtime Interface*
- <del>We could also use `rkt` ("Rocket") from CoreOS</del> (deprecated)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: extra-details
## Some runtimes available through CRI
- [containerd](https://github.com/containerd/containerd/blob/master/README.md)
- maintained by Docker, IBM, and community
- used by Docker Engine, microk8s, k3s, GKE; also standalone
- comes with its own CLI, `ctr`
- [CRI-O](https://github.com/cri-o/cri-o/blob/master/README.md):
- maintained by Red Hat, SUSE, and community
- used by OpenShift and Kubic
- designed specifically as a minimal runtime for Kubernetes
- [And more](https://kubernetes.io/docs/setup/production-environment/container-runtimes/)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: extra-details
## Do we need to run Docker at all?
Yes!
--
- In this workshop, we run our app on a single node first
- We will need to build images and ship them around
- We can do these things without Docker
<br/>
(but with some languages/frameworks, it might be much harder)
- Docker is still the most stable container engine today
<br/>
(but other options are maturing very quickly)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: extra-details
## Do we need to run Docker at all?
- On our Kubernetes clusters:
*Not anymore*
- On our development environments, CI pipelines ... :
*Yes, almost certainly*
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## Interacting with Kubernetes
- We will interact with our Kubernetes cluster through the Kubernetes API
- The Kubernetes API is (mostly) RESTful
- It allows us to create, read, update, delete *resources*
- A few common resource types are:
- node (a machine — physical or virtual — in our cluster)
- pod (group of containers running together on a node)
- service (stable network endpoint to connect to one or multiple containers)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
![Node, pod, container](images/k8s-arch3-thanks-weave.png)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## Scaling
- How would we scale the pod shown on the previous slide?
- **Do** create additional pods
- each pod can be on a different node
- each pod will have its own IP address
- **Do not** add more NGINX containers in the pod
- all the NGINX containers would be on the same node
- they would all have the same IP address
<br/>(resulting in `Address alreading in use` errors)
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## Together or separate
- Should we put e.g. a web application server and a cache together?
<br/>
("cache" being something like e.g. Memcached or Redis)
- Putting them **in the same pod** means:
- they have to be scaled together
- they can communicate very efficiently over `localhost`
- Putting them **in different pods** means:
- they can be scaled separately
- they must communicate over remote IP addresses
<br/>(incurring more latency, lower performance)
- Both scenarios can make sense, depending on our goals
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
## Credits
- The first diagram is courtesy of Lucas Käldström, in [this presentation](https://speakerdeck.com/luxas/kubeadm-cluster-creation-internals-from-self-hosting-to-upgradability-and-ha)
- it's one of the best Kubernetes architecture diagrams available!
- The second diagram is courtesy of Weave Works
- a *pod* can have multiple containers working together
- IP addresses are associated with *pods*, not with individual containers
Both diagrams used with permission.
???
:EN:- Kubernetes concepts
:FR:- Kubernetes en théorie
.debug[[k8s/concepts-k8s-v2.md](file:///repo/slides/k8s/concepts-k8s-v2.md)]
---
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/ShippingContainerSFBay.jpg)]
---
name: toc-declarative-vs-imperative
class: title
Declarative vs imperative
.nav[
[Previous part](#toc-kubernetes-concepts)
[Previous part](#toc-)
|
[Back to table of contents](#toc-part-1)
|
@@ -1220,7 +731,7 @@ specifying how to brew tea?]
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/aerial-view-of-containers.jpg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/ShippingContainerSFBay.jpg)]
---
@@ -1439,7 +950,7 @@ class: extra-details
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/blue-containers.jpg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/aerial-view-of-containers.jpg)]
---
@@ -2077,7 +1588,7 @@ $ curl -k https://10.96.0.1
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/chinook-helicopter-container.jpg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/blue-containers.jpg)]
---
@@ -2340,7 +1851,7 @@ class: title
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/container-cranes.jpg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/chinook-helicopter-container.jpg)]
---
@@ -2504,7 +2015,7 @@ class: title
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/container-housing.jpg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/container-cranes.jpg)]
---
@@ -3065,7 +2576,7 @@ class: extra-details
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/containers-by-the-water.jpg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/container-housing.jpg)]
---
@@ -3323,7 +2834,7 @@ Note: this is a fiction! We have enough entropy. But we need a pretext to scale
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/distillery-containers.jpg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/containers-by-the-water.jpg)]
---
@@ -3642,7 +3153,7 @@ The master node has [taints](https://kubernetes.io/docs/concepts/configuration/t
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/lots-of-containers.jpg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/distillery-containers.jpg)]
---
@@ -4198,7 +3709,7 @@ class: extra-details
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/plastic-containers.JPG)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/lots-of-containers.jpg)]
---
@@ -4697,7 +4208,7 @@ class: extra-details
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/train-of-containers-1.jpg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/plastic-containers.JPG)]
---
@@ -4893,7 +4404,7 @@ Exactly what we need!
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/train-of-containers-2.jpg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/train-of-containers-1.jpg)]
---
@@ -5309,7 +4820,7 @@ Note: we could have used `--namespace=default` for the same result.
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/two-containers-on-a-truck.jpg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/train-of-containers-2.jpg)]
---
@@ -5629,7 +5140,7 @@ Sorry Star Trek fans, this is not the federation you're looking for!
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/wall-of-containers.jpeg)]
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/two-containers-on-a-truck.jpg)]
---

View File

@@ -8,6 +8,7 @@ title: |
slides: https://training.verleun.org/
#slidenumberprefix: "#SomeHashTag &mdash; "
slidenumberprefix: "📜 "
exclude:
- self-paced
@@ -19,114 +20,5 @@ content:
- shared/toc.md
- secure-containers/sampleapp.md
- shared/about-slides-v2.md
# - containers/Docker_Overview.md
# #- containers/Docker_History.md
# #- containers/Training_Environment.md
# #- containers/Installing_Docker.md
# - containers/First_Containers.md
# - containers/Background_Containers.md
# #- containers/Start_And_Attach.md
# #- containers/Naming_And_Inspecting.md
# #- containers/Labels.md
# - containers/Getting_Inside-v2.md
# - containers/Initial_Images.md
# -
# - containers/Building_Images_Interactively.md
# - containers/Building_Images_With_Dockerfiles.md
# - containers/Cmd_And_Entrypoint.md
# - containers/Copying_Files_During_Build.md
# #- containers/Exercise_Dockerfile_Basic.md
# - custom/Exercise_Dockerfile.md
# # -
# - containers/Container_Networking_Basics.md
# #- containers/Network_Drivers.md
# - containers/Local_Development_Workflow.md
# #- containers/Container_Network_Model.md
# - containers/Compose_For_Dev_Stacks.md
# #- containers/Exercise_Composefile.md
# -
# #- containers/Multi_Stage_Builds.md
# #- containers/Publishing_To_Docker_Hub.md
# #- containers/Dockerfile_Tips.md
# #- containers/Exercise_Dockerfile_Advanced.md
# #- containers/Docker_Machine.md
# #- containers/Advanced_Dockerfiles.md
# #- containers/Buildkit.md
# #- containers/Init_Systems.md
# #- containers/Application_Configuration.md
# #- containers/Logging.md
# #- containers/Namespaces_Cgroups.md
# #- containers/Copy_On_Write.md
# #- containers/Containers_From_Scratch.md
# #- containers/Container_Engines.md
# #- containers/Pods_Anatomy.md
# #- containers/Ecosystem.md
# #- containers/Orchestration_Overview.md
# # - shared/thankyou.md
# - shared/sampleapp.md
# - containers/links.md
-
#- shared/webssh.md
#- k8s/versions-k8s.md
# Bridget doesn't go into as much depth with compose
#- shared/composescale.md
#- shared/hastyconclusions.md
# - shared/composedown.md
# - k8s/concepts-k8s-v2.md
# - shared/declarative.md
# - k8s/declarative.md
# - k8s/kubenet.md
# - k8s/kubectlget.md
# - k8s/setup-overview.md
#- k8s/setup-devel.md
#- k8s/setup-managed.md
# - k8s/setup-selfhosted.md
# - - k8s/kubectl-run.md
#- k8s/batch-jobs.md
#- k8s/labels-annotations.md
# - k8s/kubectl-logs.md
# - k8s/deploymentslideshow.md
# - k8s/kubectlexpose.md
# - k8s/shippingimages.md
#- k8s/buildshiprun-selfhosted.md
# - k8s/buildshiprun-dockerhub.md
# - k8s/ourapponkube.md
#- k8s/localkubeconfig.md
#- k8s/access-eks-cluster.md
#- k8s/accessinternal.md
#- k8s/kubectlproxy.md
- #- k8s/dashboard.md
#- k8s/k9s.md
#- k8s/tilt.md
#- k8s/kubectlscale.md
# - k8s/scalingdockercoins.md
# - shared/hastyconclusions.md
# - k8s/daemonset.md
# - k8s/rollout.md
#- k8s/record.md
# - - k8s/logs-cli.md
# Bridget hasn't added EFK yet
#- k8s/logs-centralized.md
# - k8s/namespaces.md
# - k8s/helm-intro.md
# - k8s/helm-chart-format.md
# - k8s/helm-create-basic-chart.md
# - k8s/helm-create-better-chart.md
# - k8s/helm-dependencies.md
# - k8s/helm-values-schema-validation.md
# - k8s/helm-secrets.md
# - k8s/kustomize.md
# #- k8s/ytt.md
# #- k8s/netpol.md
# # - k8s/whatsnext.md
# # - k8s/links.md
# - k8s/pod-security-admission.md
# - k8s/operators.md
# - k8s/operators-design.md
# - k8s/operators-example.md
# Bridget-specific
# - k8s/links-bridget.md
# - shared/thankyou.md
- secure-containers/possible-improvements.md
- secure-containers/cve.md

View File

@@ -29,31 +29,31 @@ Introduction Container Security<br/>
.debug[
```
D slides/.gitea/workflows/build.yaml
M slides/build.sh
?? k8s/
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-docker.yml.html
?? "slides/intro-bd-helm copy.yml.html"
?? slides/intro-bd-helm.yml
?? slides/intro-bd-helm.yml.html
?? slides/intro-bd-k8s.yml.html
?? slides/intro-container-security.yml
?? slides/intro-container-security.yml.html
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ce3849f
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]
@@ -80,44 +80,451 @@ Password: **Something**
.debug[[shared/title.md](file:///repo/slides/shared/title.md)]
---
```
Invalid content: marco/intro.md
```
## Introductions
<!--
⚠️ This slide should be customized by the tutorial instructor(s).
-->
- Hello! I am:
- 👴 Marco Verleun (marco.verleun@i-share.nl)
- 🏢 Employed by i-share (www.i-share.nl)
- 👷🏼‍♂️ Devops/Gitops/Cloud/Container/Cluster/Linux engineer (Pick one)
- 🎯 Secure clusters (air-gapped) running secure containers
--
- This presentation is partially based on the excellent work of Jérôme Petazzo.
- Feel free to interrupt for questions at any time
.debug[[marco/intro.md](file:///repo/slides/marco/intro.md)]
---
## Exercises
- Due to time constraints there are no exercises....
.debug[[marco/intro.md](file:///repo/slides/marco/intro.md)]
---
name: toc-part-1
## Part 1
- [Which application needs to be secured](#toc-which-application-needs-to-be-secured)
.debug[(auto-generated TOC)]
---
name: toc-part-2
## Part 2
- [Possible improvements](#toc-possible-improvements)
.debug[(auto-generated TOC)]
---
name: toc-part-3
## Part 3
- [Other improvements](#toc-other--improvements)
.debug[(auto-generated TOC)]
.debug[[shared/toc.md](file:///repo/slides/shared/toc.md)]
---
```
Invalid content: secure-containers/sampleapp.md
```
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/Container-Ship-Freighter-Navigation-Elbe-Romance-1782991.jpg)]
---
```
Invalid content: shared/about-slides-v2.md
```
name: toc-which-application-needs-to-be-secured
class: title
Which application needs to be secured
.nav[
[Previous part](#toc-)
|
[Back to table of contents](#toc-part-1)
|
[Next part](#toc-possible-improvements)
]
.debug[(automatically generated title slide)]
---
```
Invalid content: None
# Which application needs to be secured
- It is a DockerCoin miner! 💰🐳📦🚢
--
- No, you can't buy coffee with DockerCoin
--
- How dockercoins works:
- generate a few random bytes
- hash these bytes
- increment a counter (to keep track of speed)
- repeat forever!
--
- DockerCoin is *not* a cryptocurrency
(the only common points are "randomness," "hashing," and "coins" in the name)
.debug[[secure-containers/sampleapp.md](file:///repo/slides/secure-containers/sampleapp.md)]
---
## DockerCoin in the microservices era
- The dockercoins app is made of 5 services:
- `rng` = web service generating random bytes
- `hasher` = web service computing hash of POSTed data
- `worker` = background process calling `rng` and `hasher`
- `webui` = web interface to watch progress
- `redis` = data store (holds a counter updated by `worker`)
- These 5 services are visible in the application's Compose file,
[docker-compose.yml](
https://github.com/jpetazzo/container.training/blob/main/dockercoins/docker-compose.yml)
.debug[[secure-containers/sampleapp.md](file:///repo/slides/secure-containers/sampleapp.md)]
---
## How dockercoins works
- `worker` invokes web service `rng` to generate random bytes
- `worker` invokes web service `hasher` to hash these bytes
- `worker` does this in an infinite loop
- every second, `worker` updates `redis` to indicate how many loops were done
- `webui` queries `redis`, and computes and exposes "hashing speed" in our browser
*(See diagram on next slide!)*
.debug[[secure-containers/sampleapp.md](file:///repo/slides/secure-containers/sampleapp.md)]
---
class: pic
![Diagram showing the 5 containers of the applications](images/dockercoins-diagram.png)
.debug[[secure-containers/sampleapp.md](file:///repo/slides/secure-containers/sampleapp.md)]
---
## How to improve the `docker-compose.yml` file
Let's pretend we do not want to modify the original `docker-compose.yml` file
--
- Changes here might cause issues with upstream updates.
- Hard to keep track of differences with merge conflicts
--
Let's override values with `docker-compose.override.yml`
```bash
docker-compose ls
NAME STATUS CONFIG FILES
dockercoins running(5) docker-compose.yml,docker-compose.override.yml
```
.debug[[secure-containers/sampleapp.md](file:///repo/slides/secure-containers/sampleapp.md)]
---
## Two files are merged together
`docker-compose.yml`
```yaml
version: "2"
services:
rng:
build: rng
ports:
- "8001:80"
```
Invalid content: None
`docker-compose.override.yml`
```yaml
version: "2"
services:
rng:
user: "4242:4242"
```
</textarea>
.debug[[secure-containers/sampleapp.md](file:///repo/slides/secure-containers/sampleapp.md)]
---
.debug[[secure-containers/sampleapp.md](file:///repo/slides/secure-containers/sampleapp.md)]
---
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/ShippingContainerSFBay.jpg)]
---
name: toc-possible-improvements
class: title
Possible improvements
.nav[
[Previous part](#toc-which-application-needs-to-be-secured)
|
[Back to table of contents](#toc-part-2)
|
[Next part](#toc-other--improvements)
]
.debug[(automatically generated title slide)]
---
# Possible improvements
The app is running ~~fine~~ (It does what it is supposed to do at least)
--
Some improvement areas:
- All containers are running with root privileges
- Too many privileges (`man 7 capabilities`)
- Root filesystem is writeable
--
- Quite a few CVE's (As a result of the build)
.debug[[secure-containers/possible-improvements.md](file:///repo/slides/secure-containers/possible-improvements.md)]
---
## Starting scenario
- Default without `docker-compose.override.yml`
- Containers run with `root` identity
- `/tmp` is writeable
- 'chown' is possible
.debug[[secure-containers/possible-improvements.md](file:///repo/slides/secure-containers/possible-improvements.md)]
---
## Improvement 1
Change user id to 4242. Redis can no longer write to `/data` so we mount a writeable directory on top of it
```yaml
services:
...
rng:
user: "4242:4242"
...
redis:
user: "4242:4242"
tmpfs:
- /data
...
```
.debug[[secure-containers/possible-improvements.md](file:///repo/slides/secure-containers/possible-improvements.md)]
---
## Improvement 2
Lets reduce capabilities to make sure no weird things can happen
```yaml
...
services:
rng:
user: "4242:4242"
cap_drop:
- ALL
hasher:
user: "4242:4242"
cap_drop:
- ALL
...
```
It does not show anything different...
.debug[[secure-containers/possible-improvements.md](file:///repo/slides/secure-containers/possible-improvements.md)]
---
## Improvement 3
Make the root filesystem read only
```yaml
...
services:
rng:
user: "4242:4242"
cap_drop:
- ALL
read_only: true
```
.debug[[secure-containers/possible-improvements.md](file:///repo/slides/secure-containers/possible-improvements.md)]
---
class: pic
.interstitial[![Image separating from the next part](https://gallant-turing-d0d520.netlify.com/containers/aerial-view-of-containers.jpg)]
---
name: toc-other--improvements
class: title
Other improvements
.nav[
[Previous part](#toc-possible-improvements)
|
[Back to table of contents](#toc-part-3)
|
[Next part](#toc-)
]
.debug[(automatically generated title slide)]
---
# Other improvements
What about security of the code / packages?
Choosing the proper build image might make a big difference:
Look at the following two `Dockerfiles`:
```bash
FROM python:latest
RUN pip install redis
RUN pip install requests
COPY worker.py /
CMD ["python", "worker.py"]
```
```bash
FROM python:alpine
RUN pip install redis
RUN pip install requests
COPY worker.py /
CMD ["python", "worker.py"]
```
.debug[[secure-containers/cve.md](file:///repo/slides/secure-containers/cve.md)]
---
The only difference is the base image. But the end result is quite different:
(Scanning is done with `grype`)
| Base image | Image size | CVE's |
|---|---|---|
| python:latest | 888 Mb | 1114 |
| python:alpine | 73,5 Mb | 3 |
--
The 'full' python image has even `gcc` included....
```bash
docker run --rm --entrypoint gcc -it python-latest:latest
gcc: fatal error: no input files
compilation terminated.
docker run --rm --entrypoint gcc python-alpine:latest
docker: Error response from daemon: failed to create shim task: OCI runtime create failed: runc create failed: unable to start container process: exec: "gcc": executable file not found in $PATH: unknown.
```
.debug[[secure-containers/cve.md](file:///repo/slides/secure-containers/cve.md)]
---
Consider a `multistage build`
```bash
FROM python:latest as builder
RUN pip install redis
RUN pip install requests
# Do many other heavy things here
COPY worker.py /
CMD ["python", "worker.py"]
FROM python:alpine as runner
# Copy file from previous build container
COPY --from=builder /worker.py .
RUN pip install redis
RUN pip install requests
# Change UID here
USER 1234
CMD ["python", "worker.py"]
```
.debug[[secure-containers/cve.md](file:///repo/slides/secure-containers/cve.md)]
---
Result:
| Base image | Image size | CVE's |
|---|---|---|
| python:latest | 888 Mb | 1114 |
| python:alpine | 73,5 Mb | 3 |
| python:mulistage | 73,5 Mb | 3 |
.debug[[secure-containers/cve.md](file:///repo/slides/secure-containers/cve.md)]</textarea>
<script src="remark.min.js" type="text/javascript">
</script>
<script type="text/javascript">
var slideshow = remark.create({
ratio: '16:9',
highlightSpans: true,
slideNumberFormat: '%current%/%total%',
slideNumberFormat: '📜 %current%/%total%',
excludedClasses: ["self-paced"]
});
</script>

View File

@@ -29,31 +29,31 @@ Kubernetes<br/>for Admins and Ops<br/>
.debug[
```
D slides/.gitea/workflows/build.yaml
M slides/build.sh
?? k8s/
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-docker.yml.html
?? "slides/intro-bd-helm copy.yml.html"
?? slides/intro-bd-helm.yml
?? slides/intro-bd-helm.yml.html
?? slides/intro-bd-k8s.yml.html
?? slides/intro-container-security.yml
?? slides/intro-container-security.yml.html
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ce3849f
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]

View File

@@ -29,31 +29,31 @@ Kubernetes<br/>for administrators<br/>and operators<br/>
.debug[
```
D slides/.gitea/workflows/build.yaml
M slides/build.sh
?? k8s/
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-docker.yml.html
?? "slides/intro-bd-helm copy.yml.html"
?? slides/intro-bd-helm.yml
?? slides/intro-bd-helm.yml.html
?? slides/intro-bd-k8s.yml.html
?? slides/intro-container-security.yml
?? slides/intro-container-security.yml.html
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ce3849f
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]

View File

@@ -29,31 +29,31 @@ Deploying and Scaling Microservices<br/>with Kubernetes<br/>
.debug[
```
D slides/.gitea/workflows/build.yaml
M slides/build.sh
?? k8s/
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-docker.yml.html
?? "slides/intro-bd-helm copy.yml.html"
?? slides/intro-bd-helm.yml
?? slides/intro-bd-helm.yml.html
?? slides/intro-bd-k8s.yml.html
?? slides/intro-container-security.yml
?? slides/intro-container-security.yml.html
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ce3849f
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]

View File

@@ -29,31 +29,31 @@ Kubernetes 101<br/>
.debug[
```
D slides/.gitea/workflows/build.yaml
M slides/build.sh
?? k8s/
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-docker.yml.html
?? "slides/intro-bd-helm copy.yml.html"
?? slides/intro-bd-helm.yml
?? slides/intro-bd-helm.yml.html
?? slides/intro-bd-k8s.yml.html
?? slides/intro-container-security.yml
?? slides/intro-container-security.yml.html
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ce3849f
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]
@@ -7976,7 +7976,7 @@ The `readme` may or may not have (accurate) explanations for the values.
- Update `my-juice-shop`:
```bash
helm upgrade my-juice-shop juice/my-juice-shop \
helm upgrade my-juice-shop juice/juice-shop \
--set service.type=NodePort
```

View File

@@ -29,31 +29,31 @@ Deploying and Scaling Microservices<br/>with Docker and Kubernetes<br/>
.debug[
```
D slides/.gitea/workflows/build.yaml
M slides/build.sh
?? k8s/
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-docker.yml.html
?? "slides/intro-bd-helm copy.yml.html"
?? slides/intro-bd-helm.yml
?? slides/intro-bd-helm.yml.html
?? slides/intro-bd-k8s.yml.html
?? slides/intro-container-security.yml
?? slides/intro-container-security.yml.html
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ce3849f
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]
@@ -15001,7 +15001,7 @@ The `readme` may or may not have (accurate) explanations for the values.
- Update `my-juice-shop`:
```bash
helm upgrade my-juice-shop juice/my-juice-shop \
helm upgrade my-juice-shop juice/juice-shop \
--set service.type=NodePort
```

View File

@@ -29,31 +29,31 @@ Deploying and Scaling Microservices<br/>with Kubernetes<br/>
.debug[
```
D slides/.gitea/workflows/build.yaml
M slides/build.sh
?? k8s/
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-docker.yml.html
?? "slides/intro-bd-helm copy.yml.html"
?? slides/intro-bd-helm.yml
?? slides/intro-bd-helm.yml.html
?? slides/intro-bd-k8s.yml.html
?? slides/intro-container-security.yml
?? slides/intro-container-security.yml.html
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ce3849f
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]
@@ -11887,7 +11887,7 @@ The `readme` may or may not have (accurate) explanations for the values.
- Update `my-juice-shop`:
```bash
helm upgrade my-juice-shop juice/my-juice-shop \
helm upgrade my-juice-shop juice/juice-shop \
--set service.type=NodePort
```

View File

@@ -0,0 +1,80 @@
# Other improvements
What about security of the code / packages?
Choosing the proper build image might make a big difference:
Look at the following two `Dockerfiles`:
```bash
FROM python:latest
RUN pip install redis
RUN pip install requests
COPY worker.py /
CMD ["python", "worker.py"]
```
```bash
FROM python:alpine
RUN pip install redis
RUN pip install requests
COPY worker.py /
CMD ["python", "worker.py"]
```
---
The only difference is the base image. But the end result is quite different:
(Scanning is done with `grype`)
| Base image | Image size | CVE's |
|---|---|---|
| python:latest | 888 Mb | 1114 |
| python:alpine | 73,5 Mb | 3 |
--
The 'full' python image has even `gcc` included....
```bash
docker run --rm --entrypoint gcc -it python-latest:latest
gcc: fatal error: no input files
compilation terminated.
docker run --rm --entrypoint gcc python-alpine:latest
docker: Error response from daemon: failed to create shim task: OCI runtime create failed: runc create failed: unable to start container process: exec: "gcc": executable file not found in $PATH: unknown.
```
---
Consider a `multistage build`
```bash
FROM python:latest as builder
RUN pip install redis
RUN pip install requests
# Do many other heavy things here
COPY worker.py /
CMD ["python", "worker.py"]
FROM python:alpine as runner
# Copy file from previous build container
COPY --from=builder /worker.py .
RUN pip install redis
RUN pip install requests
# Change UID here
USER 1234
CMD ["python", "worker.py"]
```
---
Result:
| Base image | Image size | CVE's |
|---|---|---|
| python:latest | 888 Mb | 1114 |
| python:alpine | 73,5 Mb | 3 |
| python:mulistage | 73,5 Mb | 3 |

View File

@@ -0,0 +1,87 @@
# Possible improvements
The app is running ~~fine~~ (It does what it is supposed to do at least)
--
Some improvement areas:
- All containers are running with root privileges
- Too many privileges (`man 7 capabilities`)
- Root filesystem is writeable
--
- Quite a few CVE's (As a result of the build)
---
## Starting scenario
- Default without `docker-compose.override.yml`
- Containers run with `root` identity
- `/tmp` is writeable
- 'chown' is possible
---
## Improvement 1
Change user id to 4242. Redis can no longer write to `/data` so we mount a writeable directory on top of it
```yaml
services:
...
rng:
user: "4242:4242"
...
redis:
user: "4242:4242"
tmpfs:
- /data
...
```
---
## Improvement 2
Lets reduce capabilities to make sure no weird things can happen
```yaml
...
services:
rng:
user: "4242:4242"
cap_drop:
- ALL
hasher:
user: "4242:4242"
cap_drop:
- ALL
...
```
It does not show anything different...
---
## Improvement 3
Make the root filesystem read only
```yaml
...
services:
rng:
user: "4242:4242"
cap_drop:
- ALL
read_only: true
```

View File

@@ -68,7 +68,7 @@ class: pic
---
## How do improve the `docker-compose.yml` file
## How to improve the `docker-compose.yml` file
Let's pretend we do not want to modify the original `docker-compose.yml` file
@@ -82,217 +82,38 @@ Let's pretend we do not want to modify the original `docker-compose.yml` file
Let's override values with `docker-compose.override.yml`
---
## Example in `worker/worker.py`
```python
redis = Redis("`redis`")
def get_random_bytes():
r = requests.get("http://`rng`/32")
return r.content
def hash_bytes(data):
r = requests.post("http://`hasher`/",
data=data,
headers={"Content-Type": "application/octet-stream"})
```bash
docker-compose ls
NAME STATUS CONFIG FILES
dockercoins running(5) docker-compose.yml,docker-compose.override.yml
```
---
## Two files are merged together
`docker-compose.yml`
```yaml
version: "2"
services:
rng:
build: rng
ports:
- "8001:80"
```
`docker-compose.override.yml`
```yaml
version: "2"
services:
rng:
user: "4242:4242"
```
(Full source code available [here](
https://@@GITREPO@@/blob/8279a3bce9398f7c1a53bdd95187c53eda4e6435/dockercoins/worker/worker.py#L17
))
---
class: extra-details
## Links, naming, and service discovery
- Containers can have network aliases (resolvable through DNS)
- Compose file version 2+ makes each container reachable through its service name
- Compose file version 1 required "links" sections to accomplish this
- Network aliases are automatically namespaced
- you can have multiple apps declaring and using a service named `database`
- containers in the blue app will resolve `database` to the IP of the blue database
- containers in the green app will resolve `database` to the IP of the green database
---
## Show me the code!
- You can check the GitHub repository with all the materials of this workshop:
<br/>https://@@GITREPO@@
- The application is in the [dockercoins](
https://@@GITREPO@@/tree/master/dockercoins)
subdirectory
- The Compose file ([docker-compose.yml](
https://@@GITREPO@@/blob/master/dockercoins/docker-compose.yml))
lists all 5 services
- `redis` is using an official image from the Docker Hub
- `hasher`, `rng`, `worker`, `webui` are each built from a Dockerfile
- Each service's Dockerfile and source code is in its own directory
(`hasher` is in the [hasher](https://@@GITREPO@@/blob/master/dockercoins/hasher/) directory,
`rng` is in the [rng](https://@@GITREPO@@/blob/master/dockercoins/rng/)
directory, etc.)
---
class: extra-details
## Compose file format version
*This is relevant only if you have used Compose before 2016...*
- Compose 1.6 introduced support for a new Compose file format (aka "v2")
- Services are no longer at the top level, but under a `services` section
- There has to be a `version` key at the top level, with value `"2"` (as a string, not an integer)
- Containers are placed on a dedicated network, making links unnecessary
- There are other minor differences, but upgrade is easy and straightforward
---
## Our application at work
- On the left-hand side, the "rainbow strip" shows the container names
- On the right-hand side, we see the output of our containers
- We can see the `worker` service making requests to `rng` and `hasher`
- For `rng` and `hasher`, we see HTTP access logs
---
## Connecting to the web UI
- "Logs are exciting and fun!" (No-one, ever)
- The `webui` container exposes a web dashboard; let's view it
.lab[
- With a web browser, connect to `node1` on port 8000
- Remember: the `nodeX` aliases are valid only on the nodes themselves
- In your browser, you need to enter the IP address of your node
<!-- ```open http://node1:8000``` -->
]
A drawing area should show up, and after a few seconds, a blue
graph will appear.
---
class: self-paced, extra-details
## If the graph doesn't load
If you just see a `Page not found` error, it might be because your
Docker Engine is running on a different machine. This can be the case if:
- you are using the Docker Toolbox
- you are using a VM (local or remote) created with Docker Machine
- you are controlling a remote Docker Engine
When you run DockerCoins in development mode, the web UI static files
are mapped to the container using a volume. Alas, volumes can only
work on a local environment, or when using Docker Desktop for Mac or Windows.
How to fix this?
Stop the app with `^C`, edit `dockercoins.yml`, comment out the `volumes` section, and try again.
---
class: extra-details
## Why does the speed seem irregular?
- It *looks like* the speed is approximately 4 hashes/second
- Or more precisely: 4 hashes/second, with regular dips down to zero
- Why?
--
class: extra-details
- The app actually has a constant, steady speed: 3.33 hashes/second
<br/>
(which corresponds to 1 hash every 0.3 seconds, for *reasons*)
- Yes, and?
---
class: extra-details
## The reason why this graph is *not awesome*
- The worker doesn't update the counter after every loop, but up to once per second
- The speed is computed by the browser, checking the counter about once per second
- Between two consecutive updates, the counter will increase either by 4, or by 0
- The perceived speed will therefore be 4 - 4 - 4 - 0 - 4 - 4 - 0 etc.
- What can we conclude from this?
--
class: extra-details
- "I'm clearly incapable of writing good frontend code!" 😀 — Jérôme
---
## Stopping the application
- If we interrupt Compose (with `^C`), it will politely ask the Docker Engine to stop the app
- The Docker Engine will send a `TERM` signal to the containers
- If the containers do not exit in a timely manner, the Engine sends a `KILL` signal
.lab[
- Stop the application by hitting `^C`
<!--
```key ^C```
-->
]
--
Some containers exit immediately, others take longer.
The containers that do not handle `SIGTERM` end up being killed after a 10s timeout. If we are very impatient, we can hit `^C` a second time!

View File

@@ -0,0 +1,73 @@
## Accessing these slides now
- We recommend that you open these slides in your browser:
@@SLIDES@@
- Use arrows to move to next/previous slide
(up, down, left, right, page up, page down)
- Type a slide number + ENTER to go to that slide
- The slide number is also visible in the URL bar
(e.g. .../#123 for slide 123)
---
## Accessing these slides later
- Slides will remain online some time.
- You can download the slides using that URL:
@@ZIP@@
(then open the file `@@HTML@@`)
- You will find new versions of these slides (and more) on the upstream repo:
https://container.training/
---
## These slides are open source
- You are welcome to use, re-use, share these slides
- These slides are written in Markdown
- The sources of these slides are available in a public GitHub repository:
https://@@GITREPO@@
- Typos? Mistakes? Questions? Feel free to hover over the bottom of the slide ...
.footnote[👇 Try it! The source file will be shown and you can view it on GitHub and fork and edit it.]
<!--
.lab[
```open https://@@GITREPO@@/tree/master/slides/common/about-slides.md```
]
-->
---
class: extra-details
## Extra details
- This slide has a little magnifying glass in the top left corner
- This magnifying glass indicates slides that provide extra details
- Feel free to skip them if:
- you are in a hurry
- you are new to this and want to avoid cognitive overload
- you want only the most essential information
- You can review these slides another time if you want, they'll be waiting for you ☺

View File

@@ -29,31 +29,31 @@ Container Orchestration<br/>with Docker and Swarm<br/>
.debug[
```
D slides/.gitea/workflows/build.yaml
M slides/build.sh
?? k8s/
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-docker.yml.html
?? "slides/intro-bd-helm copy.yml.html"
?? slides/intro-bd-helm.yml
?? slides/intro-bd-helm.yml.html
?? slides/intro-bd-k8s.yml.html
?? slides/intro-container-security.yml
?? slides/intro-container-security.yml.html
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ce3849f
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]

View File

@@ -29,31 +29,31 @@ Container Orchestration<br/>with Docker and Swarm<br/>
.debug[
```
D slides/.gitea/workflows/build.yaml
M slides/build.sh
?? k8s/
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-docker.yml.html
?? "slides/intro-bd-helm copy.yml.html"
?? slides/intro-bd-helm.yml
?? slides/intro-bd-helm.yml.html
?? slides/intro-bd-k8s.yml.html
?? slides/intro-container-security.yml
?? slides/intro-container-security.yml.html
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ce3849f
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]

View File

@@ -29,31 +29,31 @@ Container Orchestration<br/>with Docker and Swarm<br/>
.debug[
```
D slides/.gitea/workflows/build.yaml
M slides/build.sh
?? k8s/
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-docker.yml.html
?? "slides/intro-bd-helm copy.yml.html"
?? slides/intro-bd-helm.yml
?? slides/intro-bd-helm.yml.html
?? slides/intro-bd-k8s.yml.html
?? slides/intro-container-security.yml
?? slides/intro-container-security.yml.html
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ce3849f
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]

View File

@@ -29,31 +29,31 @@ Container Orchestration<br/>with Docker and Swarm<br/>
.debug[
```
D slides/.gitea/workflows/build.yaml
M slides/build.sh
?? k8s/
M slides/intro-bd-k8s.yml.html
M slides/intro-container-security.yml
M slides/intro-container-security.yml.html
M slides/kadm-fullday.yml.html
M slides/kadm-twodays.yml.html
M slides/kube-fullday.yml.html
M slides/kube-halfday.yml.html
M slides/kube-selfpaced.yml.html
M slides/kube-twodays.yml.html
M slides/secure-containers/sampleapp.md
M slides/swarm-fullday.yml.html
M slides/swarm-halfday.yml.html
M slides/swarm-selfpaced.yml.html
M slides/swarm-video.yml.html
?? .gitea/
?? shpod/
?? slides/intro-bd-docker.yml.html
?? "slides/intro-bd-helm copy.yml.html"
?? slides/intro-bd-helm.yml
?? slides/intro-bd-helm.yml.html
?? slides/intro-bd-k8s.yml.html
?? slides/intro-container-security.yml
?? slides/intro-container-security.yml.html
?? slides/kadm-fullday.yml.html
?? slides/kadm-twodays.yml.html
?? slides/kube-adv.yml.html
?? slides/kube-fullday.yml.html
?? slides/kube-halfday.yml.html
?? slides/kube-selfpaced.yml.html
?? slides/kube-twodays.yml.html
?? slides/swarm-fullday.yml.html
?? slides/swarm-halfday.yml.html
?? slides/swarm-selfpaced.yml.html
?? slides/swarm-video.yml.html
?? slides/secure-containers/cve.md
?? slides/secure-containers/possible-improvements.md
?? slides/shared/about-slides-v2.md
```
These slides have been built from commit: ce3849f
These slides have been built from commit: 4571b5e
[shared/title.md](file:///repo/slides/shared/title.md)]