"Zainstaluj Docker", "uruchom docker compose up", "odpal to w kontenerze" — te zdania padają dziś tak często, jak kiedyś "zrób npm install". Docker stał się standardowym elementem workflow, ale dla wielu frontendowców nadal brzmi jak osobny świat DevOps.
W praktyce Docker rozwiązuje bardzo konkretny problem: środowisko uruchomieniowe przestaje zależeć od tego, co masz aktualnie zainstalowane lokalnie. W tym artykule przejdziemy przez podstawy bez mistyki i bez założenia, że chcesz zostać administratorem systemów.
Krótka odpowiedź: Docker pakuje aplikację z jej zależnościami w kontener, który działa identycznie na każdym komputerze. Podstawy dla frontendowca: docker run (uruchom kontener), Dockerfile (zbuduj obraz), docker compose (wiele kontenerów, np. app + baza danych). Najważniejszy use case: lokalny stack dev z bazą PostgreSQL bez globalnej instalacji.
Kontener = aplikacja + zależności
Działa identycznie wszędzie
Podstawowe pojęcia
Image (obraz): Szablon. Read-only. Jak klasa.
Container (kontener): Uruchomiona instancja. Jak obiekt.
Dockerfile: Instrukcja budowania obrazu.
docker compose: Uruchamianie wielu kontenerów.
Volume: Trwałe dane poza cyklem życia kontenera.
Najważniejsza rzecz do zapamiętania: kontener to nie pełna maszyna wirtualna. To izolowany proces z własnym filesystemem, siecią i zależnościami, ale współdzielący kernel hosta.
Instalacja
Pobierz Docker Desktop (macOS/Windows). Docker Desktop zawiera dziś także docker compose.
Na Linuksie możesz zainstalować Dockera z repozytorium dystrybucji lub z oficjalnych paczek:
# Szybki test instalacjidocker run --rm hello-world# Uruchom kontener w tledocker run -d -p 8080:80 nginx# http://localhost:8080 -> nginx# Lista kontenerówdocker ps# Zatrzymajdocker stop <container_id># Logidocker logs <container_id># Wejdź do konteneradocker exec -it <container_id> sh
Najlepiej myśleć o tym tak: docker run bierze obraz i tworzy z niego działający proces. Gdy kontener usuniesz, jego lokalny filesystem zwykle znika razem z nim, chyba że używasz volume.
Kolejność instrukcji nie jest przypadkowa. Najpierw kopiujesz pliki zależności i instalujesz pakiety, a dopiero potem resztę projektu. Dzięki temu Docker lepiej wykorzystuje cache warstw i nie reinstaluje wszystkiego po każdej drobnej zmianie w kodzie.
W tym przykładzie łączymy Node.js z PostgreSQL — najpopularniejszą relacyjną bazą danych w fullstack projektach.
Ważny niuans: samo depends_on nie oznacza jeszcze, że baza jest gotowa na połączenia. Dlatego dodałem healthcheck. I tak w realnej aplikacji warto mieć retry po stronie aplikacji, bo "kontener uruchomiony" nie zawsze znaczy "usługa gotowa".
Development z hot-reload
Code
# compose.dev.ymlservices: app: build: . volumes: - .:/app - /app/node_modules ports: - "3000:3000" command: npm run dev
To klasyczny układ developerski: bind mount mapuje lokalny katalog projektu do kontenera, a osobny mount na /app/node_modules chroni zależności zainstalowane w kontenerze przed nadpisaniem przez hosta.
Komendy czyszczące są wygodne, ale potrafią zabrać Ci obrazy, cache builda i nieużywane wolumeny, których jednak jeszcze potrzebowałeś. Zanim odruchowo użyjesz prune, sprawdź, co dokładnie zostanie usunięte.
Multi-stage build (optymalizacja)
Code
# Build stageFROM node:20-alpine AS builderWORKDIR /appCOPY package*.json ./RUN npm ciCOPY . .RUN npm run build# Production stageFROM node:20-alpineWORKDIR /appCOPY package*.json ./RUN npm ci --omit=devCOPY --from=builder /app/dist ./distCMD ["node", "dist/index.js"]
To podejście zmniejsza obraz i oddziela etap budowania od etapu uruchamiania. W praktyce prawie każdy sensowny obraz produkcyjny powinien być multi-stage.
FAQ
Czym jest Docker i do czego służy?
Docker to platforma do konteneryzacji — pakuje aplikację razem z jej zależnościami (Node.js w konkretnej wersji, biblioteki systemowe, konfiguracja) w izolowany kontener. Kontener działa identycznie na każdym komputerze i serwerze, eliminując problem "u mnie działa, na produkcji nie". Dla frontendowców najważniejszy use case: uruchomienie lokalnej bazy danych bez instalowania PostgreSQL/Redis/MongoDB globalnie.
Jaka różnica między Docker image a kontenerem?
Image (obraz) to read-only szablon — jak klasa lub blueprint. Zawiera system plików, kod aplikacji, środowisko uruchomieniowe. Kontener to uruchomiona instancja image — jak obiekt stworzony z klasy. Możesz uruchomić wiele kontenerów z jednego image. Image budujesz przez docker build, kontenery uruchamiasz przez docker run. Gdy kontener usuniesz, jego lokalny filesystem znika — dane przeżywają restart tylko gdy używasz volumes.
Czym jest docker compose i kiedy go używać?
docker compose to narzędzie do uruchamiania wielu powiązanych kontenerów z jednego pliku konfiguracyjnego (compose.yml). Definiujesz serwisy (np. aplikacja Node.js + baza PostgreSQL + Redis), ich porty, zmienne środowiskowe, volumes i zależności. Jedno polecenie docker compose up -d uruchamia cały stack. Idealne do lokalnego developmentu i prostego deploymentu. Od Docker 20.10+ wbudowany — nie potrzebujesz osobnej instalacji.
Jak skonteneryzować aplikację Node.js?
Stwórz Dockerfile: zacznij od FROM node:20-alpine, ustaw WORKDIR /app, skopiuj package.json i uruchom npm ci, potem skopiuj resztę kodu, expose port i ustaw CMD ["npm", "start"]. Kolejność jest ważna — zależności kopiujesz przed kodem źródłowym, żeby Docker mógł cache'ować tę warstwę i nie reinstalować pakietów przy każdej małej zmianie. Dodaj .dockerignore z node_modules i .next.
Czym jest multi-stage build w Docker?
Multi-stage build dzieli Dockerfile na kilka etapów (stages) — każdy może bazować na innym image. Typowy wzorzec: stage builder używa pełnego Node.js do instalacji zależności i buildu, stage production kopiuje tylko artefakty builda bez devDependencies i narzędzi buildowych. Efekt: znacznie mniejszy obraz produkcyjny (bez webpack, TypeScript, testów), szybszy start kontenera i mniejsza powierzchnia ataku.
Jak uruchomić bazę danych lokalnie przez Docker?
Najprostsza metoda to docker compose z serwisem bazy. W compose.yml dodaj serwis db z image: postgres:14, zmiennymi środowiskowymi (POSTGRES_USER, POSTGRES_PASSWORD, POSTGRES_DB) i volume dla danych. Użyj healthcheck żeby aplikacja czekała na gotowość bazy przed startem. Dane przeżywają restarty kontenerów dzięki named volume. Dostęp: localhost:5432 lub przez nazwę serwisu w sieci Docker (db:5432).
Czym Docker różni się od maszyny wirtualnej?
VM emuluje pełny sprzęt i uruchamia osobny system operacyjny — zajmuje GB RAM i GB na dysku, startuje minutami. Docker kontener współdzieli kernel hosta — uruchamia tylko izolowany proces, zajmuje MB, startuje sekundami. VM daje pełną izolację systemu operacyjnego. Docker daje izolację procesu i środowiska. Docker jest szybszy i lżejszy, VM jest bezpieczniejszy i bardziej izolowany. Dla developmentu i większości deploymentów Docker jest wystarczający.
Najważniejsza korzyść z Dockera nie polega na tym, że "używasz nowoczesnego narzędzia". Polega na tym, że środowisko staje się powtarzalne: ten sam Node, ta sama baza, te same komendy, ten sam efekt u Ciebie, u kolegi i na CI.
Jeśli dopiero zaczynasz, zrób trzy rzeczy:
uruchom pojedynczy kontener przez docker run
zbuduj własny obraz z prostego Dockerfile
połącz aplikację z bazą przez docker compose
To wystarczy, żeby Docker przestał być czarną magią i zaczął być po prostu kolejnym narzędziem w workflow.
Jeśli chcesz uporządkować backendowe fundamenty aplikacji i uniknąć typowych błędów architektonicznych już na starcie, skontaktuj się ze mną. Pomagam przekładać wiedzę techniczną na rozwiązania, które da się sensownie utrzymać i rozwijać.
Maciej Sala — project manager i frontendowiec z doświadczeniem w marketingu internetowym. Na co dzień pracuję z Reactem, Next.js i TypeScriptem, łącząc perspektywę produktową z praktycznym podejściem do kodu. Przez kilka lat związany z branżą gier wideo jako project manager i game designer.
Absolwent historii na Uniwersytecie Jagiellońskim i studiów podyplomowych z marketingu internetowego na Akademii Górniczo-Hutniczej w Krakowie. Poza pracą trenuje na siłowni, maluje figurki i realizuje własne projekty.
Anthropic uderza w Figmę i Adobe — oto Claude Design
Anthropic wypuścił właśnie narzędzie AI do tworzenia stron, landing page'ów i prezentacji z promptu. Oto co wiemy o Claude Design i Opus 4.7 — i co to oznacza dla developerów.
Astro.js vs Next.js — które narzędzie wybrać w 2026 roku?
Fachowe porównanie Astro.js i Next.js z perspektywy developera pracującego na co dzień w Next.js. Architektura, wydajność, SEO, DX, koszty i konkretne use case — z benchmarkami i przykładami kodu.
WordPress → Next.js — migracja treści, redirecty 301 i zachowanie pozycji SEO
Jak przenieść stronę z WordPress na Next.js bez utraty pozycji w Google? Eksport treści, mapowanie URL, redirecty 301, migracja obrazów i weryfikacja indeksacji.