# Az Nginx biztonságos konfigurálása PHP-hez

> Nginx biztonságos konfigurálása PHP-hez: csak valódi szkripteket adjon át a PHP-FPM-nek, zárolja a dotfájlokat, és állítson be megfelelő méretkorlátokat.

Forrás: https://phpsos.de/hu/blog/nginx-fuer-php-absichern/  
Állapot: 2026. 10. 25.  
Szolgáltató: PHP SOS, PHP-vészhelyzeti segítség és szerverbiztonság. Azonnali segítség WhatsAppon: https://wa.me/491736494914?text=%C3%9Cdv%C3%B6zl%C3%B6m%2C%20PHP%20SOS%21%20Seg%C3%ADts%C3%A9gre%20van%20sz%C3%BCks%C3%A9g%C3%BCnk%20a%20PHP-szerver%C3%BCnkkel.%20C%C3%A9g%3A%20%E2%80%A6%20Weboldal%3A%20%E2%80%A6

**Röviden:** Az Nginx PHP-hez való biztonságos konfigurálásához csak olyan szkripteket adjon át a PHP-FPM-nek, amelyek valóban léteznek, front controlleres alkalmazásoknál kizárólag az `index.php`-t. Ehhez jönnek a zárolt dotfájlok, mint a `.git` és a `.env`, egy alapértelmezett szerver az ismeretlen hosztnevekhez, megfelelő méretkorlátok és a `security.limit_extensions = .php` a poolban. Ez nem véd a magában a PHP-ban lévő rések ellen, de korlátozza, mi futtatható egy hiba után.

## A legveszélyesebb sorok a PHP-locationben állnak

