Czy bardzo wolno działający WordPress to potencjalny malware lub wirus? Jak zbadać to w terminalu Linux?

Bardzo wolne /wp-admin/ nie musi oznaczać malware, ale jeżeli wcześniej działało normalnie i nagle zaczęło się „wieszać”, warto potraktować to jako incydent do diagnostyki. Przyczyną może być plugin/theme, PHP-FPM, baza danych, cron, brak RAM/CPU/dysku, problem z DNS/HTTP albo faktycznie złośliwy kod.

Najlepiej diagnostykę zrobić z terminala, bez korzystania z panelu WordPressa. WP-CLI jest do tego wręcz stworzone — pozwala wykonywać operacje na WordPressie bez przeglądarki.

1. Najpierw sprawdź, czy problem leży w WordPressie

Wejdź do katalogu instalacji:

cd /var/www/html

oczywiście podając właściwą ścieżkę.

Sprawdź wersję:

wp core version

i czy WordPress poprawnie ładuje się z CLI:

wp core is-installed

Jeżeli to działa bardzo wolno, mamy już ważną wskazówkę.

Następnie:

time wp option get siteurl

oraz:

time wp option get home

Jeżeli proste polecenia WP-CLI wykonują się np. kilkanaście kilkadziesiąt sekund, problem prawdopodobnie nie dotyczy samego panelu /wp-admin/, tylko czegoś ładowanego podczas bootstrapu WordPressa.

2. Bardzo ważny test: wyłącz pluginy „w pamięci”

Nie musisz ich fizycznie wyłączać.

WP-CLI pozwala pominąć ładowanie pluginów:

wp option get siteurl --skip-plugins

i porównaj:

time wp option get siteurl
time wp option get siteurl --skip-plugins

Możesz zrobić to samo z motywami:

time wp option get siteurl --skip-themes

oraz z obydwoma:

time wp option get siteurl --skip-plugins --skip-themes

Jeżeli masz np.:

normalnie:             18.5 s
--skip-plugins:         0.4 s
--skip-themes:         17.9 s

to masz bardzo mocną wskazówkę, że problem powoduje plugin.

Jeżeli natomiast:

normalnie:              18 s
--skip-plugins:         17 s
--skip-themes:          17 s

szukałbym dalej — baza, PHP, sieć, cron, filesystem itd.

3. Sprawdź logi PHP-FPM i webservera

To jest jeden z pierwszych kroków, które zrobiłbym na serwerze.

Najpierw:

systemctl status php*-fpm

oraz:

journalctl -u php*-fpm --since "1 hour ago"

W zależności od dystrybucji PHP-FPM może mieć np. usługę:

php8.3-fpm

więc:

journalctl -u php8.3-fpm --since "1 hour ago"

Szukaj szczególnie:

PHP Fatal error
PHP Warning
Maximum execution time
Allowed memory size
Out of memory
segmentation fault
child exited
pool seems busy
server reached pm.max_children

Jeżeli używasz nginx:

tail -n 200 /var/log/nginx/error.log

Apache:

tail -n 200 /var/log/apache2/error.log

I równocześnie warto obserwować log podczas próby wejścia na /wp-admin/:

tail -f /var/log/nginx/error.log

W drugim terminalu otwierasz:

https://twojadomena.pl/wp-admin/

i patrzysz, co pojawia się w logu.

4. Sprawdź zasoby serwera

To banalne, ale bardzo często właśnie tutaj leży problem.

uptime
free -h
df -h
df -i

oraz:

top

albo:

htop

Szczególnie interesuje mnie:

free -h

Jeżeli zobaczysz praktycznie zerowy RAM i zaczyna się swapowanie, WordPress może działać dramatycznie wolno.

Sprawdź również:

dmesg -T | grep -Ei 'oom|out of memory|killed process'

Jeżeli znajdziesz:

Out of memory: Killed process ...

to prawdopodobnie masz problem z pamięcią, a nie wirusa.

5. Sprawdź bazę danych

Jeżeli wp-admin długo „myśli”, bardzo często winna jest baza.

WP-CLI pozwala wykonać:

wp db check

Możesz również sprawdzić rozmiar bazy:

wp db size

oraz szczególnie interesujące są autoloaded options.

WP-CLI Doctor ma nawet diagnostykę dotyczącą zbyt dużego rozmiaru automatycznie ładowanych opcji, ponieważ mogą one powodować problemy z wydajnością.

Jeżeli masz zainstalowany wp doctor, możesz sprawdzić:

wp doctor check --all

6. Teraz najważniejsze: sprawdzenie, czy WordPress został zmodyfikowany

Tutaj nie zaczynałbym od ClamAV.

Najpierw wykorzystaj mechanizm checksumów WordPressa.

wp core verify-checksums

WP-CLI porównuje pliki core WordPressa z checksumami opublikowanymi przez WordPress.org, bez ładowania całego WordPressa.

Prawidłowy wynik:

Success: WordPress installation verifies against checksums.

Podejrzany:

