mirror of
https://github.com/jpetazzo/container.training.git
synced 2026-04-23 18:46:32 +00:00
Compare commits
45 Commits
velocitysj
...
oscon2018
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
56f67aedb3 | ||
|
|
cb47280632 | ||
|
|
28863728c2 | ||
|
|
05588a86d9 | ||
|
|
dc341da813 | ||
|
|
1d210ad808 | ||
|
|
76d9adadf5 | ||
|
|
065371fa99 | ||
|
|
e45f21454e | ||
|
|
4d8c13b0bf | ||
|
|
5e6b38e8d1 | ||
|
|
5dd2b6313e | ||
|
|
96bf00c59b | ||
|
|
065310901f | ||
|
|
103261ea35 | ||
|
|
c6fb6f30af | ||
|
|
134d24e23b | ||
|
|
8a8e97f6e2 | ||
|
|
29c1bc47d4 | ||
|
|
8af5a10407 | ||
|
|
8e9991a860 | ||
|
|
8ba5d6d736 | ||
|
|
b3d1e2133d | ||
|
|
b3cf30f804 | ||
|
|
59ffe6b6c8 | ||
|
|
54f1300305 | ||
|
|
b845543e5f | ||
|
|
1b54470046 | ||
|
|
ee2b20926c | ||
|
|
96a76d2a19 | ||
|
|
78ac91fcd5 | ||
|
|
971b5b0e6d | ||
|
|
3393563498 | ||
|
|
94483ebfec | ||
|
|
db5d5878f5 | ||
|
|
2585daac9b | ||
|
|
21043108b3 | ||
|
|
65faa4507c | ||
|
|
644f2b9c7a | ||
|
|
dab9d9fb7e | ||
|
|
139757613b | ||
|
|
10eed2c1c7 | ||
|
|
c4fa75a1da | ||
|
|
847140560f | ||
|
|
1dc07c33ab |
@@ -28,5 +28,5 @@ def rng(how_many_bytes):
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
app.run(host="0.0.0.0", port=80)
|
||||
app.run(host="0.0.0.0", port=80, threaded=False)
|
||||
|
||||
|
||||
@@ -35,7 +35,7 @@ class: extra-details
|
||||
|
||||
- This slide has a little magnifying glass in the top left corner
|
||||
|
||||
- This magnifiying glass indicates slides that provide extra details
|
||||
- This magnifying glass indicates slides that provide extra details
|
||||
|
||||
- Feel free to skip them if:
|
||||
|
||||
|
||||
@@ -15,10 +15,13 @@ TEMPLATE="""<html>
|
||||
|
||||
{% for item in coming_soon %}
|
||||
<tr>
|
||||
<td>{{ item.prettydate }}: {{ item.title }} at {{ item.event }} in {{ item.city }}</td>
|
||||
<td>{{ item.title }}</td>
|
||||
<td>{% if item.slides %}<a class="slides" href="{{ item.slides }}" />{% endif %}</td>
|
||||
<td><a class="attend" href="{{ item.attend }}" /></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="details">Scheduled {{ item.prettydate }} at {{ item.event }} in {{item.city }}.</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
{% endif %}
|
||||
|
||||
@@ -27,10 +30,14 @@ TEMPLATE="""<html>
|
||||
|
||||
{% for item in past_workshops[:5] %}
|
||||
<tr>
|
||||
<td>{{ item.prettydate }}: {{ item.title }} {% if item.event %}at {{ item.event }} {% endif %} {% if item.city %} in {{ item.city }} {% endif %}</td>
|
||||
<td>{{ item.title }}</td>
|
||||
<td><a class="slides" href="{{ item.slides }}" /></td>
|
||||
<td>{% if item.video %}<a class="video" href="{{ item.video }}" />{% endif %}</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="details">Delivered {{ item.prettydate }} at {{ item.event }} in {{item.city }}.</td>
|
||||
</tr>
|
||||
|
||||
{% endfor %}
|
||||
|
||||
{% if past_workshops[5:] %}
|
||||
|
||||
@@ -1,3 +1,12 @@
|
||||
- date: 2018-07-12
|
||||
city: Minneapolis, MN
|
||||
country: us
|
||||
event: devopsdays Minneapolis
|
||||
title: Kubernetes 101
|
||||
speaker: "ashleymcnamara, bketelsen"
|
||||
slides: https://devopsdaysmsp2018.container.training
|
||||
attend: https://www.devopsdays.org/events/2018-minneapolis/registration/
|
||||
|
||||
- date: 2018-10-01
|
||||
city: New York, NY
|
||||
country: us
|
||||
@@ -14,12 +23,22 @@
|
||||
speaker: jpetazzo
|
||||
attend: https://conferences.oreilly.com/velocity/vl-ny/public/schedule/detail/69875
|
||||
|
||||
- date: 2018-09-17
|
||||
country: fr
|
||||
city: Paris
|
||||
event: ENIX SAS
|
||||
speaker: jpetazzo
|
||||
title: Déployer ses applications avec Kubernetes (in French)
|
||||
lang: fr
|
||||
attend: https://enix.io/fr/services/formation/deployer-ses-applications-avec-kubernetes/
|
||||
|
||||
- date: 2018-07-17
|
||||
city: Portland, OR
|
||||
country: us
|
||||
event: OSCON
|
||||
title: Kubernetes 101
|
||||
speaker: bridgetkromhout
|
||||
slides: https://oscon2018.container.training/
|
||||
attend: https://conferences.oreilly.com/oscon/oscon-or/public/schedule/detail/66287
|
||||
|
||||
- date: 2018-06-27
|
||||
@@ -28,6 +47,7 @@
|
||||
event: devopsdays
|
||||
title: Kubernetes 101
|
||||
speaker: bridgetkromhout
|
||||
slides: https://devopsdaysams2018.container.training
|
||||
attend: https://www.devopsdays.org/events/2018-amsterdam/registration/
|
||||
|
||||
- date: 2018-06-12
|
||||
|
||||
@@ -355,7 +355,7 @@ class: extra-details
|
||||
|
||||
## Overriding the `ENTRYPOINT` instruction
|
||||
|
||||
The entry point can be overriden as well.
|
||||
The entry point can be overridden as well.
|
||||
|
||||
```bash
|
||||
$ docker run -it training/ls
|
||||
|
||||
@@ -117,7 +117,7 @@ CONTAINER ID IMAGE ... CREATED STATUS ...
|
||||
|
||||
Many Docker commands will work on container IDs: `docker stop`, `docker rm`...
|
||||
|
||||
If we want to list only the IDs of our containers (without the other colums
|
||||
If we want to list only the IDs of our containers (without the other columns
|
||||
or the header line),
|
||||
we can use the `-q` ("Quiet", "Quick") flag:
|
||||
|
||||
|
||||
@@ -98,7 +98,7 @@ $ curl localhost:32768
|
||||
* We can see that metadata with `docker inspect`:
|
||||
|
||||
```bash
|
||||
$ docker inspect nginx --format {{.Config.ExposedPorts}}
|
||||
$ docker inspect --format '{{.Config.ExposedPorts}}' nginx
|
||||
map[80/tcp:{}]
|
||||
```
|
||||
|
||||
|
||||
@@ -64,7 +64,7 @@ Create this Dockerfile.
|
||||
|
||||
## Testing our C program
|
||||
|
||||
* Create `hello.c` and `Dockerfile` in the same direcotry.
|
||||
* Create `hello.c` and `Dockerfile` in the same directory.
|
||||
|
||||
* Run `docker build -t hello .` in this directory.
|
||||
|
||||
|
||||
@@ -30,7 +30,7 @@
|
||||
|
||||
## Environment variables
|
||||
|
||||
- Most of the tools (CLI, libraries...) connecting to the Docker API can use ennvironment variables.
|
||||
- Most of the tools (CLI, libraries...) connecting to the Docker API can use environment variables.
|
||||
|
||||
- These variables are:
|
||||
|
||||
@@ -40,7 +40,7 @@
|
||||
|
||||
- `DOCKER_CERT_PATH` (path to the keypair and certificate to use for auth)
|
||||
|
||||
- `docker-machine env ...` will generate the variables needed to connect to an host.
|
||||
- `docker-machine env ...` will generate the variables needed to connect to a host.
|
||||
|
||||
- `$(eval docker-machine env ...)` sets these variables in the current shell.
|
||||
|
||||
@@ -50,7 +50,7 @@
|
||||
|
||||
With `docker-machine`, we can:
|
||||
|
||||
- upgrade an host to the latest version of the Docker Engine,
|
||||
- upgrade a host to the latest version of the Docker Engine,
|
||||
|
||||
- start/stop/restart hosts,
|
||||
|
||||
|
||||
@@ -176,7 +176,7 @@ $ docker run -d -v $(pwd):/src -P namer
|
||||
|
||||
* `namer` is the name of the image we will run.
|
||||
|
||||
* We don't specify a command to run because is is already set in the Dockerfile.
|
||||
* We don't specify a command to run because it is already set in the Dockerfile.
|
||||
|
||||
Note: on Windows, replace `$(pwd)` with `%cd%` (or `${pwd}` if you use PowerShell).
|
||||
|
||||
|
||||
@@ -102,7 +102,7 @@ Cons:
|
||||
|
||||
- not very readable
|
||||
|
||||
- some unnecessary files might still remain if the cleanup is not torough
|
||||
- some unnecessary files might still remain if the cleanup is not thorough
|
||||
|
||||
- that layer is expensive (slow to build)
|
||||
|
||||
|
||||
@@ -144,7 +144,7 @@ class: extra-details, deep-dive
|
||||
|
||||
- Also allows to set the NIS domain.
|
||||
|
||||
(If you dont' know what a NIS domain is, you don't have to worry about it!)
|
||||
(If you don't know what a NIS domain is, you don't have to worry about it!)
|
||||
|
||||
- If you're wondering: UTS = UNIX time sharing.
|
||||
|
||||
|
||||
@@ -2,8 +2,8 @@ title: |
|
||||
Kubernetes 101
|
||||
|
||||
#chat: "[Slack](https://dockercommunity.slack.com/messages/C7GKACWDV)"
|
||||
#chat: "[Gitter](https://gitter.im/jpetazzo/training-20180413-paris)"
|
||||
chat: "In person!"
|
||||
chat: "[Gitter](https://gitter.im/jpetazzo/workshop-20180717-portland)"
|
||||
#chat: "In person!"
|
||||
|
||||
gitrepo: github.com/jpetazzo/container.training
|
||||
|
||||
|
||||
@@ -239,7 +239,11 @@ Yes!
|
||||
- namespace (more-or-less isolated group of things)
|
||||
- secret (bundle of sensitive data to be passed to a container)
|
||||
|
||||
And much more! (We can see the full list by running `kubectl get`)
|
||||
And much more!
|
||||
|
||||
- We can see the full list by running `kubectl api-resources`
|
||||
|
||||
(In Kubernetes 1.10 and prior, the command to list API resources was `kubectl get`)
|
||||
|
||||
---
|
||||
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
|
||||
- If we want to connect to our pod(s), we need to create a *service*
|
||||
|
||||
- Once a service is created, `kube-dns` will allow us to resolve it by name
|
||||
- Once a service is created, CoreDNS will allow us to resolve it by name
|
||||
|
||||
(i.e. after creating service `hello`, the name `hello` will resolve to something)
|
||||
|
||||
@@ -46,7 +46,7 @@ Under the hood: `kube-proxy` is using a userland proxy and a bunch of `iptables`
|
||||
|
||||
- `ExternalName`
|
||||
|
||||
- the DNS entry managed by `kube-dns` will just be a `CNAME` to a provided record
|
||||
- the DNS entry managed by CoreDNS will just be a `CNAME` to a provided record
|
||||
- no port, no IP address, no nothing else is allocated
|
||||
|
||||
The `LoadBalancer` type is currently only available on AWS, Azure, and GCE.
|
||||
@@ -123,7 +123,7 @@ Note: please DO NOT call the service `search`. It would collide with the TLD.
|
||||
|
||||
.exercise[
|
||||
|
||||
- Let's obtain the IP address that was allocated for our service, *programatically:*
|
||||
- Let's obtain the IP address that was allocated for our service, *programmatically:*
|
||||
```bash
|
||||
IP=$(kubectl get svc elastic -o go-template --template '{{ .spec.clusterIP }}')
|
||||
```
|
||||
@@ -179,7 +179,7 @@ class: extra-details
|
||||
|
||||
- Since there is no virtual IP address, there is no load balancer either
|
||||
|
||||
- `kube-dns` will return the pods' IP addresses as multiple `A` records
|
||||
- CoreDNS will return the pods' IP addresses as multiple `A` records
|
||||
|
||||
- This gives us an easy way to discover all the replicas for a deployment
|
||||
|
||||
|
||||
@@ -83,7 +83,9 @@
|
||||
|
||||
- `kubectl` has pretty good introspection facilities
|
||||
|
||||
- We can list all available resource types by running `kubectl get`
|
||||
- We can list all available resource types by running `kubectl api-resources`
|
||||
<br/>
|
||||
(In Kubernetes 1.10 and prior, this command used to be `kubectl get`)
|
||||
|
||||
- We can view details about a resource with:
|
||||
```bash
|
||||
@@ -224,7 +226,7 @@ The `kube-system` namespace is used for the control plane.
|
||||
|
||||
- `kube-controller-manager` and `kube-scheduler` are other master components
|
||||
|
||||
- `kube-dns` is an additional component (not mandatory but super useful, so it's there)
|
||||
- `coredns` provides DNS-based service discovery ([replacing kube-dns as of 1.11](https://kubernetes.io/blog/2018/07/10/coredns-ga-for-kubernetes-cluster-dns/))
|
||||
|
||||
- `kube-proxy` is the (per-node) component managing port mappings and such
|
||||
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
|
||||
- [Play With Kubernetes Hands-On Labs](https://medium.com/@marcosnils/introducing-pwk-play-with-k8s-159fcfeb787b)
|
||||
|
||||
- [Azure Container Service](https://docs.microsoft.com/azure/aks/)
|
||||
- [Azure Kubernetes Service](https://docs.microsoft.com/azure/aks/)
|
||||
|
||||
- [Cloud Developer Advocates](https://developer.microsoft.com/advocates/)
|
||||
|
||||
|
||||
@@ -151,7 +151,7 @@ Note: it might take a minute or two for the app to be up and running.
|
||||
|
||||
- A pod in the `default` namespace can communicate with a pod in the `kube-system` namespace
|
||||
|
||||
- `kube-dns` uses a different subdomain for each namespace
|
||||
- CoreDNS uses a different subdomain for each namespace
|
||||
|
||||
- Example: from any pod in the cluster, you can connect to the Kubernetes API with:
|
||||
|
||||
|
||||
@@ -154,19 +154,29 @@ That rollout should be pretty quick. What shows in the web UI?
|
||||
|
||||
--
|
||||
|
||||
Our rollout is stuck. However, the app is not dead (just 10% slower).
|
||||
Our rollout is stuck. However, the app is not dead.
|
||||
|
||||
(After a minute, it will stabilize to be 20-25% slower.)
|
||||
|
||||
---
|
||||
|
||||
## What's going on with our rollout?
|
||||
|
||||
- Why is our app 10% slower?
|
||||
- Why is our app a bit slower?
|
||||
|
||||
- Because `MaxUnavailable=1`, so the rollout terminated 1 replica out of 10 available
|
||||
- Because `MaxUnavailable=25%`
|
||||
|
||||
- Okay, but why do we see 2 new replicas being rolled out?
|
||||
... So the rollout terminated 2 replicas out of 10 available
|
||||
|
||||
- Because `MaxSurge=1`, so in addition to replacing the terminated one, the rollout is also starting one more
|
||||
- Okay, but why do we see 5 new replicas being rolled out?
|
||||
|
||||
- Because `MaxSurge=25%`
|
||||
|
||||
... So in addition to replacing 2 replicas, the rollout is also starting 3 more
|
||||
|
||||
- It rounded down the number of MaxUnavailable pods conservatively,
|
||||
<br/>
|
||||
but the total number of pods being rolled out is allowed to be 25+25=50%
|
||||
|
||||
---
|
||||
|
||||
@@ -176,15 +186,15 @@ class: extra-details
|
||||
|
||||
- We start with 10 pods running for the `worker` deployment
|
||||
|
||||
- Current settings: MaxUnavailable=1 and MaxSurge=1
|
||||
- Current settings: MaxUnavailable=25% and MaxSurge=25%
|
||||
|
||||
- When we start the rollout:
|
||||
|
||||
- one replica is taken down (as per MaxUnavailable=1)
|
||||
- another is created (with the new version) to replace it
|
||||
- another is created (with the new version) per MaxSurge=1
|
||||
- two replicas are taken down (as per MaxUnavailable=25%)
|
||||
- two others are created (with the new version) to replace them
|
||||
- three others are created (with the new version) per MaxSurge=25%)
|
||||
|
||||
- Now we have 9 replicas up and running, and 2 being deployed
|
||||
- Now we have 8 replicas up and running, and 5 being deployed
|
||||
|
||||
- Our rollout is stuck at this point!
|
||||
|
||||
@@ -251,7 +261,7 @@ Note the `3xxxx` port.
|
||||
|
||||
- revert to `v0.1`
|
||||
- be conservative on availability (always have desired number of available workers)
|
||||
- be aggressive on rollout speed (update more than one pod at a time)
|
||||
- go slow on rollout speed (update only one pod at a time)
|
||||
- give some time to our workers to "warm up" before starting more
|
||||
|
||||
The corresponding changes can be expressed in the following YAML snippet:
|
||||
@@ -267,7 +277,7 @@ spec:
|
||||
strategy:
|
||||
rollingUpdate:
|
||||
maxUnavailable: 0
|
||||
maxSurge: 3
|
||||
maxSurge: 1
|
||||
minReadySeconds: 10
|
||||
```
|
||||
]
|
||||
@@ -296,7 +306,7 @@ spec:
|
||||
strategy:
|
||||
rollingUpdate:
|
||||
maxUnavailable: 0
|
||||
maxSurge: 3
|
||||
maxSurge: 1
|
||||
minReadySeconds: 10
|
||||
"
|
||||
kubectl rollout status deployment worker
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
## Versions installed
|
||||
|
||||
- Kubernetes 1.10.4
|
||||
- Kubernetes 1.11.0
|
||||
- Docker Engine 18.03.1-ce
|
||||
- Docker Compose 1.21.1
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ And *then* it is time to look at orchestration!
|
||||
|
||||
- Each of the two `redis` services has its own `ClusterIP`
|
||||
|
||||
- `kube-dns` creates two entries, mapping to these two `ClusterIP` addresses:
|
||||
- CoreDNS creates two entries, mapping to these two `ClusterIP` addresses:
|
||||
|
||||
`redis.blue.svc.cluster.local` and `redis.green.svc.cluster.local`
|
||||
|
||||
|
||||
@@ -1,12 +1,18 @@
|
||||
## Intros
|
||||
|
||||
- Hello! I am:
|
||||
- Hello! We are:
|
||||
|
||||
- .emoji[✨] Bridget ([@bridgetkromhout](https://twitter.com/bridgetkromhout))
|
||||
- .emoji[✨] Bridget Kromhout ([@bridgetkromhout](https://twitter.com/bridgetkromhout))
|
||||
|
||||
- The workshop will run from 13:30-17:00
|
||||
- .emoji[🌟] Joe Laha ([@joelaha](https://twitter.com/joelaha))
|
||||
|
||||
- There will be a break from 15:00-15:30
|
||||
- .emoji[💁🏻♀️] Karen Chu ([@karenhchu](https://twitter.com/karenhchu))
|
||||
|
||||
- .emoji[🐳] Jérôme Petazzoni ([@jpetazzo](https://twitter.com/jpetazzo)) (joining us from Berlin in the chat room!)
|
||||
|
||||
- The workshop will run from 9:00-12:30
|
||||
|
||||
- There will be a break from 10:30-11:00
|
||||
|
||||
- Feel free to interrupt for questions at any time
|
||||
|
||||
@@ -16,7 +22,7 @@
|
||||
|
||||
## Say hi!
|
||||
|
||||
- We encourage networking at [#velocityconf](https://twitter.com/hashtag/velocityconf?f=tweets&vertical=default&src=hash)
|
||||
- We encourage networking at [#oscon](https://twitter.com/hashtag/oscon?f=tweets&vertical=default&src=hash)
|
||||
|
||||
- Take a minute to introduce yourself to your neighbors
|
||||
|
||||
|
||||
@@ -77,7 +77,7 @@ More resources on this topic:
|
||||
|
||||
- It won't be scheduled automatically when constraints are satisfiable again
|
||||
|
||||
- You will have to update the service; you can do a no-op udate with:
|
||||
- You will have to update the service; you can do a no-op update with:
|
||||
```bash
|
||||
docker service update ... --force
|
||||
```
|
||||
|
||||
@@ -386,7 +386,7 @@ class: btw-labels
|
||||
|
||||
- owner of a service (for billing, paging...)
|
||||
|
||||
- corelate Swarm objects together (services, volumes, configs, secrets, etc.)
|
||||
- correlate Swarm objects together (services, volumes, configs, secrets, etc.)
|
||||
|
||||
---
|
||||
|
||||
|
||||
@@ -554,7 +554,7 @@ class: snap
|
||||
|
||||
## Instruct all nodes to join the agreement
|
||||
|
||||
- We dont need another fancy global service!
|
||||
- We don't need another fancy global service!
|
||||
|
||||
- We can join nodes from any existing node of the cluster
|
||||
|
||||
|
||||
@@ -179,7 +179,7 @@ class: self-paced
|
||||
|
||||
- one of the main take-aways was *"you're gonna need a bigger manager"*
|
||||
|
||||
- Testing by the community: [4700 heterogenous nodes all over the 'net](https://sematext.com/blog/2016/11/14/docker-swarm-lessons-from-swarm3k/)
|
||||
- Testing by the community: [4700 heterogeneous nodes all over the 'net](https://sematext.com/blog/2016/11/14/docker-swarm-lessons-from-swarm3k/)
|
||||
|
||||
- it just works
|
||||
|
||||
|
||||
@@ -75,7 +75,7 @@ When enabling user namespaces:
|
||||
|
||||
For practical reasons, when enabling user namespaces, the Docker Engine places containers and images (and everything else) in a different directory.
|
||||
|
||||
As a resut, if you enable user namespaces on an existing installation:
|
||||
As a result, if you enable user namespaces on an existing installation:
|
||||
|
||||
- all containers and images (and e.g. Swarm data) disappear
|
||||
|
||||
|
||||
@@ -302,7 +302,7 @@ class: extra-details, benchmarking
|
||||
|
||||
- Requests are a bit slower in the parallel benchmark
|
||||
|
||||
- It looks like `hasher` is better equiped to deal with concurrency than `rng`
|
||||
- It looks like `hasher` is better equipped to deal with concurrency than `rng`
|
||||
|
||||
---
|
||||
|
||||
|
||||
@@ -69,7 +69,7 @@ class: extra-details
|
||||
|
||||
(containerd, libcontainer, SwarmKit...)
|
||||
|
||||
- More predictible release schedule (see next slide)
|
||||
- More predictable release schedule (see next slide)
|
||||
|
||||
---
|
||||
|
||||
|
||||
Reference in New Issue
Block a user