A PHP2Shell óta sok csapat ellenőrzi a PHP-FPM-verzióit és poolait, ahogyan azt az [Az Nginx biztonságossá tétele PHP-FPM-mel](https://phpsos.de/hu/server/nginx-php-fpm/) oldal leírja, és a frissítés után [újraindítja az összes workert](https://phpsos.de/hu/php2shell/php-fpm-neustart/). Egy második pillantás magára az Nginx-konfigurációra vonatkozik. Ott dől el, mely fájlokat hajtják végre egyáltalán PHP-ként.

Sok konfigurációban van egy blokk, amely minden `.php` végű kérést átad a PHP-FPM-nek, akárhol is van a fájl. Ha egy bejuttatott PHP-fájl egy feltöltési mappába kerül, a szerver végrehajtja. Egy fájlhibából így hátsó ajtó lesz.

Ez a cikk az Nginx oldalára koncentrál: mely direktívák számítanak, hogyan hat a location-blokkok sorrendje, és hogyan tesztelje az eredményt.

## Hogyan dönt az Nginx, melyik blokk érvényesül

Aki az Nginxet biztonságosan akarja konfigurálni PHP-hez, annak ismernie kell a location-blokkok kiválasztását. Az Nginx dokumentációja szerint így zajlik:

1. A `location =` pontos találata azonnal véget vet a keresésnek.
2. A prefix-locationök közül a leghosszabb illeszkedőt jegyzi meg. Ha `^~` van rajta, reguláris kifejezéseket már nem vizsgál.
3. Egyébként a reguláris kifejezéseket (`~`, `~*`) a konfigurációs fájl sorrendjében vizsgálja; az első találat nyer.
4. Ha egy reguláris kifejezés sem illik, a megjegyzett prefix-location érvényes.

Ebből két gyakorlati szabály következik. A feltöltési mappákban a PHP zárolását vagy `^~` prefixként kell létrehozni, vagy reguláris kifejezésként az általános PHP-blokk elé kell tenni. És egy normál prefix-location, mint a `location /uploads/`, nem véd, mert a `.php`-re vonatkozó reguláris kifejezés túlszárnyalja.

## Egy biztonságos alapkonfiguráció

A következő példa egy front controlleres alkalmazás szerverblokkját mutatja, ahogyan a Laravelnél, a Symfonynál, a Shopware 6-nál vagy sok egyedi fejlesztésnél szokásos. Az útvonalakat, a sockete és a tanúsítványokat igazítsa.

```nginx
server {
    listen 443 ssl;
    server_name www.example.de;
    root /var/www/seite1/public;
    index index.php;

    ssl_certificate     /etc/ssl/seite1/fullchain.pem;
    ssl_certificate_key /etc/ssl/seite1/privkey.pem;

    server_tokens off;
    client_max_body_size 32m;

    # A Let's Encrypt és más ismert útvonalak engedélyezése
    location ^~ /.well-known/ {
        try_files $uri =404;
    }

    # Rejtett fájlok és mappák zárolása (.git, .env, .htaccess)
    location ~ /\. {
        deny all;
    }

    location / {
        try_files $uri $uri/ /index.php$is_args$args;
    }

    # Csak a front controllert adják át a PHP-FPM-nek
    location = /index.php {
        include fastcgi_params;
        fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name;
        fastcgi_param DOCUMENT_ROOT $realpath_root;
        fastcgi_hide_header X-Powered-By;
        fastcgi_pass unix:/run/php/seite1.sock;
    }

    # Minden más PHP-fájlt nem hajtanak végre
    location ~ \.php$ {
        return 404;
    }
}
```

A `$realpath_root` feloldja a szimbolikus hivatkozásokat. Ez fontos az olyan telepítéseknél, amelyekben egy váltakozó szimbolikus link mutat az aktuális kiadásra, hogy a PHP-FPM és az OPcache a helyes útvonalat lássa. Vegye figyelembe továbbá: az Nginx dokumentációja szerint a `fastcgi_param` direktívákat csak akkor örökli a magasabb szintekről, ha az aktuális szinten nincsenek sajátok. Ezért az `include fastcgi_params;` ugyanabba a blokkba tartozik.

A klasszikus CMS-eknek, mint a WordPress, a TYPO3 vagy a Contao, több belépési pontjuk van. Náluk a front controller blokkot egy általános PHP-locationre cserélje, amely csak létező fájlokat ad át (`try_files $uri =404;`), és zárolja a végrehajtást az összes írható mappában. Hogyan sikerül ez, azt a [PHP-végrehajtás tiltása a feltöltési mappákban](https://phpsos.de/hu/blog/php-in-uploads-verbieten/) cikk írja le.

## A második védelem a PHP-FPM-ben

Az Nginx dönti el, mi kerül átadásra, a PHP-FPM dönti el, mit hajt végre. A PHP kézikönyve szerint a PHP-FPM alapértelmezetten a `.php` és `.phar` végű fájlokat hajtja végre, és maga javasolja, hogy ezt korlátozzák a `.php`-re. Ez felfogja a webszerver konfigurációs hibáit.

```ini
; a poolban, pl. /etc/php/8.3/fpm/pool.d/seite1.conf
security.limit_extensions = .php
listen = /run/php/seite1.sock
listen.owner = www-data
listen.group = www-data
listen.mode = 0660
```

A socketnek csak az Nginx számára szabad elérhetőnek lennie. Az FPM-portokat a hálózaton, például a `9000`-et, nem szabad kifelé megnyitni. Hogyan mutat a szerver egészében csak a szükséges portokat, azt a [Tűzfal webszerverekhez: csak a szükséges portokat nyissa meg](https://phpsos.de/hu/blog/firewall-fuer-webserver/) írja le.

## Ismeretlen hosztnevek és további beállítócsavarok

Saját alapértelmezett szerver nélkül az Nginx az ismeretlen hosztnevekre irányuló kéréseket az első illeszkedő szerverblokkal válaszolja meg. Az automatizált vizsgálatok, amelyek csak az IP-címet szólítják meg, ilyenkor közvetlenül az Ön alkalmazásába kerülnek. Egy saját alapértelmezett szerver válasz nélkül lezárja az ilyen kéréseket.

```nginx
server {
    listen 80 default_server;
    listen 443 ssl default_server;
    server_name _;
    ssl_reject_handshake on;
    return 444;
}
```

További, bevált pontok:

| Beállítócsavar | Ajánlás | Cél |
|---|---|---|
| `server_tokens` | `off` | nincs verziószám a fejlécben és a hibaoldalakon |
| `client_max_body_size` | a `post_max_size`-hoz illő | a nagy kéréseket korán elutasítani |
| `autoindex` | ki (alapértelmezés) | nincsenek könyvtárlisták |
| `fastcgi_hide_header` | `X-Powered-By` | nincs PHP-verzió kifelé |
| Státuszoldalak | `pm.status_path` csak belsőleg | nincsenek nyilvános üzemi adatok |
| Mentési fájlok | `.sql`, `.zip`, `.bak` a webrootban zárolni vagy eltávolítani | adatbázisok letöltése nélkül |

A verziómegjelölésekről bővebben az [expose_php és Server-fejléc](https://phpsos.de/hu/blog/expose-php-versionsangaben/) cikkben.

Egy további beállítócsavar az engedélyezett HTTP-metódusokat érinti. A legtöbb weboldalnak csak GET, HEAD és POST kell. A `limit_except`-tel más metódusok elutasíthatók egy locationben; az Nginx dokumentációja szerint a GET engedélyezése automatikusan a HEAD-et is engedélyezi. Előtte ellenőrizze, hogy az alkalmazás felületei használnak-e például PUT-ot vagy DELETE-et, mert a REST API-k gyakran igen.

## Tesztelés az újratöltés előtt

Minden módosítást először az `nginx -t` paranccsal ellenőrizzen, és csak utána töltse újra az Nginxet. Ezután tesztelje a viselkedést kívülről normál kérésekkel a saját domainjére:

```bash
sudo nginx -t && sudo systemctl reload nginx
# Elvárt: 403 vagy 404
curl -s -o /dev/null -w "%{http_code}\n" https://www.example.de/.git/HEAD
curl -s -o /dev/null -w "%{http_code}\n" https://www.example.de/.env
# Elvárt: 404, mert csak a front controllert hajtják végre
curl -s -o /dev/null -w "%{http_code}\n" https://www.example.de/info.php
# Mely blokkok adnak át a PHP-FPM-nek?
sudo nginx -T 2>/dev/null | grep -nE "location|fastcgi_pass"
```

Minden nagyobb módosítás előtt mentse az `nginx -T` teljes kimenetét dátummal. Ez tartalmazza az egész érvényes konfigurációt az összes beágyazott fájllal együtt. Ha egy módosítás után valami félresikerül, az összevetés azonnal megmutatja, mi különbözik. A következő kritikus résnél ezzel emellett megbízható alapja van az állapotfelméréshez, anélkül hogy először fájlokat kellene összegyűjtenie.

> **Tipp:**
> A konfigurációt előbb egy tesztkörnyezetben vagy a szerverblokk egy másolatán módosítsa. Egy elfelejtett belépési pont, például egy fizetési callback, különben csak akkor tűnik fel, amikor elmaradnak a rendelések.

## Hogyan segít konkrétan a PHP SOS?

- **A konfiguráció olvasása:** Az `nginx -T` segítségével kiértékeljük a teljes Nginx-konfigurációt, és minden PHP-átadást hozzárendelünk a weboldalához és a poolhoz.
- **A belépési pontok meghatározása:** A fejlesztőivel közösen meghatározzuk, mely szkripteket kell végrehajtani, és a többit zároljuk.
- **Megvalósítás és tesztelés:** Igazítjuk a szerverblokkokat és poolokat, az `nginx -t` paranccsal ellenőrizzük, és teszteljük az űrlapokat, fizetési utakat és feltöltéseket.
- **Tartós védelem:** A konfiguráció a [szerverkeményítésünk](https://phpsos.de/hu/leistungen/server-haertung/) és a szervere dokumentációjának részévé válik.


## Gyakori kérdések

**Újra kell indítani az Nginxet egy PHP-frissítés után?**  
A PHP-javításhoz nem, mert az Nginx nem tartalmaz PHP-t. Az összes PHP-FPM-szolgáltatást kell újraindítani. Ha közben az Nginx-konfigurációt is módosítja, előtte ellenőrizze az nginx -t paranccsal, majd töltse újra az Nginxet.

**Miért csak az index.php-t adjam át a PHP-nak?**  
Sok modern alkalmazásnak egyetlen belépési pontja van, a front controller. Ha csak ezt a fájlt adják át a PHP-FPM-nek, egy máshol bejuttatott PHP-fájl nem futtatható a böngészőn keresztül. Sok belépési ponttal rendelkező rendszereknél ez a minta nem lehetséges.

**Mit ad a security.limit_extensions a PHP-FPM-ben?**  
A beállítás meghatározza, mely fájlvégződéseket hajtja végre a PHP-FPM szkriptként. A PHP kézikönyve szerint az alapértelmezés a .php .phar; a .php-re való korlátozás ajánlott. Ez felfogja a webszerver-konfiguráció hibáit, de nem pótolja azt.

**Az Nginx-szabályok védelmet jelentenek a PHP2Shell ellen?**  
Nem. A PHP2Shell a PHP-értelmezőben van, és csak a javított verzióra való frissítés és az összes worker újraindítása zárja le. Egy biztonságos Nginx-konfiguráció csökkenti a támadási felületet, és korlátozza a kárt egy behatolás után.

## Források

- [Nginx: ngx_http_core_module](https://nginx.org/en/docs/http/ngx_http_core_module.html)
- [Nginx: ngx_http_fastcgi_module](https://nginx.org/en/docs/http/ngx_http_fastcgi_module.html)
- [PHP kézikönyv: FPM-konfiguráció](https://www.php.net/manual/en/install.fpm.configuration.php)
- [OWASP Cheat Sheets](https://cheatsheetseries.owasp.org/)