Warning: File doesn't verify against checksum: ...

Jeszcze lepiej:

wp core verify-checksums --include-root

Ta opcja sprawdza również pliki znajdujące się w katalogu głównym instalacji i może ostrzec o nieznanych plikach.

To jest bardzo wartościowy test w przypadku podejrzenia włamania.

7. Sprawdź pluginy

Uruchom:

wp plugin list

a następnie:

wp plugin verify-checksums --all

WP-CLI może porównać pliki pluginów z checksumami WordPress.org.

Tutaj jednak jest ważne zastrzeżenie.

Jeżeli masz plugin premium albo własny plugin, możesz zobaczyć:

Warning: Could not retrieve the checksums...

To nie oznacza automatycznie malware.

Po prostu WordPress.org może nie posiadać checksumów danego pluginu. Dotyczy to między innymi wielu komercyjnych i customowych pluginów.

8. Sprawdź motywy

wp theme list

Następnie warto przejrzeć:

find wp-content/themes -type f -name '*.php' -printf '%TY-%Tm-%Td %TH:%TM %p\n' | sort

Szczególnie zwróć uwagę na niedawno zmodyfikowane pliki.

To samo dla pluginów:

find wp-content/plugins -type f -name '*.php' -printf '%TY-%Tm-%Td %TH:%TM %p\n' | sort

Jeżeli np. znany plugin ma 150 plików z datą sprzed roku, a nagle:

wp-content/plugins/some-plugin/x.php
2026-08-22 ...

to warto się temu przyjrzeć.

9. Poszukaj typowych śladów malware w PHP

Możesz zacząć od prostego grep:

grep -RniE 'base64_decode|eval\s*\(|gzinflate|str_rot13|shell_exec|passthru|proc_open|popen|assert\s*\(' wp-content

Ale uwaga: samo znalezienie base64_decode() nie oznacza infekcji.

Legalny plugin może używać:

base64_decode()

albo:

eval()

choć eval() jest już bardzo mocnym powodem do sprawdzenia kontekstu.

Ciekawszy jest wzorzec, np.:

eval(base64_decode(...))

WP-CLI Doctor ma nawet domyślny test wykrywający wzorzec eval(...base64_decode(...)).

Możesz więc zrobić:

grep -RniE 'eval\s*\(\s*base64_decode|eval\s*\(\s*gzinflate|base64_decode\s*\(\s*gzinflate' wp-content

10. Poszukaj świeżo utworzonych plików PHP

To jest bardzo dobry test po potencjalnym włamaniu.

Na przykład ostatnie 7 dni:

find /var/www/html -type f -name '*.php' -mtime -7 -ls

Ostatnie 24 godziny:

find /var/www/html -type f -name '*.php' -mtime -1 -ls

Jeszcze bardziej interesujące:

find /var/www/html -type f -name '*.php' -printf '%TY-%Tm-%Td %TH:%TM:%TS %u %p\n' | sort -r | head -100

Jeżeli zobaczysz dziwne nazwy:

wp-content/uploads/2026/08/x.php
wp-content/cache/.something.php
wp-includes/class-wp-xxxx.php
wp-content/plugins/xxxx/.tmp.php

nie usuwaj ich od razu. Najpierw zrób kopię i sprawdź zawartość.

Szczególnie podejrzane jest PHP w:

wp-content/uploads/

Normalnie WordPress przechowuje tam przede wszystkim media. PHP pojawiające się tam bez uzasadnienia jest warte bardzo dokładnego sprawdzenia.

11. ClamAV – tak, ale jako dodatkowa warstwa

Na poziomie Linuxa możesz zainstalować ClamAV.

Debian/Ubuntu:

sudo apt update
sudo apt install clamav clamav-freshclam

Zaktualizuj sygnatury:

sudo freshclam

Następnie przeskanuj katalog WordPressa:

sudo clamscan -r /var/www/html

Możesz zapisać wynik:

sudo clamscan -r /var/www/html \
  --log=/var/log/clamav/wordpress-scan.log

Jeżeli interesują Cię tylko znalezione infekcje:

sudo clamscan -r -i /var/www/html

ClamAV oficjalnie obsługuje skanowanie rekurencyjne przez --recursive i zapis raportu przez --log.

Nie rób od razu:

clamscan --move=...

Nie pozwalałbym antywirusowi automatycznie przenosić plików WordPressa.

Najpierw:

wykryj → zabezpiecz kopię → przeanalizuj → dopiero usuń/odtwórz.

12. Bardzo ważne: malware może być niewykrywalny przez ClamAV

To jest chyba najważniejsza rzecz w całej odpowiedzi.

Jeżeli:

clamscan

niczego nie znajdzie, nie oznacza to, że WordPress jest czysty.

ClamAV jest skanerem sygnaturowym/heurystycznym. Złośliwy kod PHP może być:

  • nowy,
  • zmodyfikowany,
  • zakodowany,
  • ukryty w legalnym pluginie,
  • dodany jako nowy plik,
  • zapisany w bazie danych,
  • umieszczony w wp_options,
  • wykonywany przez mu-plugins,
  • albo pochodzić z konta systemowego.

