# display_errors off: klaidų išvedimo išjungimas produkcijoje

> display_errors Off ir daugiau: kurie PHP nustatymai neleidžia klaidų pranešimų gyvoje svetainėje, ką prideda karkasai ir kaip patikrinti nutekėjimus.

Šaltinis: https://phpsos.de/lt/blog/display-errors-produktion/  
Būsena: 2026-10-25  
Teikėjas: PHP SOS, PHP avarinė pagalba ir serverio sauga. Skubi pagalba per „WhatsApp“: https://wa.me/491736494914?text=Sveiki%2C%20PHP%20SOS%2C%20mums%20reikia%20pagalbos%20su%20m%C5%ABs%C5%B3%20PHP%20serveriu.%20%C4%AEmon%C4%97%3A%20%E2%80%A6%20Svetain%C4%97%3A%20%E2%80%A6

**Trumpai:** gyvoje svetainėje `display_errors = Off` priklauso php.ini kartu su `display_startup_errors = Off`, `log_errors = On` ir klaidų žurnalu už žiniatinklio šakninio katalogo ribų. Be to, CMS ir karkasai turi veikti produkciniu režimu, kitaip savų klaidų puslapių detales parodys jie. Užrakintos su `php_admin_flag` ir tikrinamos po kiekvieno atnaujinimo, klaidos lieka žurnale, o ne naršyklėje.

## Ką išduoda vienas klaidos pranešimas

Įspėjimas puslapio viršuje, „Fatal error“ užuot užsakymo apžvalgos: tokie išvedimai atrodo nekenksmingi. Užpuolikui jie yra žemėlapis. Jie rodo pilnus failų kelius, duomenų bazių ir lentelių pavadinimus, naudojamas bibliotekas ir dažnai PHP versiją.

Būtent tokioje padėtyje kaip PHP2Shell, kai masiškai ieškoma pažeidžiamų serverių, serveris turėtų apie save atskleisti kuo mažiau. Tai neuždaro PHP interpretatoriaus spragos, bet apsunkina kiekvieną kitą žingsnį po įsilaužimo ir sunkina tikslines atakas prieš jūsų programą.

Be to, duomenų apsauga. Klaidų pranešimuose gali būti užklausų dalių, pavyzdžiui, el. pašto adresų iš formų. Kas pasirodo lankytojo naršyklėje, nebėra jūsų kontrolėje.

## Numatytosios reikšmės nėra skirtos produkcijai

Daugelis mano, kad PHP klaidas paslepia pats. PHP vadovas sako kitaip: įtaisytoji `display_errors` numatytoji reikšmė yra 1, o `display_startup_errors` nuo PHP 8.0 taip pat numatytai įjungtas. Tik pateiktas šablonas `php.ini-production` abu nustato į Off. Vadovas `display_errors` aiškiai vadina kūrimo funkcija, kurios sistemose internete niekada nereikėtų naudoti.

Ar jūsų serveris naudoja produkcijos šabloną, nėra savaime suprantama. Konteinerių atvaizdai kartais paleidžiami visai be php.ini, hostingo skydeliai nustato savas reikšmes, o po perkėlimo mėgstama nukopijuoti kūrimo šabloną.

## display_errors off: nustatymų apžvalga

Šios reikšmės prasmingos produkciniams serveriams. Konstantos, tokios kaip `E_ALL`, veikia tik php.ini; Apache konfigūracijoje, pasak PHP vadovo, jos neturi prasmės ir turi būti nurodytos skaičiumi.

| Nustatymas | Produkcija | Paskirtis |
|---|---|---|
| `display_errors` | `Off` | jokių klaidų naršyklėje |
| `display_startup_errors` | `Off` | jokių klaidų išvestyje PHP paleidimo metu |
| `log_errors` | `On` | klaidas rašyti į žurnalą |
| `error_log` | kelias už žiniatinklio šakninio katalogo ribų | atskiras žurnalo failas kiekvienai svetainei ar baseinui |
| `error_reporting` | `E_ALL` | registruoti visas klaidas, nerodyti |
| `html_errors` | `Off` | paprastas tekstas vietoj HTML žurnaluose |
| `zend.exception_ignore_args` | `On` | jokių funkcijų argumentų steko pėdsakuose |
| `fatal_error_backtraces` | `0` iki atnaujinimo (tik PHP 8.5) | pereinamoji priemonė pasak php.net |

