ЁЯН▒ рдзрдбрд╛ 01 тАФ рдХрдВрдЯреЗрдирд░ рдХрд╛: "рдорд╛рдЭреНрдпрд╛ рдорд╢реАрдирд╡рд░ рдЪрд╛рд▓рддреЗ" рдЪрд╛ рд╢реЗрд╡рдЯ
ЁЯУН рддреБрдореНрд╣реА рдЗрдереЗ рдЖрд╣рд╛рдд: 12 рдкреИрдХреА рдзрдбрд╛ 01 ┬╖ рдкреБрдвреЗ: lesson-02-images-layers
ЁЯУж рдпрд╛ рдмреНрд░рдБрдЪрдордзреНрдпреЗ рдХрд╛рдп рдЖрд╣реЗ
рд╕рдЧрд│реНрдпрд╛рдЪрд╛ рдкрд╛рдпрд╛: рдХрдВрдЯреЗрдирд░ рдореНрд╣рдгрдЬреЗ рдХрд╛рдп рдЖрдгрд┐ рддреЛ рдХрд╛ рдЖрд╣реЗ. рдЦрд▒реНрдпрд╛ files:
- app/server.js тАФ рд╕рдВрдкреВрд░реНрдг рдХреЛрд░реНрд╕рд╕рд╛рдареАрдЪреЗ demo ре▓рдк (рд╢реВрдиреНрдп dependencies, рд╕реНрд╡рддрдГрдЪрд╛ hostname рджрд╛рдЦрд╡рддреЗ)
- app/Dockerfile тАФ рддреНрдпрд╛рдЪреА recipe (рдзрдбрд╛ 03 рддреА рдУрд│-рдУрд│ рд╡рд╛рдЪрддреЛ)
ЁЯзТ 5 рд╡рд░реНрд╖рд╛рдВрдЪреНрдпрд╛ рдореБрд▓рд╛рд▓рд╛ рд╕рдордЬрд╛рд╡рд▓реНрдпрд╛рд╕рд╛рд░рдЦреЗ
рддреБрдордЪреЗ ре▓рдк рддреБрдордЪреНрдпрд╛ laptop рд╡рд░ рдорд╕реНрдд рдЪрд╛рд▓рддреЗ. рддреБрдореНрд╣реА рддреЗ рдореИрддреНрд░рд┐рдгреАрд▓рд╛ рдкрд╛рдард╡рддрд╛тАж ЁЯТе crash. рддрд┐рдЪреНрдпрд╛ laptop рд╡рд░ Node 14 рдЖрд╣реЗ, рддреБрдордЪреНрдпрд╛рдХрдбреЗ Node 20. рддрд┐рдЪреНрдпрд╛рдХрдбреЗ рдПрдХ library рдирд╛рд╣реА. рддрд┐рдЪреЗ paths рд╡реЗрдЧрд│реЗ рдЖрд╣реЗрдд. рдУрд│рдЦреАрдЪреЗ рд╡рд╛рдЯрддреЗ рдирд╛? ЁЯШд
рдЖрддрд╛ рдХрд▓реНрдкрдирд╛ рдХрд░рд╛, рддреБрдордЪреА рдЖрдИ рддреБрдореНрд╣рд╛рд▓рд╛ рдбрдмрд╛ ЁЯН▒ рднрд░реВрди рджреЗрддреЗ тАФ рднрд╛рдд, рдЖрдордЯреА, рдЪрдордЪрд╛, рд░реБрдорд╛рд▓, рддреБрдореНрд╣рд╛рд▓рд╛ рд▓рд╛рдЧрдгрд╛рд░реЗ рд╕рдЧрд│реЗ, рдбрдмреНрдпрд╛рдЪреНрдпрд╛ рдЖрдд. рддреЛ рдбрдмрд╛ рдХреЛрдгрд╛рдЪреНрдпрд╛рд╣реА рдШрд░реА рдЙрдШрдбрд▓рд╛ рддрд░реА рдХрд╛рд╣реА рдлрд░рдХ рдкрдбрдд рдирд╛рд╣реА: рдЬреЗрд╡рдг рдЕрдЧрджреА рддреЗрдЪ рдЕрд╕рддреЗ.
рдХрдВрдЯреЗрдирд░ рдореНрд╣рдгрдЬреЗ рддреБрдордЪреНрдпрд╛ program рд╕рд╛рдареАрдЪрд╛ рдбрдмрд╛: ре▓рдк + Node 20 + libraries
- settings, рд╕рдЧрд│реЗ рдЖрдд рдмрдВрдж рдХреЗрд▓реЗрд▓реЗ. рддреБрдордЪрд╛ laptop, рдореИрддреНрд░рд┐рдгреАрдЪрд╛ laptop, рдПрдЦрд╛рджрд╛ рдореЛрдард╛ AWS server тАФ рддреЛрдЪ рдбрдмрд╛, рддреЗрдЪ рдЬреЗрд╡рдг, рдкреНрд░рддреНрдпреЗрдХ рд╡реЗрд│реА.
рдЕрдЬреВрди рдПрдХ рдЧреБрдкрд┐рдд: рд╣рд╛ рд╕рдВрдЧрдгрдХрд╛рдЪреНрдпрд╛ рдЖрддрд▓рд╛ рдЫреЛрдЯрд╛ рд╕рдВрдЧрдгрдХ рдирд╛рд╣реА (рддреЛ рдЕрд╕рддреЛ virtual machine тАФ рдЯреНрд░рдХрдордзреВрди рдкрд╛рдард╡рд▓реЗрд▓реЗ рд╕рдВрдкреВрд░реНрдг рдШрд░ ЁЯЪЪ). рдХрдВрдЯреЗрдирд░ рддреБрдордЪреНрдпрд╛ рдорд╢реАрдирдЪрд╛ Linux kernel рд╡рд╛рдЯреВрди рдШреЗрддреЛ рдЖрдгрд┐ рдлрдХреНрдд ре▓рдкрд▓рд╛ рд╡реЗрдЧрд│реЗ рдареЗрд╡рддреЛ тАФ рдореНрд╣рдгреВрдирдЪ рддреЛ milliseconds рдордзреНрдпреЗ рд╕реБрд░реВ рд╣реЛрддреЛ рдЖрдгрд┐ рддреНрдпрд╛рдЪреЗ рд╡рдЬрди gigabytes рдирд╡реНрд╣реЗ рддрд░ megabytes рдЕрд╕рддреЗ.
ЁЯЧ║я╕П рдЖрдХреГрддреА
flowchart LR
loose["ЁЯШд unpacked app<br/>works here, crashes there"]
box["ЁЯН▒ container<br/>app + runtime + libs + config<br/>ALL inside the box"]
a["ЁЯТ╗ laptop A тЬЕ"]
b["ЁЯТ╗ laptop B тЬЕ"]
c["тШБя╕П AWS server тЬЕ"]
loose -->|"1 pack everything"| box
box -->|"2 identical"| a
box -->|"2 identical"| b
box -->|"2 identical"| c
тЭУ рдХрд╛рдп
- Container = рд╕реНрд╡рддрдГрдЪреА filesystem, network view рдЖрдгрд┐ dependencies рдЕрд╕рд▓реЗрд▓реА, host рдЪрд╛ kernel рд╡рд╛рдЯреВрди рдШреЗрдгрд╛рд░реА рд╡реЗрдЧрд│реА рдареЗрд╡рд▓реЗрд▓реА process.
- VM рд╡рд┐рд░реБрджреНрдз container: VM рд╕рдВрдкреВрд░реНрдг OS boot рдХрд░рддреЗ (рдорд┐рдирд┐рдЯреЗ, GBs); container рдПрдХ process рд╕реБрд░реВ рдХрд░рддреЛ (milliseconds, MBs). рд╡реЗрдЧрд╡реЗрдЧрд│реНрдпрд╛ рдХрд╛рдорд╛рдВрд╕рд╛рдареА рд╡реЗрдЧрд╡реЗрдЧрд│реА рд╕рд╛рдзрдиреЗ.
- Docker = containers build, run рдЖрдгрд┐ ship рдХрд░рдгрд╛рд░рд╛ рд╕рд╛рдзрдирд╛рдВрдЪрд╛ рд╕рдВрдЪ. рдПрдХрдореЗрд╡ рдирд╛рд╣реА, рдкрдг рдкреНрд░рддреНрдпреЗрдХрдЬрдг рд╕рд░реНрд╡рд╛рдд рдЖрдзреА рд╣рд╛рдЪ рд╢рд┐рдХрддреЛ.
ЁЯза Container тЙа virtual machine
VM App тЖТ libraries тЖТ GUEST OS тЖТ hypervisor тЖТ host
Container App тЖТ libraries тЖТ container runtime тЖТ HOST kernel
рдХрдВрдЯреЗрдирд░ application рдЖрдгрд┐ рддреНрдпрд╛рдЪреНрдпрд╛ user-space dependencies (libraries, runtime, config) рдкреЕрдХ рдХрд░рддреЛ тАФ рддреЛ рд╕рд╛рдзрд╛рд░рдгрдкрдгреЗ host рдЪрд╛ kernel рд╡рд╛рдЯреВрди рдШреЗрддреЛ. рдбрдмреНрдпрд╛рдЪреНрдпрд╛ рдЖрдд рдХреЛрдгрддреАрд╣реА "рдЫреЛрдЯреА operating system" рдирд╕рддреЗ; рдореНрд╣рдгреВрдирдЪ рддреЛ milliseconds рдордзреНрдпреЗ рд╕реБрд░реВ рд╣реЛрддреЛ рдЖрдгрд┐ megabytes рдЗрддрдХрд╛рдЪ рдЕрд╕рддреЛ. рдиреЗрдордХреЗ рд╕рд╛рдВрдЧрд╛рдпрдЪреЗ рддрд░: рддреАрдЪ image рдкреНрд░рддреНрдпреЗрдХ рдорд╢реАрдирд╡рд░ рд╕реБрд╕рдВрдЧрдд application environment рджреЗрддреЗ тАФ рдЦрд╛рд▓рдЪрд╛ kernel, CPU architecture рдЖрдгрд┐ Docker version рдорд╛рддреНрд░ рддрд░реАрд╣реА рд╡реЗрдЧрд│реЗ рдЕрд╕реВ рд╢рдХрддрд╛рдд.
ЁЯдФ рдХрд╛
рдпрд╛ trilogy рдордзрд▓реЗ рдкреНрд░рддреНрдпреЗрдХ tool рдпрд╛рд╡рд░рдЪ рдЙрднреЗ рдЖрд╣реЗ: Kubernetes containers schedule рдХрд░рддреЗ, ECR container images рд╕рд╛рдард╡рддреЗ, ArgoCD рдЕрд╕реЗ manifests deploy рдХрд░рддреЗ рдЬреЗ containers рдЪрд╛рд▓рд╡рддрд╛рдд. рдбрдмреНрдпрд╛рдЪреА рдХрд▓реНрдкрдирд╛ рдкрдХреНрдХреА рдЭрд╛рд▓реА, рдХреА рдкреБрдврдЪреЗ рд╕рдЧрд│реЗ рдлрдХреНрдд рд╡рд╛рд╣рддреБрдХреАрдЪреЗ рдХрд╛рдо рдЖрд╣реЗ. ЁЯЪЪ
ЁЯФз рдХрд╕реЗ (рдпрд╛ repo рдордзреНрдпреЗ)
app/server.js рдореБрджреНрджрд╛рдо dependency-free рдареЗрд╡рд▓реЗ рдЖрд╣реЗ тАФ рдПрдХ file, рд╕рд╛рдзрд╛ Node. рддреЗ рдЖрдкрд▓реНрдпрд╛ hostname рдиреЗ рдЙрддреНрддрд░ рджреЗрддреЗ, рдореНрд╣рдгрдЬреЗ рдкреБрдвреЗ рддреБрдореНрд╣реА 3 рдкреНрд░рддреА рдЪрд╛рд▓рд╡рд╛рд▓ рддреЗрд╡реНрд╣рд╛ рдХреЛрдгрддреНрдпрд╛ рдбрдмреНрдпрд╛рдиреЗ рдЙрддреНрддрд░ рджрд┐рд▓реЗ рддреЗ рдкреНрд░рддреНрдпрдХреНрд╖ рджрд┐рд╕реЗрд▓. рд╣реА рдЫреЛрдЯреА рдпреБрдХреНрддреА рддрд┐рдиреНрд╣реА рдХреЛрд░реНрд╕рдордзреНрдпреЗ рдкреБрдвреЗ рдЪрд╛рд▓рдд рд░рд╛рд╣рддреЗ.
ЁЯзк рдХрд░реВрди рдкрд╛рд╣рд╛
# 0) install Docker Desktop, then prove the pain is real:
node app/server.js # works IF you happen to have Node 20... maybe you don't!
# ^ that's exactly the problem containers solve
# 1) now the lunchbox way тАФ no Node needed on your machine at all:
docker run --rm -p 3000:3000 -v "$PWD/app":/app -w /app node:20-alpine node server.js
curl localhost:3000 # ЁЯН▒ hello from <container-id>
# 2) peek behind the curtain:
docker ps # your running box
docker version # client + engine
тЪая╕П рдиреЗрд╣рдореАрдЪреНрдпрд╛ рдЪреБрдХрд╛
- рдХрдВрдЯреЗрдирд░рдордзреНрдпреЗ "OS рдЕрд╕рддреЗ" рдЕрд╕реЗ рд╕рдордЬрдгреЗ тАФ рддреНрдпрд╛рдд user-space files рдЕрд╕рддрд╛рдд рдЖрдгрд┐ рддреЛ host рдЪрд╛ kernel рд╡рд╛рдЯреВрди рдШреЗрддреЛ
- CPU architecture рдХрд╛рд╣реАрд╣реА рдЕрд╕рд▓реЗ рддрд░реА рдХрдВрдЯреЗрдирд░ рдХреБрдареЗрд╣реА рдЪрд╛рд▓реЗрд▓ рдЕрд╢реА рдЕрдкреЗрдХреНрд╖рд╛ рдХрд░рдгреЗ (arm64 рдЖрдгрд┐ amd64 images рд╡реЗрдЧрд│реНрдпрд╛ рдЕрд╕рддрд╛рдд)
- рдХрдВрдЯреЗрдирд░рд▓рд╛ VM рд╕рд╛рд░рдЦреЗ рд╡рд╛рдЧрд╡рдгреЗ, рддреНрдпрд╛рдд login рдХрд░реВрди рд╣рд╛рддрд╛рдиреЗ configure рдХрд░рдгреЗ тАФ рддреНрдпрд╛рдРрд╡рдЬреА image рдкреБрдиреНрд╣рд╛ build рдХрд░рд╛
тПня╕П рдкреБрдвреЗ
рдЖрдкрдг рдЖрддреНрддрд╛ рд╡рд╛рдкрд░рд▓реЗрд▓реА рддреА node:20-alpine рдЧреЛрд╖реНрдЯ рдореНрд╣рдгрдЬреЗ image тАФ рдПрдХрд╛рд╡рд░ рдПрдХ рд░рдЪрд▓реЗрд▓реНрдпрд╛ рдерд░рд╛рдВрдиреА
рдмрдирд▓реЗрд▓рд╛ рдЧреЛрдард╡рд▓реЗрд▓рд╛ рдбрдмрд╛. рдЖрддрд╛ рдХреЗрдХрдЪреА рдУрд│рдЦ рдХрд░реВрди рдШреЗрдКрдпрд╛. ЁЯОВ
git checkout lesson-02-images-layers