Dlatego checksumy WordPressa + analiza plików + logi + ClamAV dają znacznie lepszy obraz niż sam antywirus.

13. Sprawdź mu-plugins

To często pomijane miejsce.

ls -la wp-content/mu-plugins/

i:

find wp-content/mu-plugins -type f -ls

mu-plugins są szczególnie istotne, bo są automatycznie ładowane przez WordPress i zwykłe:

wp plugin deactivate ...

ich nie wyłącza.

Dlatego jeśli:

wp option get siteurl --skip-plugins

nadal działa bardzo wolno, mu-plugins nadal mogą być przyczyną.

14. Sprawdź użytkowników WordPressa

Jeżeli podejrzewasz włamanie:

wp user list

Zwróć uwagę na nieznane konta administratorów.

Możesz wyświetlić administratorów:

wp user list --role=administrator

Jeżeli znajdziesz nieznane konto — nie kasuj go od razu, jeśli podejrzewasz aktywne włamanie. Najpierw zabezpiecz dowody i backup.

15. Sprawdź crony WordPressa

Atakujący bardzo często wykorzystują mechanizmy cron do okresowego uruchamiania kodu.

Jeżeli masz odpowiedni pakiet WP-CLI:

wp cron event list

Szczególnie interesują mnie:

  • dziwne nazwy hooków,
  • bardzo częste uruchamianie,
  • adresy URL,
  • callbacki związane z nieznanym pluginem.

WP-CLI Doctor ma również kontrole liczby cronów i duplikatów, bo ich nadmiar może być symptomem problemów.

16. Sprawdź też sam Linux

Jeżeli naprawdę podejrzewasz, że cała maszyna została zainfekowana, a nie tylko WordPress, rozszerzyłbym diagnostykę poza /var/www.

Na początek:

ps auxf
ss -tulpn

oraz:

ss -tpn

Sprawdź procesy uruchomione przez użytkownika webservera:

ps aux | grep -E 'www-data|nginx|apache'

Na Debian/Ubuntu:

sudo systemctl list-units --type=service --state=running

i:

sudo systemctl list-timers --all

Sprawdź cron:

sudo crontab -l

oraz:

sudo ls -la /etc/cron.d/
sudo ls -la /etc/cron.daily/

Jeżeli znalazłeś podejrzany proces, nie zabijaj go automatycznie. Najpierw:

ps -fp PID

oraz:

readlink -f /proc/PID/exe

17. Ja zrobiłbym to w takiej kolejności

Jeżeli to jest mój serwer i właśnie przestał działać /wp-admin/, moja pierwsza sesja SSH wyglądałaby mniej więcej tak:

cd /var/www/html

time wp option get siteurl
time wp option get siteurl --skip-plugins
time wp option get siteurl --skip-themes

wp core verify-checksums --include-root

wp plugin verify-checksums --all

wp plugin list
wp theme list

wp user list --role=administrator

wp db check
wp db size

find wp-content -type f -name '*.php' -mtime -7 -ls

grep -RniE \
'eval\s*\(\s*base64_decode|eval\s*\(\s*gzinflate|shell_exec|passthru|proc_open' \
wp-content

Potem:

free -h
df -h
df -i
uptime

i:

journalctl -u php8.3-fpm --since "1 hour ago"

oczywiście zmieniając wersję PHP na tę, którą faktycznie masz.

Na końcu:

sudo freshclam
sudo clamscan -r -i /var/www/html

A teraz najważniejsze

Jeżeli chcesz, możemy to zrobić razem krok po kroku, bez zgadywania.

Podeślij mi wynik tych 10 poleceń (możesz zamazać domenę, IP, username’y i dane wrażliwe):

cd /ścieżka/do/wordpressa

time wp option get siteurl
time wp option get siteurl --skip-plugins
time wp option get siteurl --skip-themes

wp core version
wp core verify-checksums --include-root

wp plugin list
wp theme list

wp user list --role=administrator

wp db check

free -h

Jeżeli wp wymaga użytkownika www-data, uruchom odpowiednio np.:

sudo -u www-data wp ...

Nie wklejaj tutaj zawartości wp-config.php, haseł do bazy, kluczy API ani sekretów.

Na podstawie tych wyników będę w stanie powiedzieć, czy bardziej wygląda to na plugin/PHP, bazę danych, zasoby serwera, uszkodzony WordPress czy potencjalne włamanie.

About the author

Autor "BIELI" to zapalony entuzjasta otwartego oprogramowania, który dzieli się swoją pasją na blogu poznajlinuxa.pl. Jego wpisy są skarbnicą wiedzy na temat Linuxa, programowania oraz najnowszych trendów w świecie technologii. Autor "BIELI" wierzy w siłę społeczności Open Source i zawsze stara się inspirować swoich czytelników do eksplorowania i eksperymentowania z kodem.