LEMP Stack — Nginx + MySQL + PHP-FPM na Ubuntu
Opublikowano: 9 kwietnia 2026 · Kategoria: VPS / Hosting
LEMP Stack to nowoczesna alternatywa dla klasycznego LAMP: Nginx zamiast Apache, z wydajnym PHP-FPM jako osobnym procesem. Dzięki asynchronicznej architekturze Nginx obsługuje tysiące równoczesnych połączeń przy minimalnym zużyciu RAM. To preferowany wybór dla nowych projektów, API i aplikacji o dużym ruchu. Ten przewodnik przeprowadzi Cię przez pełną instalację na Ubuntu 22.04/24.04 — od czystego serwera do działającego stacku.
Krok 1: Instalacja Nginx
apt update apt install -y nginx # Sprawdzenie statusu systemctl status nginx # Firewall — otwórz port 80 i 443 ufw allow 'Nginx Full' ufw status # Test — otwórz http://IP_TWOJEGO_VPS # Powinnaś zobaczyć stronę "Welcome to nginx!" # Sprawdzenie wersji nginx -v
Krok 2: Instalacja MySQL / MariaDB
# MySQL apt install -y mysql-server # Lub MariaDB (drop-in replacement, często szybsza) # apt install -y mariadb-server # Zabezpieczenie mysql_secure_installation # Utwórz bazę i użytkownika mysql -u root -p CREATE DATABASE moja_aplikacja CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci; CREATE USER 'app_user'@'localhost' IDENTIFIED BY 'silne-haslo'; GRANT ALL PRIVILEGES ON moja_aplikacja.* TO 'app_user'@'localhost'; FLUSH PRIVILEGES; EXIT;
Krok 3: Instalacja PHP-FPM
# PHP 8.2 FPM i najpopularniejsze moduły
apt install -y php8.2-fpm php8.2-cli php8.2-mysql \
php8.2-curl php8.2-gd php8.2-mbstring \
php8.2-xml php8.2-zip php8.2-intl php8.2-bcmath
# Sprawdzenie wersji
php --version
# Status PHP-FPM
systemctl status php8.2-fpm
# Sprawdź socket — będzie potrzebny w konfiguracji Nginx
ls -la /run/php/php8.2-fpm.sock Krok 4: Nginx server block z PHP-FPM
Utwórz plik konfiguracyjny w /etc/nginx/sites-available/. Kluczowy element to
blok location ~ \.php$ z fastcgi_pass do socketu PHP-FPM:
# /etc/nginx/sites-available/moja-domena.pl
server {
listen 80;
listen [::]:80;
server_name moja-domena.pl www.moja-domena.pl;
root /var/www/moja-domena.pl/public;
index index.php index.html;
# Standardowe logowanie
access_log /var/log/nginx/moja-domena-access.log;
error_log /var/log/nginx/moja-domena-error.log;
# Pliki statyczne — bez PHP-FPM
location ~* \.(jpg|jpeg|png|gif|ico|css|js|woff2)$ {
expires 30d;
add_header Cache-Control "public, immutable";
}
# Główny routing (try_files — wymagany przez WordPress i inne CMS)
location / {
try_files $uri $uri/ /index.php?$query_string;
}
# PHP-FPM przez socket Unix
location ~ \.php$ {
# Bezpieczeństwo: nie wykonuj PHP w uploadach
try_files $uri =404;
fastcgi_split_path_info ^(.+\.php)(/.+)$;
# Socket PHP-FPM
fastcgi_pass unix:/run/php/php8.2-fpm.sock;
fastcgi_index index.php;
# Parametry FastCGI
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param PATH_INFO $fastcgi_path_info;
}
# Ukryj pliki .htaccess i .env
location ~ /\. {
deny all;
}
} # Utwórz katalog i ustaw uprawnienia mkdir -p /var/www/moja-domena.pl/public chown -R www-data:www-data /var/www/moja-domena.pl # Aktywacja strony ln -s /etc/nginx/sites-available/moja-domena.pl /etc/nginx/sites-enabled/ # Wyłącz domyślny site (opcjonalne) rm /etc/nginx/sites-enabled/default # TEST KONFIGURACJI (zawsze przed reload!) nginx -t # Przeładowanie Nginx (bez przerwy w ruchu) systemctl reload nginx
Testowanie PHP-FPM
# Utwórz plik testowy echo "<?php phpinfo(); ?>" > /var/www/moja-domena.pl/public/info.php # Otwórz http://moja-domena.pl/info.php # Szukaj: "Server API" = FPM/FastCGI — potwierdza działanie PHP-FPM # PO TEŚCIE USUŃ PLIK! rm /var/www/moja-domena.pl/public/info.php
Optymalizacja Nginx — worker_processes i keepalive
# /etc/nginx/nginx.conf — kluczowe parametry
user www-data;
worker_processes auto; # auto = tyle ile rdzeni CPU (zalecane)
events {
worker_connections 1024; # połączeń per worker (domyślnie 512)
use epoll; # Linux: epoll jest najwydajniejszy
multi_accept on; # akceptuj wiele połączeń jednocześnie
}
http {
sendfile on;
tcp_nopush on;
tcp_nodelay on;
keepalive_timeout 65;
keepalive_requests 1000; # requesty na jedno połączenie keep-alive
types_hash_max_size 2048;
# Buforowanie
client_body_buffer_size 128k;
client_max_body_size 64M; # max rozmiar uploadu
client_header_buffer_size 1k;
# Gzip kompresja
gzip on;
gzip_comp_level 6;
gzip_types text/plain text/css application/json application/javascript;
} Optymalizacja PHP-FPM pool
# /etc/php/8.2/fpm/pool.d/www.conf — dostosuj do RAM serwera [www] user = www-data group = www-data listen = /run/php/php8.2-fpm.sock listen.owner = www-data listen.group = www-data ; Dynamiczne zarządzanie procesami pm = dynamic pm.max_children = 20 ; max 20 procesów PHP pm.start_servers = 5 ; 5 na starcie pm.min_spare_servers = 2 ; min 2 w gotowości pm.max_spare_servers = 8 ; max 8 w gotowości pm.max_requests = 500 ; restart procesu po 500 requestach ; Status endpoint (monitorowanie) pm.status_path = /fpm-status
Reguła ogólna dla pm.max_children: dostępny RAM podziel przez zużycie jednego
procesu PHP. Sprawdź: ps aux | grep php-fpm | awk '{print $6}' — wartości
w KB. Typowy proces PHP z WordPress to 30-60 MB.