`zend.exception_ignore_args` ypač vertingas. Be šio nustatymo steko pėdsakuose žurnaluose ir klaidų puslapiuose gali būti funkcijų iškvietimų argumentų, taigi ir slaptažodžių ar prieigos raktų (token), kurie kaip tik buvo apdorojami.

```ini
; žiniatinklio SAPI php.ini
display_errors = Off
display_startup_errors = Off
log_errors = On
error_log = /var/log/php/website-fehler.log
error_reporting = E_ALL
html_errors = Off
zend.exception_ignore_args = On
; tik PHP 8.5, pereinamoji priemonė iki atnaujinimo į 8.5.12:
; fatal_error_backtraces = 0
```

FPM baseine svarbiausias reikšmes papildomai užrakinkite, kad jokia programa jų vėl neįjungtų per `ini_set()`:

```ini
; pvz., /etc/php/8.3/fpm/pool.d/seite1.conf
php_admin_flag[display_errors] = off
php_admin_flag[display_startup_errors] = off
php_admin_flag[log_errors] = on
php_admin_value[error_log] = /var/log/php/seite1-fehler.log
```

Po to iš naujo paleiskite atitinkamą PHP paslaugą. Kaip tiksliai veikia užrakinimas, paaiškina straipsnis [php_admin_value: nustatymų užrakinimas nuo perrašymo](https://phpsos.de/lt/blog/php-admin-value-sperren/). Pilną bazinę konfigūraciją rasite skyriuje [Saugus php.ini konfigūravimas](https://phpsos.de/lt/ratgeber/php-ini-sicher-konfigurieren/).

## Antras jungiklis: programos derinimo režimas

PHP yra tik pusė reikalo. Šiuolaikiniai karkasai klaidas pagauna patys ir rodo savus, dažnai labai išsamius klaidų puslapius. Derinimo režimu juose yra šaltinio kodo ištraukų, konfigūracijos reikšmių ir kartais aplinkos kintamųjų. Šie puslapiai pasirodo net tada, kai `display_errors` PHP išjungtas.

Todėl kiekvienai programai patikrinkite jos pačios jungiklį. WordPress tai `WP_DEBUG` ir `WP_DEBUG_DISPLAY` faile `wp-config.php`, Laravel ir Symfony `APP_DEBUG` ir aplinka faile `.env`, kitose sistemose produkcinis režimas pagal gamintojo dokumentaciją. Gyvoje sistemoje derinimo režimas turi būti išjungtas visam laikui, net „tik trumpam išbandyti“ yra rizika.

Kaip programoje klaidos tvarkomos švariai, užuot jas slopinus, aprašo [Klaidos ir išimtys PHP](https://phpsos.de/lt/php/fehler-und-exceptions/).

## Kaip rasti klaidų išvedimus prieš kitiems juos radus

Vieno karto nustatyti nepakanka. Klaidų išvedimai sugrįžta po atnaujinimų, perkėlimų ar skydelio pakeitimų. Padeda trumpa patikros eiga:

1. Patikrinti veiksmingas reikšmes žiniatinklio kontekste, ne tik komandinėje eilutėje, pavyzdžiui, trumpam padėtu, po to iš karto ištrintu patikros failu.
2. Patikrinti kiekvienos programos derinimo režimą jos konfigūracijos faile.
3. Pateiktuose puslapiuose ieškoti tipinių klaidų tekstų, kaip parodyta kodo bloke žemiau.
4. Paieškos sistemoje su `site:` užklausa jūsų domene ieškoti tokių terminų kaip „Fatal error“ ar „Warning“.
5. Patikrinti, ar klaidų žurnalas rašomas ir ar jis nėra žiniatinklio šakniniame kataloge.

```bash
# Pateiktuose puslapiuose ieškoti PHP klaidų tekstų (tik savo domenai)
for url in https://www.example.de/ https://www.example.de/kontakt/; do
  curl -s "$url" | grep -E -o "(Fatal error|Warning|Notice|Deprecated|Stack trace)[^<]{0,80}" | head -3
done
# Ar klaidų žurnalas rašomas?
ls -l /var/log/php/
```

> **Svarbu:**
> Klaidų slėpimas nepakeičia jų taisymo. Žurnalas, pilnas įspėjimų, yra užuomina apie priežiūros poreikį, o po įsilaužimo dažnai svarbus pėdsakas. Ką čia registruoti ir ko ne, aprašo [Saugus registravimas: klaidų žurnalas be duomenų nutekėjimo](https://phpsos.de/lt/blog/sicher-loggen-php/).

## Išvada: tyliai naršyklėje, šnekiai žurnale

Produkcinių serverių taisyklė paprasta: klaidos priklauso žurnalui, o ne svetainei. Praktikoje ji strigsta dėl numatytųjų reikšmių, kurios nėra skirtos produkcijai, dėl programų derinimo jungiklių ir dėl konfigūracijų, kurios po atnaujinimų ar perkėlimų grįžta atgal.

Kas išjungia `display_errors` ir `display_startup_errors`, užrakina reikšmes baseine, kontroliuoja programos derinimo režimą ir reguliariai tikrina rezultatą, uždaro vieną dažniausių nereikalingo informacijos atskleidimo šaltinių. Darbo kiekis mažas, poveikis išlieka, kol patikra lieka kiekvieno atnaujinimo dalimi.

Vieno dalyko neturėtų pamiršti: klaidų žurnalas nėra šiukšlių dėžė. Kas jį reguliariai skaito, atpažįsta klaidingus atnaujinimus, pasenusias funkcijas ir kartais net pirmuosius atakos pėdsakus gerokai anksčiau, nei ką nors pastebi klientai.

## Kaip PHP SOS padeda konkrečiai?

- **Patikrinti:** nuskaitome veiksmingus klaidų nustatymus kiekvienai svetainei ir baseinui ir pateiktuose puslapiuose ieškome klaidų išvedimų.
- **Perjungti:** PHP ir programos nustatymus nustatome produkciniam veikimui ir užrakiname nuo perrašymo.
- **Įrengti žurnalus:** klaidų žurnalai yra už žiniatinklio šakninio katalogo ribų, rotuojami ir prieinami jūsų kūrėjams.
- **Išlaikyti ilgam:** [saugumo priežiūros sutartyje](https://phpsos.de/lt/leistungen/security-wartungsvertrag/) nustatymus iš naujo tikriname po kiekvieno atnaujinimo.


## Dažni klausimai

**Ar display_errors PHP nėra išjungtas ir taip?**  
Ne automatiškai. Pasak PHP vadovo, įtaisytoji display_errors numatytoji reikšmė yra 1. Tik pateiktas šablonas php.ini-production nustato Off. Ar jūsų serveris naudoja šį šabloną, priklauso nuo distribucijos, skydelio ar konteinerio atvaizdo ir turėtų būti patikrinta.

**Ar pakanka display_errors = Off, jei WordPress ar Laravel veikia derinimo režimu?**  
Ne. Daugelis CMS ir karkasų turi savus klaidų puslapius, kurie nepriklausomai nuo PHP gali rodyti detales. Todėl išjunkite ir programos derinimo režimą, pavyzdžiui, WP_DEBUG_DISPLAY WordPress arba APP_DEBUG Laravel ir Symfony.

**Kur keliauja klaidos, kai jos nebeberodomos?**  
Su log_errors = On PHP jas rašo į failą, kurį nurodo error_log, arba į atitinkamo veikimo režimo žurnalą, pavyzdžiui, Apache ar PHP-FPM klaidų žurnalą. Failas turėtų būti už žiniatinklio šakninio katalogo ribų ir reguliariai rotuojamas.

**Ką fatal_error_backtraces turi bendro su PHP2Shell?**  
Nustatymas egzistuoja nuo PHP 8.5 ir numatytai aktyvus. php.net įvardija fatal_error_backtraces=0 su vėlesniu paleidimu iš naujo kaip vieną iš pereinamųjų priemonių PHP 8.5, kol dar laukiama atnaujinimo į 8.5.12. Jis nepakeičia atnaujinimo.

## Šaltiniai

- [PHP vadovas: klaidų tvarkymas ir registravimas](https://www.php.net/manual/en/errorfunc.configuration.php)
- [PHP vadovas: konfigūracijos keitimas (php_admin_flag)](https://www.php.net/manual/en/configuration.changes.php)
- [php.net: saugumo pranešimai](https://www.php.net/)
- [OWASP Cheat Sheets](https://cheatsheetseries.owasp.org/)
