SlideShare uma empresa Scribd logo
1 de 53
Baixar para ler offline
Przygód z Dockerem ciąg
dalszy
Słów kilka o Dockerze
Bartosz Tkaczewski
email: tkaczu@tsh.io twitter: @btkaczewski github: tkaczu1
Plan prezentacji
Docker - co to jest, jak działa, zalety i jak
zainstalować?
Środowisko developerskie
Jak używacie
Przydatne polecenia
Co na produkcji
2
- co to jest?
Docker to narzędzie, które pozwala umieścić
aplik ację oraz jej zależności w lekkim ,
przenośnym, wirtualnym kontenerze - który
można uruchomić na prawie każdym serwerze .
To gwarantuje, że oprogramowanie będzie zawsze
działać tak samo, niezależnie od architektury,
systemu i środowiska w którym go uruchomi.
3
- Docker VS VM
Maszyny wirtualne
np. Vagrant
Kontenery Docker
- jakie zalety?
Wyeliminujesz SOA#1!
Izolacja aplikacji
Szybkie wdrażanie aplikacji
Łatwość konfiguracji
Wieloplatformowość
Możliwość ponownego użycia
Wygodna obsługa zależności
Społeczność
- jak zainstalować?
Linux:
Ubuntu: https://docs.docker.com/engine/installation/linux/ubuntulinux/
Arch Linux: https://docs.docker.com/engine/installation/linux/archlinux/
Debian: https://docs.docker.com/engine/installation/linux/debian/
Fedora: https://docs.docker.com/engine/installation/linux/fedora/
Mac OS X, macOS
Toolbox (zalecana) - https://docs.docker.com/toolbox/toolbox_install_mac/
Natywny - https://docs.docker.com/docker-for-mac/
Windows
Toolbox (zalecana) - https://docs.docker.com/toolbox/toolbox_install_windows/
Natywny - https://docs.docker.com/docker-for-windows/
- koniecznie zainstaluj
docker-compose:
https://docs.docker.com/compose/install/
Ułatwia zarządzanie kontenerami i ich zależnościami.
Stack całej aplikacji opisany w pliku .yml
docker-machine-nfs
https://github.com/adlogix/docker-machine-nfs
Aktywuje współdzielenie plików przez NFS na maszynie
wirtualnej obsługiwanej przez docker-machine
- środowisko developerskie
Tworzenie maszyny developerskiej - docker-machine create
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master o [17:21:54]
$ docker-machine create --driver=virtualbox --virtualbox-disk-size=10240 --virtualbox-memory=3072 --virtualbox-cpu-count=2
development-machine
Running pre-create checks ...
(development-machine) Latest release for github.com/boot2docker/boot2docker is v1.12.2
(development-machine) Downloading /Users/tkaczu/.docker/machine/cache/boot2docker.iso from https: //github.com/boot2docker/
boot2docker/releases/download/v1.12.2/boot2docker.iso ...
Creating machine ...
(development-machine) Copying /Users/tkaczu/.docker/machine/cache/boot2docker.iso to /Users/tkaczu/.docker/machine/machines/
development-machine/boot2docker.iso ...
(development-machine) Creating VirtualBox VM ...
(development-machine) Creating SSH key ...
(development-machine) Starting the VM ...
(development-machine) Check network to re-create if needed ...
(development-machine) Waiting for an IP ...
Waiting for machine to be running, this may take a few minutes ...
Detecting operating system of created instance ...
Waiting for SSH to be available ...
Detecting the provisioner ...
Provisioning with boot2docker ...
Copying certs to the local machine directory ...
Copying certs to the remote machine ...
Setting Docker configuration on the remote daemon ...
Checking connection to Docker ...
Docker is up and running!
To see how to connect your Docker Client to the Docker Engine running on this virtual machine, run: docker-machine env
development-machine
- środowisko developerskie
Pobranie ustawień maszyny - docker-machine env
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master o [17:24:39]
$ docker-machine env development-machine
export DOCKER_TLS_VERIFY="1"
export DOCKER_HOST="tcp: //192.168.99.101:2376"
export DOCKER_CERT_PATH="/Users/tkaczu/.docker/machine/machines/development-machine"
export DOCKER_MACHINE_NAME="development-machine"
# Run this command to configure your shell:
# eval $(docker-machine env development-machine)
Ustawienie zmiennych środowiskowych maszyny
#tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master o [17:42:30]
$ eval $(docker-machine env development-machine)
- środowisko developerskie
Współdzielenie plików na maszynie developerskiej przez NFS
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master o [18:02:51]
$ docker-machine-nfs development-machine --shared-folder=/Users/tkaczu/Workspace/TSH/Uszanowanko/Docker --nfs-
config="-mapall=tkaczu:staff 192.168.99.100" --mount-
opts="rw,async,noatime,rsize=32768,wsize=32768,proto=tcp,nfsvers=3" -f
[INFO] Configuration:
- Machine Name: development-machine
- Shared Folder: /Users/tkaczu/Workspace/TSH/Uszanowanko/Docker
- Mount Options: rw,async,noatime,rsize=32768,wsize=32768,proto=tcp,nfsvers=3
- Force: true
[INFO] machine presence ... OK
[INFO] machine running ... OK
[INFO] Lookup mandatory properties ... OK
- Machine IP: 192.168.99.101
- Network ID: vboxnet0
- NFSHost IP: 192.168.99.1
[INFO] Configure NFS ...
!!! Sudo will be necessary for editing /etc/exports !!!
[INFO] Configure Docker Machine ... OK
[INFO] Restart Docker Machine ... OK
[INFO] Verify NFS mount ... OK
--- --- --- --- --- --- --- --- --- --- --- --- --- --- --
The docker-machine 'development-machine'
is now mounted with NFS!
ENJOY high speed mounts :D
--- --- --- --- --- --- --- --- --- --- --- --- --- --- --
- poznajmy się!
Dockerfile - opis bazowego konteneru aplikacji
FROM ruby:2.3.1 # Bazowy obraz - zawiera ruby i wszystkie paczki
MAINTAINER "Bartosz 'tkaczu' Tkaczewski"
RUN apt-get update -qq && apt-get upgrade -qq # aktualizujemy nasz image
RUN apt-get install -yq curl git build-essential libpq-dev postgresql-client
RUN curl -sL https: //deb.nodesource.com/setup | bash - && apt-get install -yq nodejs
RUN npm -g install npm@latest-2 # instalujemy node.js i npm
RUN mkdir /up-app # tworzymy katalog dla aplikacji
ADD Gemfile /up-app/Gemfile # Dodaje Gemfile i Gemfile.lock
ADD Gemfile.lock /up-app/Gemfile.lock
WORKDIR /up-app # Wykonuje `cd` do wskazanego katalogu
RUN bundle install # instaluje gemy
EXPOSE 3000
CMD /bin/bash
docker-compose.yml - opis stacku aplikacji
version: ‘2' # wykorzystujemy drugi, nowszy sposób zapsiu pliku
volumes: # sekcja wolumenów
app_data:
services:
postgres_data: # kontener z bazą danych
container_name: up_postgres_data
image: busybox
volumes: # współdzelone pliki i foldery
- /var/lib/postgresql/data
postgres:
container_name: up_postgres
restart: on-failure # kiedy restartować
image: postgres:9.4.4
volumes_from:
- postgres_data
ports:
- “5432:5432" # porty do bindowania
environment: # zmienne środowiskowe używane przez bazowy image
POSTGRES_DB: 'up_docker_development'
POSTGRES_USER: 'up_docker'
POSTGRES_PASSWORD: 'up_docker'
app:
container_name: up_app
build: # opis w jaki sposób ma zostać zbudowany kontener
context: ../ ../.
dockerfile: ./devops/docker/Dockerfile
image: up_app
command: bash -c "rm -rf tmp/pids/server.pid && rails server -b ‘0.0.0.0'"
# komenda wykonywana przez nasz kontener
restart: on-failure
ports:
- "3000:3000"
volumes:
- ../ ../.:/up-app
links: # jakie konenery mają być widoczne przez kontener aplikacji
- postgres:postgres
tty: true
stdin_open: true
Struktura projektu
.
├── Gemfile
├── Gemfile.lock
├── app
├── bin
├── config
├── config.ru
├── db
├── devops
│   └── docker
│   ├── Dockerfile
│   └── docker-compose.yml
├── lib
├── log
├── public
└── vendor
Co dalej?
13
Podstawowe polecenia
docker-compose build - buduje aplikację i jej zależności
docker-compose up - uruchamia aplikację i zależności
docker-compose status - pokazuje status kontenerów i zależności
docker exec - wykonuje polecenie na uruchomionym kontenerze
docker-compose run - wykonuje polecenie uruchamiając nowy kontener
docker attach - podłącza się do działającego kontenera
docker-compose logs oraz docker logs - podgląd logów z kontenerów
docker-compose stop - wyłącza kontenery
docker-compose down - wyłącza i USUWA kontenery
14
docker-compose build - budowanie aplikacji i jej zależności
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x
[23:24:48]
$ docker-compose -f devops/docker/docker-compose.yml build
postgres_data uses an image, skipping
postgres uses an image, skipping
Building app
Step 1 : FROM ruby:2.3.1
Step 2 : MAINTAINER "Bartosz 'tkaczu' Tkaczewski"
Step 3 : RUN apt-get update -qq && apt-get upgrade -qq
Step 4 : RUN apt-get install -yq curl git build-essential libpq-dev postgresql-
client
Step 5 : RUN curl -sL https: //deb.nodesource.com/setup | bash - && apt-get install
-yq nodejs
Step 6 : RUN npm -g install npm@latest-2
Step 7 : RUN mkdir /up-app
Step 8 : ADD Gemfile /up-app/Gemfile
Step 9 : ADD Gemfile.lock /up-app/Gemfile.lock
Step 10 : WORKDIR /up-app
Step 11 : RUN bundle install
Step 12 : EXPOSE 3000
Step 13 : CMD /bin/bash
Removing intermediate container 63f26b37685c
Successfully built f5ddcf5cd5c1
docker-compose up - uruchamia aplikację i jej zależności
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [23:32:09]
$ docker-compose -f devops/docker/docker-compose.yml up -d
Creating network "docker_default" with the default driver
Creating volume "docker_app_data" with default driver
Pulling postgres_data (busybox:latest) ...
latest: Pulling from library/busybox
56bec22e3559: Pull complete
Digest: sha256:29f5d56d12684887bdfa50dcd29fc31eea4aaf4ad3bec43daf19026a7ce69912
Status: Downloaded newer image for busybox:latest
Pulling postgres (postgres:9.4.4) ...
9.4.4: Pulling from library/postgres
Digest: sha256:2380a12b9a90724e278b0fa4e4173774bb729752b7fc85bacb4881d942931d3e
Status: Downloaded newer image for postgres:9.4.4
Creating up_postgres_data
Creating up_postgres
Creating up_app
Rezultat?
17
18
I co teraz?
19
docker-compose run - wykonuje polecenie uruchamiając nowy kontener
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [0:37:28]
$ docker-compose -f devops/docker/docker-compose.yml run --rm app rake db:migrate
== 20160711132854 CreatePosts: migrating === === === === === === === === === === === === ==
-- create_table(:posts)
-> 0.0098s
== 20160711132854 CreatePosts: migrated (0.0102s) === === === === === === === === === ==
== 20160712130514 CreateCkeditorAssets: migrating === === === === === === === === === ==
-- create_table(:ckeditor_assets)
-> 0.0087s
-- add_index("ckeditor_assets", ["assetable_type", "type", "assetable_id"],
{:name =>"idx_ckeditor_assetable_type"})
-> 0.0046s
-- add_index("ckeditor_assets", ["assetable_type", "assetable_id"], {:name =>"idx_ckeditor_assetable"})
-> 0.0053s
== 20160712130514 CreateCkeditorAssets: migrated (0.0221s) === === === === === === ==
docker exec - wykonuje polecenie na uruchomionym kontenerze
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [0:18:27]
$ docker exec -it up_app rake db:migrate
== 20160711132854 CreatePosts: migrating === === === === === === === === === === === === ==
-- create_table(:posts)
-> 0.0101s
== 20160711132854 CreatePosts: migrated (0.0103s) === === === === === === === === === ==
== 20160712130514 CreateCkeditorAssets: migrating === === === === === === === === === ==
-- create_table(:ckeditor_assets)
-> 0.0069s
-- add_index("ckeditor_assets", ["assetable_type", "type", "assetable_id"],
{:name =>"idx_ckeditor_assetable_type"})
-> 0.0042s
-- add_index("ckeditor_assets", ["assetable_type", "assetable_id"], {:name =>"idx_ckeditor_assetable"})
-> 0.0098s
== 20160712130514 CreateCkeditorAssets: migrated (0.0218s) === === === === === === ==
21
22
docker attach - podłącza się do działającego kontenera
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [0:40:40]
$ docker attach up_app
Started GET "/" for 192.168.99.1 at 2016-10-23 22:41:55 +0000
Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
Processing by PostsController#index as HTML
Post Load (0.4ms) SELECT "posts".* FROM "posts"
Rendered posts/index.html.erb within layouts/application (1.6ms)
Completed 200 OK in 102ms (Views: 100.7ms | ActiveRecord: 0.4ms)
Started GET "/posts/new" for 192.168.99.1 at 2016-10-23 22:44:11 +0000
Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
Processing by PostsController#new as HTML
Rendered posts/_form.html.erb (34.7ms)
Rendered posts/new.html.erb within layouts/application (62.5ms)
Completed 200 OK in 247ms (Views: 240.9ms | ActiveRecord: 2.1ms)
Started GET "/assets/ckeditor/config.js?t=FB9E" for 192.168.99.1 at 2016-10-23 22:44:12 +0000
Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
Started GET "/posts" for 192.168.99.1 at 2016-10-23 22:57:11 +0000
Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
Processing by PostsController#index as HTML
[2, 11] in /up-app/app/controllers/posts_controller.rb
2: before_action :find_post, only: [:edit, :update, :show, :delete]
3:
4: # Index action to render all posts
5: def index
6: byebug
=> 7: @posts = Post.all
8: end
9:
10: # New action for creating post
11: def new
(byebug) exit
Completed 500 Internal Server Error in 51610ms (ActiveRecord: 0.0ms)
SystemExit (exit):
app/controllers/posts_controller.rb:7:in `index'
Rendered /usr/local/bundle/gems/actionpack-4.2.6/lib/action_dispatch/middleware/templates/rescues/_source.erb (70.5ms)
Started GET "/assets/posts.self-e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855.css?body=1" for
192.168.99.1 at 2016-10-23 22:44:20 +0000
Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
docker-compose logs -podgląd logów z kontenerów
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [1:03:40] C:1
$ docker-compose -f devops/docker/docker-compose.yml logs --follow --tail="10"
Attaching to up_app, up_postgres, up_postgres_data
up_app | [2016-10-23 23:02:49] INFO WEBrick ::HTTPServer#start: pid=7 port=3000
up_app |
up_app |
up_app | Started GET "/posts" for 192.168.99.1 at 2016-10-23 23:03:43 +0000
up_app | Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1,
127.0.0.0/127.255.255.255
up_app | ActiveRecord ::SchemaMigration Load (0.6ms) SELECT "schema_migrations".* FROM
"schema_migrations"
up_app | Processing by PostsController#index as HTML
up_app | Post Load (0.6ms) SELECT "posts".* FROM "posts"
up_app | Rendered posts/index.html.erb within layouts/application (10.3ms)
up_app | Completed 200 OK in 2695ms (Views: 2678.0ms | ActiveRecord: 3.5ms)
up_postgres_data exited with code 0
up_postgres | LOG: database system is ready to accept connections
up_postgres | LOG: autovacuum launcher started
up_postgres | LOG: received smart shutdown request
up_postgres | LOG: autovacuum launcher shutting down
up_postgres | LOG: shutting down
up_postgres | LOG: database system is shut down
up_postgres | LOG: database system was shut down at 2016-10-23 22:40:30 UTC
up_postgres | LOG: MultiXact member wraparound protections are now enabled
up_postgres | LOG: database system is ready to accept connections
up_postgres | LOG: autovacuum launcher started
docker logs - podgląd logów z konkretnego kontenera
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [1:04:51] C:1
$ docker logs up_app --follow --tail="10"
[2016-10-23 23:02:49] INFO WEBrick ::HTTPServer#start: pid=7 port=3000
Started GET "/posts" for 192.168.99.1 at 2016-10-23 23:03:43 +0000
Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
ActiveRecord ::SchemaMigration Load (0.6ms) SELECT "schema_migrations".* FROM "schema_migrations"
Processing by PostsController#index as HTML
Post Load (0.6ms) SELECT "posts".* FROM "posts"
Rendered posts/index.html.erb within layouts/application (10.3ms)
Completed 200 OK in 2695ms (Views: 2678.0ms | ActiveRecord: 3.5ms)
Started GET "/posts/1" for 192.168.99.1 at 2016-10-23 23:06:44 +0000
Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
Processing by PostsController#show as HTML
Parameters: {"id" =>"1"}
Post Load (0.3ms) SELECT "posts".* FROM "posts" WHERE "posts"."id" = $1 LIMIT 1 [["id", 1]]
Rendered posts/show.html.erb within layouts/application (0.7ms)
Completed 200 OK in 109ms (Views: 97.9ms | ActiveRecord: 0.5ms)
Started GET "/posts/new" for 192.168.99.1 at 2016-10-23 23:06:54 +0000
Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
Processing by PostsController#new as HTML
Rendered posts/_form.html.erb (17.4ms)
Rendered posts/new.html.erb within layouts/application (23.7ms)
Completed 200 OK in 110ms (Views: 109.2ms | ActiveRecord: 0.0ms)
Started POST "/posts" for 192.168.99.1 at 2016-10-23 23:07:10 +0000
Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
Processing by PostsController#create as HTML
Parameters: {"utf8" =>"✓", "authenticity_token" =>"gkd3UEQLg1J+I34uL2BOKqYH5JRMfO+3zz5ahKhlBiyow2NwRwOapRuxq/
st9PATsm01AWvALX47ekwJ0Ya6og ==", "post" =>{"title" =>"Nowy post", "body" =>"<p>Treść nowego posta </p>rn"}, "commit" =>"Create Post"}
(0.2ms) BEGIN
SQL (0.3ms) INSERT INTO "posts" ("title", "body", "created_at", "updated_at") VALUES ($1, $2, $3, $4) RETURNING "id" [["title",
"Nowy post"], ["body", "<p>Treść nowego posta </p>rn"], ["created_at", "2016-10-23 23:07:10.097025"], ["updated_at", "2016-10-23
23:07:10.097025"]]
(1.0ms) COMMIT
Redirected to http: //192.168.99.100:3000/posts/2
Completed 302 Found in 7ms (ActiveRecord: 1.5ms)
Started GET "/posts/2" for 192.168.99.1 at 2016-10-23 23:07:10 +0000
Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
Processing by PostsController#show as HTML
Parameters: {"id" =>"2"}
Post Load (0.3ms) SELECT "posts".* FROM "posts" WHERE "posts"."id" = $1 LIMIT 1 [["id", 2]]
Rendered posts/show.html.erb within layouts/application (0.2ms)
Completed 200 OK in 94ms (Views: 92.2ms | ActiveRecord: 0.3ms)
docker-compose down - wyłącza i USUWA(!!!) kontenery
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [1:36:49]
$ docker-compose -f devops/docker/docker-compose.yml down
Stopping up_app ... done
Stopping up_postgres ... done
Removing up_app ... done
Removing up_postgres ... done
Removing up_postgres_data ... done
Removing network docker_default
docker-compose stop - wyłącza kontenery
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [1:35:38]
$ docker-compose -f devops/docker/docker-compose.yml stop
Stopping up_app ... done
Stopping up_postgres ... done
Co teraz?
Zabawmy się!
Dodajmy ELK stack do
naszej aplikacji
27
ELK Docker
28
https://github.com/willdurand/docker-elk/tree/
kibana-4.1.2
docker-compose.yml - opis stacku aplikacji
version: '2'
volumes:
app_data:
services:
postgres_data:
.. .. ..
postgres:
.. .. ..
app:
.. .. ..
elk:
container_name: up_elk
restart: on-failure
image: willdurand/elk:kibana-4.1.2
ports:
- "8080:80"
volumes:
- ./elk/logstash:/etc/logstash
- ./elk/logstash/patterns:/opt/logstash/patterns
volumes_from:
- app
Struktura projektu
├── Gemfile
├── Gemfile.lock
├── app
├── bin
├── config
├── config.ru
├── db
├── devops
│   └── docker
│   ├── Dockerfile
│   ├── docker-
compose.yml
│   └── elk
│   └── logstash
│   ├──
logstash.conf
│   └── patterns
├── lib
├── log
│   └── development.log
├── public
├── tmp
└── vendor
input {
file {
type => "rails_dev"
path => "/up-app/log/development.log"
start_position => beginning
}
}
output {
elasticsearch {
host => "localhost"
cluster => "logstash"
}
}
logstash.conf - konfiguracja Logstash (zbiera logi)
30
31
Tipsy
32
Jeden proces na
kontener
33
Pamiętaj by zawsze
Dockerfile i docker-
compose.yml miał zapisane
wszystko co potrzeba do
uruchomienia projektu
34
Używaj osobnych plików
dla każdego z środowisk:
development, staging,
production, qa, etc, itd, itp
35
docker-compose.yml -persistent storage - bazy danych
version: ‘2’
volumes:
app_data:
postgres_data:
services:
postgres_data:
container_name: up_postgres_data
image: busybox
volumes: # Mapuje katalog z hosta do katalogu w kontenerze
- ~/PersistedVolumes/up_postgres_data:/var/lib/postgresql/data
postgres:
container_name: up_postgres
restart: on-failure
image: postgres:9.4.4
volumes_from:
- postgres_data
ports:
- “5432:5432"
environment:
POSTGRES_DB: 'up_docker_development'
POSTGRES_USER: 'up_docker'
POSTGRES_PASSWORD: 'up_docker'
app:
container_name: up_app
build:
context: ../ ../.
dockerfile: ./devops/docker/Dockerfile
image: up_app
command: bash -c "rm -rf tmp/pids/server.pid && rails server -b ‘0.0.0.0'"
restart: on-failure
ports:
- "3000:3000"
volumes:
- ../ ../.:/up-app
links:
- postgres:postgres
tty: true
stdin_open: true
Usunięcie “śmieciowych” wolumenów
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [12:03:22]
$ docker volume rm $(docker volume ls -qf dangling=true)
Usunięcie “śmieciowych” kontenerów
# tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [12:01:23]
$ docker images -a -q --filter "dangling=true" | xargs docker rmi --force
docker-compose.yml - dodanie np. Redis
version: ‘2’
volumes:
app_data:
postgres_data:
services:
postgres_data:
.. .. ..
postgres:
.. .. ..
redis: # Definicja konteneru z Redisem
container_name: up_redis
restart: on-failure
image: redis:alpine
ports:
- "6379:6379"
app:
container_name: up_app
build:
context: ../ ../.
dockerfile: ./devops/docker/Dockerfile
image: up_app
command: bash -c "rm -rf tmp/pids/server.pid && rails server -b ‘0.0.0.0'"
restart: on-failure
ports:
- "3000:3000"
volumes:
- ../ ../.:/up-app
links:
- postgres:postgres
- redis:redis # Dodanie konteneru z Redisem jako zależności
tty: true
stdin_open: true
docker-compose.yml - pliki .env
version: '2'
volumes:
app_data:
postgres_data:
services:
postgres_data:
.. .. ..
postgres:
container_name: up_postgres
restart: on-failure
image: postgres:9.4.4
volumes_from:
- postgres_data
ports:
- "5432:5432"
env_file:
- ../ ../env/development.env
redis:
.. .. ..
app:
.. .. ..
Struktura projektu
├── Gemfile
├── Gemfile.lock
├── app
├── bin
├── config
├── config.ru
├── db
├── devops
│   └── docker
│   ├── Dockerfile
│   ├── docker-compose.yml
│   └── elk
│   └── logstash
│   ├── logstash.conf
│   └── patterns
├── env
│   ├── development.env
│   └── sample.env
├── lib
├── log
│   └── development.log
├── public
├── tmp
└── vendor
POSTGRES_USER=up_docker
POSTGRES_PASSWORD=up_docker
POSTGRES_DB=up_docker_development
development.env - plik ze zmiennymi środowiskowymi
Docker na produkcji
40
- deploymenty
Tkaczu way
Budowanie obrazów i korzystanie z rejestrów (Docker
Hub, Docker Registry)
Własne skrypty (Capistrano, Ansible, Fabric, Bash etc.)
Usługi typu CI/CD (Continuous Integration, Continuous
Deployment)
Docker-machine - na sterownikach popularnych
środowisk cloudowych (Digital Ocean, AWS, Azure)
Tkaczu way
Lokalnie:
git commit - commitujemy
git push - pushujemy
docker-compose build - budujemy obrazy
docker-compose push - pushujemy obrazy na prywatny rejestr
Produkcja:
docker-compose stop - zatrzymanie projektu
git pull
docker-compose pull - ściągamy obrazy
docker-compose up - startujemy aplikacje
Docker-machine -Cloud drivers -
AWS
https://docs.docker.com/machine/drivers/aws/
https://docs.docker.com/machine/examples/aws/
http://blog.scottlowe.org/2016/03/22/using-
docker-machine-with-aws/
Gotowe kontenery - produkcja
Nginx-proxy - https://github.com/jwilder/nginx-
proxy
Postgres Backup S3 - https://github.com/schickling/
dockerfiles/tree/master/postgres-backup-s3
Postgres Restore S3 - https://github.com/schickling/
dockerfiles/tree/master/postgres-restore-s3
Mysql Backup S3 - https://github.com/schickling/
dockerfiles/tree/master/mysql-backup-s3
Warto zobaczyć
45
Dry
46
Manager kontenerów dockera w terminalu
https://github.com/moncho/dry
Dry
47
Rancher
48
Umożliwia zarządzanie kontenerami na produkcji oraz
wiele, wiele więcej …
http://docs.rancher.com/rancher/v1.2/en/quick-start-
guide/
49
Dockercraft
50
…
https://github.com/docker/dockercraft
Dockercraft = Minecraft + Docker
51
Repozytorium
https://github.com/
tkaczu/uszanowanko-
docker
52
Dziękuje za uwagę :)
Zapraszam do dyskusji.
53

Mais conteúdo relacionado

Mais procurados

Kubernetes Deployment Tutorial | Kubernetes Tutorial For Beginners | Kubernet...
Kubernetes Deployment Tutorial | Kubernetes Tutorial For Beginners | Kubernet...Kubernetes Deployment Tutorial | Kubernetes Tutorial For Beginners | Kubernet...
Kubernetes Deployment Tutorial | Kubernetes Tutorial For Beginners | Kubernet...Edureka!
 
Role Based Access Controls (RBAC) for SSH and Kubernetes Access with Teleport
Role Based Access Controls (RBAC) for SSH and Kubernetes Access with TeleportRole Based Access Controls (RBAC) for SSH and Kubernetes Access with Teleport
Role Based Access Controls (RBAC) for SSH and Kubernetes Access with TeleportDevOps.com
 
Kubernetes internals (Kubernetes 해부하기)
Kubernetes internals (Kubernetes 해부하기)Kubernetes internals (Kubernetes 해부하기)
Kubernetes internals (Kubernetes 해부하기)DongHyeon Kim
 
Understanding docker networking
Understanding docker networkingUnderstanding docker networking
Understanding docker networkingLorenzo Fontana
 
2014 OpenStack Day in Korea - oVirt and OpenStack Integration and more
2014 OpenStack Day in Korea - oVirt and OpenStack Integration and more2014 OpenStack Day in Korea - oVirt and OpenStack Integration and more
2014 OpenStack Day in Korea - oVirt and OpenStack Integration and moreRogan Kyuseok Lee
 
"Certified Kubernetes Administrator Exam – how it was" by Andrii Fedenishin
"Certified Kubernetes Administrator Exam – how it was" by Andrii Fedenishin"Certified Kubernetes Administrator Exam – how it was" by Andrii Fedenishin
"Certified Kubernetes Administrator Exam – how it was" by Andrii FedenishinKatherine Golovinova
 
DockerとDocker Hubの操作と概念
DockerとDocker Hubの操作と概念DockerとDocker Hubの操作と概念
DockerとDocker Hubの操作と概念Masahito Zembutsu
 
Docker Security workshop slides
Docker Security workshop slidesDocker Security workshop slides
Docker Security workshop slidesDocker, Inc.
 
Cycloudのストレージ紹介と歴史
Cycloudのストレージ紹介と歴史Cycloudのストレージ紹介と歴史
Cycloudのストレージ紹介と歴史Hiroki Chinen
 
9 steps to awesome with kubernetes
9 steps to awesome with kubernetes9 steps to awesome with kubernetes
9 steps to awesome with kubernetesBaraniBuuny
 
kubernetes初心者がKnative Lambda Runtime触ってみた(Kubernetes Novice Tokyo #13 発表資料)
kubernetes初心者がKnative Lambda Runtime触ってみた(Kubernetes Novice Tokyo #13 発表資料)kubernetes初心者がKnative Lambda Runtime触ってみた(Kubernetes Novice Tokyo #13 発表資料)
kubernetes初心者がKnative Lambda Runtime触ってみた(Kubernetes Novice Tokyo #13 発表資料)NTT DATA Technology & Innovation
 
Fluentd and Kafka
Fluentd and KafkaFluentd and Kafka
Fluentd and KafkaN Masahiro
 
Nginx Reverse Proxy with Kafka.pptx
Nginx Reverse Proxy with Kafka.pptxNginx Reverse Proxy with Kafka.pptx
Nginx Reverse Proxy with Kafka.pptxwonyong hwang
 
OVS VXLAN Network Accelaration on OpenStack (VXLAN offload and DPDK) - OpenSt...
OVS VXLAN Network Accelaration on OpenStack (VXLAN offload and DPDK) - OpenSt...OVS VXLAN Network Accelaration on OpenStack (VXLAN offload and DPDK) - OpenSt...
OVS VXLAN Network Accelaration on OpenStack (VXLAN offload and DPDK) - OpenSt...VirtualTech Japan Inc.
 
Portainer.io Intro | Into The Box 2018
Portainer.io Intro | Into The Box 2018Portainer.io Intro | Into The Box 2018
Portainer.io Intro | Into The Box 2018Dillon Slaughter
 
Kubernetes Introduction
Kubernetes IntroductionKubernetes Introduction
Kubernetes IntroductionPeng Xiao
 
PostgreSQLの冗長化について
PostgreSQLの冗長化についてPostgreSQLの冗長化について
PostgreSQLの冗長化についてSoudai Sone
 

Mais procurados (20)

Kubernetes Deployment Tutorial | Kubernetes Tutorial For Beginners | Kubernet...
Kubernetes Deployment Tutorial | Kubernetes Tutorial For Beginners | Kubernet...Kubernetes Deployment Tutorial | Kubernetes Tutorial For Beginners | Kubernet...
Kubernetes Deployment Tutorial | Kubernetes Tutorial For Beginners | Kubernet...
 
Role Based Access Controls (RBAC) for SSH and Kubernetes Access with Teleport
Role Based Access Controls (RBAC) for SSH and Kubernetes Access with TeleportRole Based Access Controls (RBAC) for SSH and Kubernetes Access with Teleport
Role Based Access Controls (RBAC) for SSH and Kubernetes Access with Teleport
 
Kubernetes internals (Kubernetes 해부하기)
Kubernetes internals (Kubernetes 해부하기)Kubernetes internals (Kubernetes 해부하기)
Kubernetes internals (Kubernetes 해부하기)
 
Understanding docker networking
Understanding docker networkingUnderstanding docker networking
Understanding docker networking
 
2014 OpenStack Day in Korea - oVirt and OpenStack Integration and more
2014 OpenStack Day in Korea - oVirt and OpenStack Integration and more2014 OpenStack Day in Korea - oVirt and OpenStack Integration and more
2014 OpenStack Day in Korea - oVirt and OpenStack Integration and more
 
"Certified Kubernetes Administrator Exam – how it was" by Andrii Fedenishin
"Certified Kubernetes Administrator Exam – how it was" by Andrii Fedenishin"Certified Kubernetes Administrator Exam – how it was" by Andrii Fedenishin
"Certified Kubernetes Administrator Exam – how it was" by Andrii Fedenishin
 
Docker introduction
Docker introductionDocker introduction
Docker introduction
 
DockerとDocker Hubの操作と概念
DockerとDocker Hubの操作と概念DockerとDocker Hubの操作と概念
DockerとDocker Hubの操作と概念
 
Docker Security workshop slides
Docker Security workshop slidesDocker Security workshop slides
Docker Security workshop slides
 
Cycloudのストレージ紹介と歴史
Cycloudのストレージ紹介と歴史Cycloudのストレージ紹介と歴史
Cycloudのストレージ紹介と歴史
 
9 steps to awesome with kubernetes
9 steps to awesome with kubernetes9 steps to awesome with kubernetes
9 steps to awesome with kubernetes
 
kubernetes初心者がKnative Lambda Runtime触ってみた(Kubernetes Novice Tokyo #13 発表資料)
kubernetes初心者がKnative Lambda Runtime触ってみた(Kubernetes Novice Tokyo #13 発表資料)kubernetes初心者がKnative Lambda Runtime触ってみた(Kubernetes Novice Tokyo #13 発表資料)
kubernetes初心者がKnative Lambda Runtime触ってみた(Kubernetes Novice Tokyo #13 発表資料)
 
Fluentd and Kafka
Fluentd and KafkaFluentd and Kafka
Fluentd and Kafka
 
Kubernetes 101
Kubernetes 101Kubernetes 101
Kubernetes 101
 
Nginx Reverse Proxy with Kafka.pptx
Nginx Reverse Proxy with Kafka.pptxNginx Reverse Proxy with Kafka.pptx
Nginx Reverse Proxy with Kafka.pptx
 
OVS VXLAN Network Accelaration on OpenStack (VXLAN offload and DPDK) - OpenSt...
OVS VXLAN Network Accelaration on OpenStack (VXLAN offload and DPDK) - OpenSt...OVS VXLAN Network Accelaration on OpenStack (VXLAN offload and DPDK) - OpenSt...
OVS VXLAN Network Accelaration on OpenStack (VXLAN offload and DPDK) - OpenSt...
 
Portainer.io Intro | Into The Box 2018
Portainer.io Intro | Into The Box 2018Portainer.io Intro | Into The Box 2018
Portainer.io Intro | Into The Box 2018
 
Kubernetes Introduction
Kubernetes IntroductionKubernetes Introduction
Kubernetes Introduction
 
Swoole w PHP. Czy to ma sens?
Swoole w PHP. Czy to ma sens?Swoole w PHP. Czy to ma sens?
Swoole w PHP. Czy to ma sens?
 
PostgreSQLの冗長化について
PostgreSQLの冗長化についてPostgreSQLの冗長化について
PostgreSQLの冗長化について
 

Destaque

Confd - Uszanowanko Programowanko
Confd - Uszanowanko ProgramowankoConfd - Uszanowanko Programowanko
Confd - Uszanowanko ProgramowankoThe Software House
 
Dependency Injection w Androidzie
Dependency Injection w AndroidzieDependency Injection w Androidzie
Dependency Injection w AndroidzieThe Software House
 
e2e frameworks - czyli kij ma dwa końce
e2e frameworks - czyli kij ma dwa końcee2e frameworks - czyli kij ma dwa końce
e2e frameworks - czyli kij ma dwa końceThe Software House
 
Deploy appki na iOS, czyli magia publikacji
Deploy appki na iOS, czyli magia publikacjiDeploy appki na iOS, czyli magia publikacji
Deploy appki na iOS, czyli magia publikacjiThe Software House
 
Gherkin - jak zostać poetą w IT
Gherkin - jak zostać poetą w ITGherkin - jak zostać poetą w IT
Gherkin - jak zostać poetą w ITThe Software House
 
Inżynieria społeczna jako element testów bezpieczeństwa - tylko teoria, czy j...
Inżynieria społeczna jako element testów bezpieczeństwa - tylko teoria, czy j...Inżynieria społeczna jako element testów bezpieczeństwa - tylko teoria, czy j...
Inżynieria społeczna jako element testów bezpieczeństwa - tylko teoria, czy j...The Software House
 
Design dla estetycznie ograniczonych
Design dla estetycznie ograniczonychDesign dla estetycznie ograniczonych
Design dla estetycznie ograniczonychThe Software House
 
Wielkie protokoły wielkich ludzi
Wielkie protokoły wielkich ludziWielkie protokoły wielkich ludzi
Wielkie protokoły wielkich ludziThe Software House
 
Praktyczne porady na temat optymalizacji wydajności aplikacji tworzonych z u...
Praktyczne porady na temat optymalizacji wydajności aplikacji tworzonych z u...Praktyczne porady na temat optymalizacji wydajności aplikacji tworzonych z u...
Praktyczne porady na temat optymalizacji wydajności aplikacji tworzonych z u...The Software House
 
Angular 2.0 – Kochaj albo rzuć!
Angular 2.0 – Kochaj albo rzuć!Angular 2.0 – Kochaj albo rzuć!
Angular 2.0 – Kochaj albo rzuć!The Software House
 
Pi razy drzwi - o szacowaniu projektów
Pi razy drzwi - o szacowaniu projektówPi razy drzwi - o szacowaniu projektów
Pi razy drzwi - o szacowaniu projektówThe Software House
 
Gulp.js - alternatywa do Grunta
Gulp.js - alternatywa do GruntaGulp.js - alternatywa do Grunta
Gulp.js - alternatywa do GruntaThe Software House
 
Bitcoin - (nie)udany eksperyment?
Bitcoin - (nie)udany eksperyment?Bitcoin - (nie)udany eksperyment?
Bitcoin - (nie)udany eksperyment?The Software House
 
Tester - przyjaciel czy wróg programisty?
Tester - przyjaciel czy wróg programisty?Tester - przyjaciel czy wróg programisty?
Tester - przyjaciel czy wróg programisty?The Software House
 
Angular restmod – wygodny sposób na komunikację z API
Angular restmod – wygodny sposób na komunikację z APIAngular restmod – wygodny sposób na komunikację z API
Angular restmod – wygodny sposób na komunikację z APIThe Software House
 
AngülarJS – Czyli o czym warto pamiętać programując za Odrą
AngülarJS – Czyli o czym warto pamiętać programując za OdrąAngülarJS – Czyli o czym warto pamiętać programując za Odrą
AngülarJS – Czyli o czym warto pamiętać programując za OdrąThe Software House
 
You Shall Not Pass - Security in Symfony
You Shall Not Pass - Security in SymfonyYou Shall Not Pass - Security in Symfony
You Shall Not Pass - Security in SymfonyThe Software House
 

Destaque (20)

Confd - Uszanowanko Programowanko
Confd - Uszanowanko ProgramowankoConfd - Uszanowanko Programowanko
Confd - Uszanowanko Programowanko
 
Dependency Injection w Androidzie
Dependency Injection w AndroidzieDependency Injection w Androidzie
Dependency Injection w Androidzie
 
e2e frameworks - czyli kij ma dwa końce
e2e frameworks - czyli kij ma dwa końcee2e frameworks - czyli kij ma dwa końce
e2e frameworks - czyli kij ma dwa końce
 
Deployment z Ansible
Deployment z AnsibleDeployment z Ansible
Deployment z Ansible
 
Deploy appki na iOS, czyli magia publikacji
Deploy appki na iOS, czyli magia publikacjiDeploy appki na iOS, czyli magia publikacji
Deploy appki na iOS, czyli magia publikacji
 
Gherkin - jak zostać poetą w IT
Gherkin - jak zostać poetą w ITGherkin - jak zostać poetą w IT
Gherkin - jak zostać poetą w IT
 
TDD w iOS
TDD w iOS TDD w iOS
TDD w iOS
 
Inżynieria społeczna jako element testów bezpieczeństwa - tylko teoria, czy j...
Inżynieria społeczna jako element testów bezpieczeństwa - tylko teoria, czy j...Inżynieria społeczna jako element testów bezpieczeństwa - tylko teoria, czy j...
Inżynieria społeczna jako element testów bezpieczeństwa - tylko teoria, czy j...
 
Design dla estetycznie ograniczonych
Design dla estetycznie ograniczonychDesign dla estetycznie ograniczonych
Design dla estetycznie ograniczonych
 
Wielkie protokoły wielkich ludzi
Wielkie protokoły wielkich ludziWielkie protokoły wielkich ludzi
Wielkie protokoły wielkich ludzi
 
Varnish
VarnishVarnish
Varnish
 
Praktyczne porady na temat optymalizacji wydajności aplikacji tworzonych z u...
Praktyczne porady na temat optymalizacji wydajności aplikacji tworzonych z u...Praktyczne porady na temat optymalizacji wydajności aplikacji tworzonych z u...
Praktyczne porady na temat optymalizacji wydajności aplikacji tworzonych z u...
 
Angular 2.0 – Kochaj albo rzuć!
Angular 2.0 – Kochaj albo rzuć!Angular 2.0 – Kochaj albo rzuć!
Angular 2.0 – Kochaj albo rzuć!
 
Pi razy drzwi - o szacowaniu projektów
Pi razy drzwi - o szacowaniu projektówPi razy drzwi - o szacowaniu projektów
Pi razy drzwi - o szacowaniu projektów
 
Gulp.js - alternatywa do Grunta
Gulp.js - alternatywa do GruntaGulp.js - alternatywa do Grunta
Gulp.js - alternatywa do Grunta
 
Bitcoin - (nie)udany eksperyment?
Bitcoin - (nie)udany eksperyment?Bitcoin - (nie)udany eksperyment?
Bitcoin - (nie)udany eksperyment?
 
Tester - przyjaciel czy wróg programisty?
Tester - przyjaciel czy wróg programisty?Tester - przyjaciel czy wróg programisty?
Tester - przyjaciel czy wróg programisty?
 
Angular restmod – wygodny sposób na komunikację z API
Angular restmod – wygodny sposób na komunikację z APIAngular restmod – wygodny sposób na komunikację z API
Angular restmod – wygodny sposób na komunikację z API
 
AngülarJS – Czyli o czym warto pamiętać programując za Odrą
AngülarJS – Czyli o czym warto pamiętać programując za OdrąAngülarJS – Czyli o czym warto pamiętać programując za Odrą
AngülarJS – Czyli o czym warto pamiętać programując za Odrą
 
You Shall Not Pass - Security in Symfony
You Shall Not Pass - Security in SymfonyYou Shall Not Pass - Security in Symfony
You Shall Not Pass - Security in Symfony
 

Semelhante a Docker

Docker: A New Way to Turbocharging Your Apps Development
Docker: A New Way to Turbocharging Your Apps DevelopmentDocker: A New Way to Turbocharging Your Apps Development
Docker: A New Way to Turbocharging Your Apps Developmentmsyukor
 
[Codelab 2017] Docker 기초 및 활용 방안
[Codelab 2017] Docker 기초 및 활용 방안[Codelab 2017] Docker 기초 및 활용 방안
[Codelab 2017] Docker 기초 및 활용 방안양재동 코드랩
 
Running Docker in Development & Production (DevSum 2015)
Running Docker in Development & Production (DevSum 2015)Running Docker in Development & Production (DevSum 2015)
Running Docker in Development & Production (DevSum 2015)Ben Hall
 
廣宣學堂: 容器進階實務 - Docker進深研究班
廣宣學堂: 容器進階實務 - Docker進深研究班廣宣學堂: 容器進階實務 - Docker進深研究班
廣宣學堂: 容器進階實務 - Docker進深研究班Paul Chao
 
Academy PRO: Docker. Lecture 4
Academy PRO: Docker. Lecture 4Academy PRO: Docker. Lecture 4
Academy PRO: Docker. Lecture 4Binary Studio
 
Docker 進階實務班
Docker 進階實務班Docker 進階實務班
Docker 進階實務班Philip Zheng
 
The Dockerfile Explosion and the Need for Higher Level Tools by Gareth Rushgrove
The Dockerfile Explosion and the Need for Higher Level Tools by Gareth RushgroveThe Dockerfile Explosion and the Need for Higher Level Tools by Gareth Rushgrove
The Dockerfile Explosion and the Need for Higher Level Tools by Gareth RushgroveDocker, Inc.
 
Containerizing Web Application with Docker
Containerizing Web Application with DockerContainerizing Web Application with Docker
Containerizing Web Application with Dockermsyukor
 
Docker engine - Indroduc
Docker engine - IndroducDocker engine - Indroduc
Docker engine - IndroducAl Gifari
 
Docker in everyday development
Docker in everyday developmentDocker in everyday development
Docker in everyday developmentJustyna Ilczuk
 
時代在變 Docker 要會:台北 Docker 一日入門篇
時代在變 Docker 要會:台北 Docker 一日入門篇時代在變 Docker 要會:台北 Docker 一日入門篇
時代在變 Docker 要會:台北 Docker 一日入門篇Philip Zheng
 
Academy PRO: Docker. Part 4
Academy PRO: Docker. Part 4Academy PRO: Docker. Part 4
Academy PRO: Docker. Part 4Binary Studio
 
Docker in Action
Docker in ActionDocker in Action
Docker in ActionAlper Kanat
 
Docker for Web Developers: A Sneak Peek
Docker for Web Developers: A Sneak PeekDocker for Web Developers: A Sneak Peek
Docker for Web Developers: A Sneak Peekmsyukor
 
桃園市教育局Docker技術入門與實作
桃園市教育局Docker技術入門與實作桃園市教育局Docker技術入門與實作
桃園市教育局Docker技術入門與實作Philip Zheng
 

Semelhante a Docker (20)

Docker for dev
Docker for devDocker for dev
Docker for dev
 
Docker: A New Way to Turbocharging Your Apps Development
Docker: A New Way to Turbocharging Your Apps DevelopmentDocker: A New Way to Turbocharging Your Apps Development
Docker: A New Way to Turbocharging Your Apps Development
 
[Codelab 2017] Docker 기초 및 활용 방안
[Codelab 2017] Docker 기초 및 활용 방안[Codelab 2017] Docker 기초 및 활용 방안
[Codelab 2017] Docker 기초 및 활용 방안
 
Running Docker in Development & Production (DevSum 2015)
Running Docker in Development & Production (DevSum 2015)Running Docker in Development & Production (DevSum 2015)
Running Docker in Development & Production (DevSum 2015)
 
廣宣學堂: 容器進階實務 - Docker進深研究班
廣宣學堂: 容器進階實務 - Docker進深研究班廣宣學堂: 容器進階實務 - Docker進深研究班
廣宣學堂: 容器進階實務 - Docker進深研究班
 
Academy PRO: Docker. Lecture 4
Academy PRO: Docker. Lecture 4Academy PRO: Docker. Lecture 4
Academy PRO: Docker. Lecture 4
 
Docker 進階實務班
Docker 進階實務班Docker 進階實務班
Docker 進階實務班
 
The Dockerfile Explosion and the Need for Higher Level Tools by Gareth Rushgrove
The Dockerfile Explosion and the Need for Higher Level Tools by Gareth RushgroveThe Dockerfile Explosion and the Need for Higher Level Tools by Gareth Rushgrove
The Dockerfile Explosion and the Need for Higher Level Tools by Gareth Rushgrove
 
From zero to Docker
From zero to DockerFrom zero to Docker
From zero to Docker
 
Containerizing Web Application with Docker
Containerizing Web Application with DockerContainerizing Web Application with Docker
Containerizing Web Application with Docker
 
Docker engine - Indroduc
Docker engine - IndroducDocker engine - Indroduc
Docker engine - Indroduc
 
How to _docker
How to _dockerHow to _docker
How to _docker
 
Docker in everyday development
Docker in everyday developmentDocker in everyday development
Docker in everyday development
 
Docker
DockerDocker
Docker
 
時代在變 Docker 要會:台北 Docker 一日入門篇
時代在變 Docker 要會:台北 Docker 一日入門篇時代在變 Docker 要會:台北 Docker 一日入門篇
時代在變 Docker 要會:台北 Docker 一日入門篇
 
Academy PRO: Docker. Part 4
Academy PRO: Docker. Part 4Academy PRO: Docker. Part 4
Academy PRO: Docker. Part 4
 
Docker in Action
Docker in ActionDocker in Action
Docker in Action
 
Docker as development environment
Docker as development environmentDocker as development environment
Docker as development environment
 
Docker for Web Developers: A Sneak Peek
Docker for Web Developers: A Sneak PeekDocker for Web Developers: A Sneak Peek
Docker for Web Developers: A Sneak Peek
 
桃園市教育局Docker技術入門與實作
桃園市教育局Docker技術入門與實作桃園市教育局Docker技術入門與實作
桃園市教育局Docker技術入門與實作
 

Mais de The Software House

Jak kraść miliony, czyli o błędach bezpieczeństwa, które mogą spotkać również...
Jak kraść miliony, czyli o błędach bezpieczeństwa, które mogą spotkać również...Jak kraść miliony, czyli o błędach bezpieczeństwa, które mogą spotkać również...
Jak kraść miliony, czyli o błędach bezpieczeństwa, które mogą spotkać również...The Software House
 
Jak efektywnie podejść do certyfikacji w AWS?
Jak efektywnie podejść do certyfikacji w AWS?Jak efektywnie podejść do certyfikacji w AWS?
Jak efektywnie podejść do certyfikacji w AWS?The Software House
 
O co chodzi z tą dostępnością cyfrową?
O co chodzi z tą dostępnością cyfrową?O co chodzi z tą dostępnością cyfrową?
O co chodzi z tą dostępnością cyfrową?The Software House
 
Chat tekstowy z użyciem Amazon Chime
Chat tekstowy z użyciem Amazon ChimeChat tekstowy z użyciem Amazon Chime
Chat tekstowy z użyciem Amazon ChimeThe Software House
 
Jak nie zwariować z architekturą Serverless?
Jak nie zwariować z architekturą Serverless?Jak nie zwariować z architekturą Serverless?
Jak nie zwariować z architekturą Serverless?The Software House
 
Analiza semantyczna artykułów prasowych w 5 sprintów z użyciem AWS
Analiza semantyczna artykułów prasowych w 5 sprintów z użyciem AWSAnaliza semantyczna artykułów prasowych w 5 sprintów z użyciem AWS
Analiza semantyczna artykułów prasowych w 5 sprintów z użyciem AWSThe Software House
 
Feature flags na ratunek projektu w JavaScript
Feature flags na ratunek projektu w JavaScriptFeature flags na ratunek projektu w JavaScript
Feature flags na ratunek projektu w JavaScriptThe Software House
 
Typowanie nominalne w TypeScript
Typowanie nominalne w TypeScriptTypowanie nominalne w TypeScript
Typowanie nominalne w TypeScriptThe Software House
 
Automatyzacja tworzenia frontendu z wykorzystaniem GraphQL
Automatyzacja tworzenia frontendu z wykorzystaniem GraphQLAutomatyzacja tworzenia frontendu z wykorzystaniem GraphQL
Automatyzacja tworzenia frontendu z wykorzystaniem GraphQLThe Software House
 
Serverless Compose vs hurtownia danych
Serverless Compose vs hurtownia danychServerless Compose vs hurtownia danych
Serverless Compose vs hurtownia danychThe Software House
 
Testy API: połączenie z bazą danych czy implementacja w pamięci
Testy API: połączenie z bazą danych czy implementacja w pamięciTesty API: połączenie z bazą danych czy implementacja w pamięci
Testy API: połączenie z bazą danych czy implementacja w pamięciThe Software House
 
Jak skutecznie read model. Case study
Jak skutecznie read model. Case studyJak skutecznie read model. Case study
Jak skutecznie read model. Case studyThe Software House
 
Firestore czyli ognista baza od giganta z Doliny Krzemowej
Firestore czyli ognista baza od giganta z Doliny KrzemowejFirestore czyli ognista baza od giganta z Doliny Krzemowej
Firestore czyli ognista baza od giganta z Doliny KrzemowejThe Software House
 
Jak utrzymać stado Lambd w ryzach
Jak utrzymać stado Lambd w ryzachJak utrzymać stado Lambd w ryzach
Jak utrzymać stado Lambd w ryzachThe Software House
 
O łączeniu Storyblok i Next.js
O łączeniu Storyblok i Next.jsO łączeniu Storyblok i Next.js
O łączeniu Storyblok i Next.jsThe Software House
 
Amazon Step Functions. Sposób na implementację procesów w chmurze
Amazon Step Functions. Sposób na implementację procesów w chmurzeAmazon Step Functions. Sposób na implementację procesów w chmurze
Amazon Step Functions. Sposób na implementację procesów w chmurzeThe Software House
 
Od Figmy do gotowej aplikacji bez linijki kodu
Od Figmy do gotowej aplikacji bez linijki koduOd Figmy do gotowej aplikacji bez linijki kodu
Od Figmy do gotowej aplikacji bez linijki koduThe Software House
 

Mais de The Software House (20)

Jak kraść miliony, czyli o błędach bezpieczeństwa, które mogą spotkać również...
Jak kraść miliony, czyli o błędach bezpieczeństwa, które mogą spotkać również...Jak kraść miliony, czyli o błędach bezpieczeństwa, które mogą spotkać również...
Jak kraść miliony, czyli o błędach bezpieczeństwa, które mogą spotkać również...
 
Uszanowanko Podsumowanko
Uszanowanko PodsumowankoUszanowanko Podsumowanko
Uszanowanko Podsumowanko
 
Jak efektywnie podejść do certyfikacji w AWS?
Jak efektywnie podejść do certyfikacji w AWS?Jak efektywnie podejść do certyfikacji w AWS?
Jak efektywnie podejść do certyfikacji w AWS?
 
O co chodzi z tą dostępnością cyfrową?
O co chodzi z tą dostępnością cyfrową?O co chodzi z tą dostępnością cyfrową?
O co chodzi z tą dostępnością cyfrową?
 
Chat tekstowy z użyciem Amazon Chime
Chat tekstowy z użyciem Amazon ChimeChat tekstowy z użyciem Amazon Chime
Chat tekstowy z użyciem Amazon Chime
 
Migracje danych serverless
Migracje danych serverlessMigracje danych serverless
Migracje danych serverless
 
Jak nie zwariować z architekturą Serverless?
Jak nie zwariować z architekturą Serverless?Jak nie zwariować z architekturą Serverless?
Jak nie zwariować z architekturą Serverless?
 
Analiza semantyczna artykułów prasowych w 5 sprintów z użyciem AWS
Analiza semantyczna artykułów prasowych w 5 sprintów z użyciem AWSAnaliza semantyczna artykułów prasowych w 5 sprintów z użyciem AWS
Analiza semantyczna artykułów prasowych w 5 sprintów z użyciem AWS
 
Feature flags na ratunek projektu w JavaScript
Feature flags na ratunek projektu w JavaScriptFeature flags na ratunek projektu w JavaScript
Feature flags na ratunek projektu w JavaScript
 
Typowanie nominalne w TypeScript
Typowanie nominalne w TypeScriptTypowanie nominalne w TypeScript
Typowanie nominalne w TypeScript
 
Automatyzacja tworzenia frontendu z wykorzystaniem GraphQL
Automatyzacja tworzenia frontendu z wykorzystaniem GraphQLAutomatyzacja tworzenia frontendu z wykorzystaniem GraphQL
Automatyzacja tworzenia frontendu z wykorzystaniem GraphQL
 
Serverless Compose vs hurtownia danych
Serverless Compose vs hurtownia danychServerless Compose vs hurtownia danych
Serverless Compose vs hurtownia danych
 
Testy API: połączenie z bazą danych czy implementacja w pamięci
Testy API: połączenie z bazą danych czy implementacja w pamięciTesty API: połączenie z bazą danych czy implementacja w pamięci
Testy API: połączenie z bazą danych czy implementacja w pamięci
 
Jak skutecznie read model. Case study
Jak skutecznie read model. Case studyJak skutecznie read model. Case study
Jak skutecznie read model. Case study
 
Firestore czyli ognista baza od giganta z Doliny Krzemowej
Firestore czyli ognista baza od giganta z Doliny KrzemowejFirestore czyli ognista baza od giganta z Doliny Krzemowej
Firestore czyli ognista baza od giganta z Doliny Krzemowej
 
Jak utrzymać stado Lambd w ryzach
Jak utrzymać stado Lambd w ryzachJak utrzymać stado Lambd w ryzach
Jak utrzymać stado Lambd w ryzach
 
Jak poskromić AWS?
Jak poskromić AWS?Jak poskromić AWS?
Jak poskromić AWS?
 
O łączeniu Storyblok i Next.js
O łączeniu Storyblok i Next.jsO łączeniu Storyblok i Next.js
O łączeniu Storyblok i Next.js
 
Amazon Step Functions. Sposób na implementację procesów w chmurze
Amazon Step Functions. Sposób na implementację procesów w chmurzeAmazon Step Functions. Sposób na implementację procesów w chmurze
Amazon Step Functions. Sposób na implementację procesów w chmurze
 
Od Figmy do gotowej aplikacji bez linijki kodu
Od Figmy do gotowej aplikacji bez linijki koduOd Figmy do gotowej aplikacji bez linijki kodu
Od Figmy do gotowej aplikacji bez linijki kodu
 

Último

TrustArc Webinar - Unlock the Power of AI-Driven Data Discovery
TrustArc Webinar - Unlock the Power of AI-Driven Data DiscoveryTrustArc Webinar - Unlock the Power of AI-Driven Data Discovery
TrustArc Webinar - Unlock the Power of AI-Driven Data DiscoveryTrustArc
 
Advantages of Hiring UIUX Design Service Providers for Your Business
Advantages of Hiring UIUX Design Service Providers for Your BusinessAdvantages of Hiring UIUX Design Service Providers for Your Business
Advantages of Hiring UIUX Design Service Providers for Your BusinessPixlogix Infotech
 
Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024The Digital Insurer
 
The 7 Things I Know About Cyber Security After 25 Years | April 2024
The 7 Things I Know About Cyber Security After 25 Years | April 2024The 7 Things I Know About Cyber Security After 25 Years | April 2024
The 7 Things I Know About Cyber Security After 25 Years | April 2024Rafal Los
 
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...DianaGray10
 
Exploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone ProcessorsExploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone Processorsdebabhi2
 
Apidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, Adobe
Apidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, AdobeApidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, Adobe
Apidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, Adobeapidays
 
🐬 The future of MySQL is Postgres 🐘
🐬  The future of MySQL is Postgres   🐘🐬  The future of MySQL is Postgres   🐘
🐬 The future of MySQL is Postgres 🐘RTylerCroy
 
2024: Domino Containers - The Next Step. News from the Domino Container commu...
2024: Domino Containers - The Next Step. News from the Domino Container commu...2024: Domino Containers - The Next Step. News from the Domino Container commu...
2024: Domino Containers - The Next Step. News from the Domino Container commu...Martijn de Jong
 
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptxHampshireHUG
 
Real Time Object Detection Using Open CV
Real Time Object Detection Using Open CVReal Time Object Detection Using Open CV
Real Time Object Detection Using Open CVKhem
 
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...
Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...Neo4j
 
Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...apidays
 
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...Miguel Araújo
 
A Year of the Servo Reboot: Where Are We Now?
A Year of the Servo Reboot: Where Are We Now?A Year of the Servo Reboot: Where Are We Now?
A Year of the Servo Reboot: Where Are We Now?Igalia
 
Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024The Digital Insurer
 
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...Drew Madelung
 
TrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law DevelopmentsTrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law DevelopmentsTrustArc
 
Scaling API-first – The story of a global engineering organization
Scaling API-first – The story of a global engineering organizationScaling API-first – The story of a global engineering organization
Scaling API-first – The story of a global engineering organizationRadu Cotescu
 
Tech Trends Report 2024 Future Today Institute.pdf
Tech Trends Report 2024 Future Today Institute.pdfTech Trends Report 2024 Future Today Institute.pdf
Tech Trends Report 2024 Future Today Institute.pdfhans926745
 

Último (20)

TrustArc Webinar - Unlock the Power of AI-Driven Data Discovery
TrustArc Webinar - Unlock the Power of AI-Driven Data DiscoveryTrustArc Webinar - Unlock the Power of AI-Driven Data Discovery
TrustArc Webinar - Unlock the Power of AI-Driven Data Discovery
 
Advantages of Hiring UIUX Design Service Providers for Your Business
Advantages of Hiring UIUX Design Service Providers for Your BusinessAdvantages of Hiring UIUX Design Service Providers for Your Business
Advantages of Hiring UIUX Design Service Providers for Your Business
 
Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024Finology Group – Insurtech Innovation Award 2024
Finology Group – Insurtech Innovation Award 2024
 
The 7 Things I Know About Cyber Security After 25 Years | April 2024
The 7 Things I Know About Cyber Security After 25 Years | April 2024The 7 Things I Know About Cyber Security After 25 Years | April 2024
The 7 Things I Know About Cyber Security After 25 Years | April 2024
 
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
 
Exploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone ProcessorsExploring the Future Potential of AI-Enabled Smartphone Processors
Exploring the Future Potential of AI-Enabled Smartphone Processors
 
Apidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, Adobe
Apidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, AdobeApidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, Adobe
Apidays New York 2024 - Scaling API-first by Ian Reasor and Radu Cotescu, Adobe
 
🐬 The future of MySQL is Postgres 🐘
🐬  The future of MySQL is Postgres   🐘🐬  The future of MySQL is Postgres   🐘
🐬 The future of MySQL is Postgres 🐘
 
2024: Domino Containers - The Next Step. News from the Domino Container commu...
2024: Domino Containers - The Next Step. News from the Domino Container commu...2024: Domino Containers - The Next Step. News from the Domino Container commu...
2024: Domino Containers - The Next Step. News from the Domino Container commu...
 
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
 
Real Time Object Detection Using Open CV
Real Time Object Detection Using Open CVReal Time Object Detection Using Open CV
Real Time Object Detection Using Open CV
 
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...
Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...
 
Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...
 
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...
 
A Year of the Servo Reboot: Where Are We Now?
A Year of the Servo Reboot: Where Are We Now?A Year of the Servo Reboot: Where Are We Now?
A Year of the Servo Reboot: Where Are We Now?
 
Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024Tata AIG General Insurance Company - Insurer Innovation Award 2024
Tata AIG General Insurance Company - Insurer Innovation Award 2024
 
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
 
TrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law DevelopmentsTrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
TrustArc Webinar - Stay Ahead of US State Data Privacy Law Developments
 
Scaling API-first – The story of a global engineering organization
Scaling API-first – The story of a global engineering organizationScaling API-first – The story of a global engineering organization
Scaling API-first – The story of a global engineering organization
 
Tech Trends Report 2024 Future Today Institute.pdf
Tech Trends Report 2024 Future Today Institute.pdfTech Trends Report 2024 Future Today Institute.pdf
Tech Trends Report 2024 Future Today Institute.pdf
 

Docker

  • 1. Przygód z Dockerem ciąg dalszy Słów kilka o Dockerze Bartosz Tkaczewski email: tkaczu@tsh.io twitter: @btkaczewski github: tkaczu1
  • 2. Plan prezentacji Docker - co to jest, jak działa, zalety i jak zainstalować? Środowisko developerskie Jak używacie Przydatne polecenia Co na produkcji 2
  • 3. - co to jest? Docker to narzędzie, które pozwala umieścić aplik ację oraz jej zależności w lekkim , przenośnym, wirtualnym kontenerze - który można uruchomić na prawie każdym serwerze . To gwarantuje, że oprogramowanie będzie zawsze działać tak samo, niezależnie od architektury, systemu i środowiska w którym go uruchomi. 3
  • 4. - Docker VS VM Maszyny wirtualne np. Vagrant Kontenery Docker
  • 5. - jakie zalety? Wyeliminujesz SOA#1! Izolacja aplikacji Szybkie wdrażanie aplikacji Łatwość konfiguracji Wieloplatformowość Możliwość ponownego użycia Wygodna obsługa zależności Społeczność
  • 6. - jak zainstalować? Linux: Ubuntu: https://docs.docker.com/engine/installation/linux/ubuntulinux/ Arch Linux: https://docs.docker.com/engine/installation/linux/archlinux/ Debian: https://docs.docker.com/engine/installation/linux/debian/ Fedora: https://docs.docker.com/engine/installation/linux/fedora/ Mac OS X, macOS Toolbox (zalecana) - https://docs.docker.com/toolbox/toolbox_install_mac/ Natywny - https://docs.docker.com/docker-for-mac/ Windows Toolbox (zalecana) - https://docs.docker.com/toolbox/toolbox_install_windows/ Natywny - https://docs.docker.com/docker-for-windows/
  • 7. - koniecznie zainstaluj docker-compose: https://docs.docker.com/compose/install/ Ułatwia zarządzanie kontenerami i ich zależnościami. Stack całej aplikacji opisany w pliku .yml docker-machine-nfs https://github.com/adlogix/docker-machine-nfs Aktywuje współdzielenie plików przez NFS na maszynie wirtualnej obsługiwanej przez docker-machine
  • 8. - środowisko developerskie Tworzenie maszyny developerskiej - docker-machine create # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master o [17:21:54] $ docker-machine create --driver=virtualbox --virtualbox-disk-size=10240 --virtualbox-memory=3072 --virtualbox-cpu-count=2 development-machine Running pre-create checks ... (development-machine) Latest release for github.com/boot2docker/boot2docker is v1.12.2 (development-machine) Downloading /Users/tkaczu/.docker/machine/cache/boot2docker.iso from https: //github.com/boot2docker/ boot2docker/releases/download/v1.12.2/boot2docker.iso ... Creating machine ... (development-machine) Copying /Users/tkaczu/.docker/machine/cache/boot2docker.iso to /Users/tkaczu/.docker/machine/machines/ development-machine/boot2docker.iso ... (development-machine) Creating VirtualBox VM ... (development-machine) Creating SSH key ... (development-machine) Starting the VM ... (development-machine) Check network to re-create if needed ... (development-machine) Waiting for an IP ... Waiting for machine to be running, this may take a few minutes ... Detecting operating system of created instance ... Waiting for SSH to be available ... Detecting the provisioner ... Provisioning with boot2docker ... Copying certs to the local machine directory ... Copying certs to the remote machine ... Setting Docker configuration on the remote daemon ... Checking connection to Docker ... Docker is up and running! To see how to connect your Docker Client to the Docker Engine running on this virtual machine, run: docker-machine env development-machine
  • 9. - środowisko developerskie Pobranie ustawień maszyny - docker-machine env # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master o [17:24:39] $ docker-machine env development-machine export DOCKER_TLS_VERIFY="1" export DOCKER_HOST="tcp: //192.168.99.101:2376" export DOCKER_CERT_PATH="/Users/tkaczu/.docker/machine/machines/development-machine" export DOCKER_MACHINE_NAME="development-machine" # Run this command to configure your shell: # eval $(docker-machine env development-machine) Ustawienie zmiennych środowiskowych maszyny #tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master o [17:42:30] $ eval $(docker-machine env development-machine)
  • 10. - środowisko developerskie Współdzielenie plików na maszynie developerskiej przez NFS # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master o [18:02:51] $ docker-machine-nfs development-machine --shared-folder=/Users/tkaczu/Workspace/TSH/Uszanowanko/Docker --nfs- config="-mapall=tkaczu:staff 192.168.99.100" --mount- opts="rw,async,noatime,rsize=32768,wsize=32768,proto=tcp,nfsvers=3" -f [INFO] Configuration: - Machine Name: development-machine - Shared Folder: /Users/tkaczu/Workspace/TSH/Uszanowanko/Docker - Mount Options: rw,async,noatime,rsize=32768,wsize=32768,proto=tcp,nfsvers=3 - Force: true [INFO] machine presence ... OK [INFO] machine running ... OK [INFO] Lookup mandatory properties ... OK - Machine IP: 192.168.99.101 - Network ID: vboxnet0 - NFSHost IP: 192.168.99.1 [INFO] Configure NFS ... !!! Sudo will be necessary for editing /etc/exports !!! [INFO] Configure Docker Machine ... OK [INFO] Restart Docker Machine ... OK [INFO] Verify NFS mount ... OK --- --- --- --- --- --- --- --- --- --- --- --- --- --- -- The docker-machine 'development-machine' is now mounted with NFS! ENJOY high speed mounts :D --- --- --- --- --- --- --- --- --- --- --- --- --- --- --
  • 11. - poznajmy się! Dockerfile - opis bazowego konteneru aplikacji FROM ruby:2.3.1 # Bazowy obraz - zawiera ruby i wszystkie paczki MAINTAINER "Bartosz 'tkaczu' Tkaczewski" RUN apt-get update -qq && apt-get upgrade -qq # aktualizujemy nasz image RUN apt-get install -yq curl git build-essential libpq-dev postgresql-client RUN curl -sL https: //deb.nodesource.com/setup | bash - && apt-get install -yq nodejs RUN npm -g install npm@latest-2 # instalujemy node.js i npm RUN mkdir /up-app # tworzymy katalog dla aplikacji ADD Gemfile /up-app/Gemfile # Dodaje Gemfile i Gemfile.lock ADD Gemfile.lock /up-app/Gemfile.lock WORKDIR /up-app # Wykonuje `cd` do wskazanego katalogu RUN bundle install # instaluje gemy EXPOSE 3000 CMD /bin/bash
  • 12. docker-compose.yml - opis stacku aplikacji version: ‘2' # wykorzystujemy drugi, nowszy sposób zapsiu pliku volumes: # sekcja wolumenów app_data: services: postgres_data: # kontener z bazą danych container_name: up_postgres_data image: busybox volumes: # współdzelone pliki i foldery - /var/lib/postgresql/data postgres: container_name: up_postgres restart: on-failure # kiedy restartować image: postgres:9.4.4 volumes_from: - postgres_data ports: - “5432:5432" # porty do bindowania environment: # zmienne środowiskowe używane przez bazowy image POSTGRES_DB: 'up_docker_development' POSTGRES_USER: 'up_docker' POSTGRES_PASSWORD: 'up_docker' app: container_name: up_app build: # opis w jaki sposób ma zostać zbudowany kontener context: ../ ../. dockerfile: ./devops/docker/Dockerfile image: up_app command: bash -c "rm -rf tmp/pids/server.pid && rails server -b ‘0.0.0.0'" # komenda wykonywana przez nasz kontener restart: on-failure ports: - "3000:3000" volumes: - ../ ../.:/up-app links: # jakie konenery mają być widoczne przez kontener aplikacji - postgres:postgres tty: true stdin_open: true Struktura projektu . ├── Gemfile ├── Gemfile.lock ├── app ├── bin ├── config ├── config.ru ├── db ├── devops │   └── docker │   ├── Dockerfile │   └── docker-compose.yml ├── lib ├── log ├── public └── vendor
  • 14. Podstawowe polecenia docker-compose build - buduje aplikację i jej zależności docker-compose up - uruchamia aplikację i zależności docker-compose status - pokazuje status kontenerów i zależności docker exec - wykonuje polecenie na uruchomionym kontenerze docker-compose run - wykonuje polecenie uruchamiając nowy kontener docker attach - podłącza się do działającego kontenera docker-compose logs oraz docker logs - podgląd logów z kontenerów docker-compose stop - wyłącza kontenery docker-compose down - wyłącza i USUWA kontenery 14
  • 15. docker-compose build - budowanie aplikacji i jej zależności # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [23:24:48] $ docker-compose -f devops/docker/docker-compose.yml build postgres_data uses an image, skipping postgres uses an image, skipping Building app Step 1 : FROM ruby:2.3.1 Step 2 : MAINTAINER "Bartosz 'tkaczu' Tkaczewski" Step 3 : RUN apt-get update -qq && apt-get upgrade -qq Step 4 : RUN apt-get install -yq curl git build-essential libpq-dev postgresql- client Step 5 : RUN curl -sL https: //deb.nodesource.com/setup | bash - && apt-get install -yq nodejs Step 6 : RUN npm -g install npm@latest-2 Step 7 : RUN mkdir /up-app Step 8 : ADD Gemfile /up-app/Gemfile Step 9 : ADD Gemfile.lock /up-app/Gemfile.lock Step 10 : WORKDIR /up-app Step 11 : RUN bundle install Step 12 : EXPOSE 3000 Step 13 : CMD /bin/bash Removing intermediate container 63f26b37685c Successfully built f5ddcf5cd5c1
  • 16. docker-compose up - uruchamia aplikację i jej zależności # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [23:32:09] $ docker-compose -f devops/docker/docker-compose.yml up -d Creating network "docker_default" with the default driver Creating volume "docker_app_data" with default driver Pulling postgres_data (busybox:latest) ... latest: Pulling from library/busybox 56bec22e3559: Pull complete Digest: sha256:29f5d56d12684887bdfa50dcd29fc31eea4aaf4ad3bec43daf19026a7ce69912 Status: Downloaded newer image for busybox:latest Pulling postgres (postgres:9.4.4) ... 9.4.4: Pulling from library/postgres Digest: sha256:2380a12b9a90724e278b0fa4e4173774bb729752b7fc85bacb4881d942931d3e Status: Downloaded newer image for postgres:9.4.4 Creating up_postgres_data Creating up_postgres Creating up_app
  • 18. 18
  • 20. docker-compose run - wykonuje polecenie uruchamiając nowy kontener # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [0:37:28] $ docker-compose -f devops/docker/docker-compose.yml run --rm app rake db:migrate == 20160711132854 CreatePosts: migrating === === === === === === === === === === === === == -- create_table(:posts) -> 0.0098s == 20160711132854 CreatePosts: migrated (0.0102s) === === === === === === === === === == == 20160712130514 CreateCkeditorAssets: migrating === === === === === === === === === == -- create_table(:ckeditor_assets) -> 0.0087s -- add_index("ckeditor_assets", ["assetable_type", "type", "assetable_id"], {:name =>"idx_ckeditor_assetable_type"}) -> 0.0046s -- add_index("ckeditor_assets", ["assetable_type", "assetable_id"], {:name =>"idx_ckeditor_assetable"}) -> 0.0053s == 20160712130514 CreateCkeditorAssets: migrated (0.0221s) === === === === === === == docker exec - wykonuje polecenie na uruchomionym kontenerze # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [0:18:27] $ docker exec -it up_app rake db:migrate == 20160711132854 CreatePosts: migrating === === === === === === === === === === === === == -- create_table(:posts) -> 0.0101s == 20160711132854 CreatePosts: migrated (0.0103s) === === === === === === === === === == == 20160712130514 CreateCkeditorAssets: migrating === === === === === === === === === == -- create_table(:ckeditor_assets) -> 0.0069s -- add_index("ckeditor_assets", ["assetable_type", "type", "assetable_id"], {:name =>"idx_ckeditor_assetable_type"}) -> 0.0042s -- add_index("ckeditor_assets", ["assetable_type", "assetable_id"], {:name =>"idx_ckeditor_assetable"}) -> 0.0098s == 20160712130514 CreateCkeditorAssets: migrated (0.0218s) === === === === === === ==
  • 21. 21
  • 22. 22
  • 23. docker attach - podłącza się do działającego kontenera # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [0:40:40] $ docker attach up_app Started GET "/" for 192.168.99.1 at 2016-10-23 22:41:55 +0000 Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255 Processing by PostsController#index as HTML Post Load (0.4ms) SELECT "posts".* FROM "posts" Rendered posts/index.html.erb within layouts/application (1.6ms) Completed 200 OK in 102ms (Views: 100.7ms | ActiveRecord: 0.4ms) Started GET "/posts/new" for 192.168.99.1 at 2016-10-23 22:44:11 +0000 Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255 Processing by PostsController#new as HTML Rendered posts/_form.html.erb (34.7ms) Rendered posts/new.html.erb within layouts/application (62.5ms) Completed 200 OK in 247ms (Views: 240.9ms | ActiveRecord: 2.1ms) Started GET "/assets/ckeditor/config.js?t=FB9E" for 192.168.99.1 at 2016-10-23 22:44:12 +0000 Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255 Started GET "/posts" for 192.168.99.1 at 2016-10-23 22:57:11 +0000 Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255 Processing by PostsController#index as HTML [2, 11] in /up-app/app/controllers/posts_controller.rb 2: before_action :find_post, only: [:edit, :update, :show, :delete] 3: 4: # Index action to render all posts 5: def index 6: byebug => 7: @posts = Post.all 8: end 9: 10: # New action for creating post 11: def new (byebug) exit Completed 500 Internal Server Error in 51610ms (ActiveRecord: 0.0ms) SystemExit (exit): app/controllers/posts_controller.rb:7:in `index' Rendered /usr/local/bundle/gems/actionpack-4.2.6/lib/action_dispatch/middleware/templates/rescues/_source.erb (70.5ms) Started GET "/assets/posts.self-e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855.css?body=1" for 192.168.99.1 at 2016-10-23 22:44:20 +0000 Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
  • 24. docker-compose logs -podgląd logów z kontenerów # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [1:03:40] C:1 $ docker-compose -f devops/docker/docker-compose.yml logs --follow --tail="10" Attaching to up_app, up_postgres, up_postgres_data up_app | [2016-10-23 23:02:49] INFO WEBrick ::HTTPServer#start: pid=7 port=3000 up_app | up_app | up_app | Started GET "/posts" for 192.168.99.1 at 2016-10-23 23:03:43 +0000 up_app | Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255 up_app | ActiveRecord ::SchemaMigration Load (0.6ms) SELECT "schema_migrations".* FROM "schema_migrations" up_app | Processing by PostsController#index as HTML up_app | Post Load (0.6ms) SELECT "posts".* FROM "posts" up_app | Rendered posts/index.html.erb within layouts/application (10.3ms) up_app | Completed 200 OK in 2695ms (Views: 2678.0ms | ActiveRecord: 3.5ms) up_postgres_data exited with code 0 up_postgres | LOG: database system is ready to accept connections up_postgres | LOG: autovacuum launcher started up_postgres | LOG: received smart shutdown request up_postgres | LOG: autovacuum launcher shutting down up_postgres | LOG: shutting down up_postgres | LOG: database system is shut down up_postgres | LOG: database system was shut down at 2016-10-23 22:40:30 UTC up_postgres | LOG: MultiXact member wraparound protections are now enabled up_postgres | LOG: database system is ready to accept connections up_postgres | LOG: autovacuum launcher started
  • 25. docker logs - podgląd logów z konkretnego kontenera # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [1:04:51] C:1 $ docker logs up_app --follow --tail="10" [2016-10-23 23:02:49] INFO WEBrick ::HTTPServer#start: pid=7 port=3000 Started GET "/posts" for 192.168.99.1 at 2016-10-23 23:03:43 +0000 Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255 ActiveRecord ::SchemaMigration Load (0.6ms) SELECT "schema_migrations".* FROM "schema_migrations" Processing by PostsController#index as HTML Post Load (0.6ms) SELECT "posts".* FROM "posts" Rendered posts/index.html.erb within layouts/application (10.3ms) Completed 200 OK in 2695ms (Views: 2678.0ms | ActiveRecord: 3.5ms) Started GET "/posts/1" for 192.168.99.1 at 2016-10-23 23:06:44 +0000 Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255 Processing by PostsController#show as HTML Parameters: {"id" =>"1"} Post Load (0.3ms) SELECT "posts".* FROM "posts" WHERE "posts"."id" = $1 LIMIT 1 [["id", 1]] Rendered posts/show.html.erb within layouts/application (0.7ms) Completed 200 OK in 109ms (Views: 97.9ms | ActiveRecord: 0.5ms) Started GET "/posts/new" for 192.168.99.1 at 2016-10-23 23:06:54 +0000 Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255 Processing by PostsController#new as HTML Rendered posts/_form.html.erb (17.4ms) Rendered posts/new.html.erb within layouts/application (23.7ms) Completed 200 OK in 110ms (Views: 109.2ms | ActiveRecord: 0.0ms) Started POST "/posts" for 192.168.99.1 at 2016-10-23 23:07:10 +0000 Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255 Processing by PostsController#create as HTML Parameters: {"utf8" =>"✓", "authenticity_token" =>"gkd3UEQLg1J+I34uL2BOKqYH5JRMfO+3zz5ahKhlBiyow2NwRwOapRuxq/ st9PATsm01AWvALX47ekwJ0Ya6og ==", "post" =>{"title" =>"Nowy post", "body" =>"<p>Treść nowego posta </p>rn"}, "commit" =>"Create Post"} (0.2ms) BEGIN SQL (0.3ms) INSERT INTO "posts" ("title", "body", "created_at", "updated_at") VALUES ($1, $2, $3, $4) RETURNING "id" [["title", "Nowy post"], ["body", "<p>Treść nowego posta </p>rn"], ["created_at", "2016-10-23 23:07:10.097025"], ["updated_at", "2016-10-23 23:07:10.097025"]] (1.0ms) COMMIT Redirected to http: //192.168.99.100:3000/posts/2 Completed 302 Found in 7ms (ActiveRecord: 1.5ms) Started GET "/posts/2" for 192.168.99.1 at 2016-10-23 23:07:10 +0000 Cannot render console from 192.168.99.1! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255 Processing by PostsController#show as HTML Parameters: {"id" =>"2"} Post Load (0.3ms) SELECT "posts".* FROM "posts" WHERE "posts"."id" = $1 LIMIT 1 [["id", 2]] Rendered posts/show.html.erb within layouts/application (0.2ms) Completed 200 OK in 94ms (Views: 92.2ms | ActiveRecord: 0.3ms)
  • 26. docker-compose down - wyłącza i USUWA(!!!) kontenery # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [1:36:49] $ docker-compose -f devops/docker/docker-compose.yml down Stopping up_app ... done Stopping up_postgres ... done Removing up_app ... done Removing up_postgres ... done Removing up_postgres_data ... done Removing network docker_default docker-compose stop - wyłącza kontenery # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [1:35:38] $ docker-compose -f devops/docker/docker-compose.yml stop Stopping up_app ... done Stopping up_postgres ... done
  • 27. Co teraz? Zabawmy się! Dodajmy ELK stack do naszej aplikacji 27
  • 29. docker-compose.yml - opis stacku aplikacji version: '2' volumes: app_data: services: postgres_data: .. .. .. postgres: .. .. .. app: .. .. .. elk: container_name: up_elk restart: on-failure image: willdurand/elk:kibana-4.1.2 ports: - "8080:80" volumes: - ./elk/logstash:/etc/logstash - ./elk/logstash/patterns:/opt/logstash/patterns volumes_from: - app Struktura projektu ├── Gemfile ├── Gemfile.lock ├── app ├── bin ├── config ├── config.ru ├── db ├── devops │   └── docker │   ├── Dockerfile │   ├── docker- compose.yml │   └── elk │   └── logstash │   ├── logstash.conf │   └── patterns ├── lib ├── log │   └── development.log ├── public ├── tmp └── vendor input { file { type => "rails_dev" path => "/up-app/log/development.log" start_position => beginning } } output { elasticsearch { host => "localhost" cluster => "logstash" } } logstash.conf - konfiguracja Logstash (zbiera logi)
  • 30. 30
  • 31. 31
  • 34. Pamiętaj by zawsze Dockerfile i docker- compose.yml miał zapisane wszystko co potrzeba do uruchomienia projektu 34
  • 35. Używaj osobnych plików dla każdego z środowisk: development, staging, production, qa, etc, itd, itp 35
  • 36. docker-compose.yml -persistent storage - bazy danych version: ‘2’ volumes: app_data: postgres_data: services: postgres_data: container_name: up_postgres_data image: busybox volumes: # Mapuje katalog z hosta do katalogu w kontenerze - ~/PersistedVolumes/up_postgres_data:/var/lib/postgresql/data postgres: container_name: up_postgres restart: on-failure image: postgres:9.4.4 volumes_from: - postgres_data ports: - “5432:5432" environment: POSTGRES_DB: 'up_docker_development' POSTGRES_USER: 'up_docker' POSTGRES_PASSWORD: 'up_docker' app: container_name: up_app build: context: ../ ../. dockerfile: ./devops/docker/Dockerfile image: up_app command: bash -c "rm -rf tmp/pids/server.pid && rails server -b ‘0.0.0.0'" restart: on-failure ports: - "3000:3000" volumes: - ../ ../.:/up-app links: - postgres:postgres tty: true stdin_open: true
  • 37. Usunięcie “śmieciowych” wolumenów # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [12:03:22] $ docker volume rm $(docker volume ls -qf dangling=true) Usunięcie “śmieciowych” kontenerów # tkaczu @ TkaczBook in ~/Workspace/TSH/Uszanowanko/Docker on git:master x [12:01:23] $ docker images -a -q --filter "dangling=true" | xargs docker rmi --force
  • 38. docker-compose.yml - dodanie np. Redis version: ‘2’ volumes: app_data: postgres_data: services: postgres_data: .. .. .. postgres: .. .. .. redis: # Definicja konteneru z Redisem container_name: up_redis restart: on-failure image: redis:alpine ports: - "6379:6379" app: container_name: up_app build: context: ../ ../. dockerfile: ./devops/docker/Dockerfile image: up_app command: bash -c "rm -rf tmp/pids/server.pid && rails server -b ‘0.0.0.0'" restart: on-failure ports: - "3000:3000" volumes: - ../ ../.:/up-app links: - postgres:postgres - redis:redis # Dodanie konteneru z Redisem jako zależności tty: true stdin_open: true
  • 39. docker-compose.yml - pliki .env version: '2' volumes: app_data: postgres_data: services: postgres_data: .. .. .. postgres: container_name: up_postgres restart: on-failure image: postgres:9.4.4 volumes_from: - postgres_data ports: - "5432:5432" env_file: - ../ ../env/development.env redis: .. .. .. app: .. .. .. Struktura projektu ├── Gemfile ├── Gemfile.lock ├── app ├── bin ├── config ├── config.ru ├── db ├── devops │   └── docker │   ├── Dockerfile │   ├── docker-compose.yml │   └── elk │   └── logstash │   ├── logstash.conf │   └── patterns ├── env │   ├── development.env │   └── sample.env ├── lib ├── log │   └── development.log ├── public ├── tmp └── vendor POSTGRES_USER=up_docker POSTGRES_PASSWORD=up_docker POSTGRES_DB=up_docker_development development.env - plik ze zmiennymi środowiskowymi
  • 41. - deploymenty Tkaczu way Budowanie obrazów i korzystanie z rejestrów (Docker Hub, Docker Registry) Własne skrypty (Capistrano, Ansible, Fabric, Bash etc.) Usługi typu CI/CD (Continuous Integration, Continuous Deployment) Docker-machine - na sterownikach popularnych środowisk cloudowych (Digital Ocean, AWS, Azure)
  • 42. Tkaczu way Lokalnie: git commit - commitujemy git push - pushujemy docker-compose build - budujemy obrazy docker-compose push - pushujemy obrazy na prywatny rejestr Produkcja: docker-compose stop - zatrzymanie projektu git pull docker-compose pull - ściągamy obrazy docker-compose up - startujemy aplikacje
  • 43. Docker-machine -Cloud drivers - AWS https://docs.docker.com/machine/drivers/aws/ https://docs.docker.com/machine/examples/aws/ http://blog.scottlowe.org/2016/03/22/using- docker-machine-with-aws/
  • 44. Gotowe kontenery - produkcja Nginx-proxy - https://github.com/jwilder/nginx- proxy Postgres Backup S3 - https://github.com/schickling/ dockerfiles/tree/master/postgres-backup-s3 Postgres Restore S3 - https://github.com/schickling/ dockerfiles/tree/master/postgres-restore-s3 Mysql Backup S3 - https://github.com/schickling/ dockerfiles/tree/master/mysql-backup-s3
  • 46. Dry 46 Manager kontenerów dockera w terminalu https://github.com/moncho/dry
  • 48. Rancher 48 Umożliwia zarządzanie kontenerami na produkcji oraz wiele, wiele więcej … http://docs.rancher.com/rancher/v1.2/en/quick-start- guide/
  • 49. 49
  • 51. Dockercraft = Minecraft + Docker 51
  • 53. Dziękuje za uwagę :) Zapraszam do dyskusji. 53