Większość porad o „bezpieczeństwie PrestaShop” powstaje z wyobraźni obrońcy — to lista rzeczy, które mogłyby pójść nie tak. My chcieliśmy czegoś przeciwnego: pomiaru tego, co naprawdę spotyka działający sklep PrestaShop, na żywo, tu i teraz. Dlatego oprzyrządowaliśmy własną flotę sklepów i policzyliśmy.

Prowadzimy i chronimy kilka produkcyjnych sklepów PrestaShop, a od ponad dekady budujemy i utrzymujemy obszerny katalog modułów PrestaShop. To dało nam coś, czego nie ma większość opracowań o bezpieczeństwie: zestaw prawdziwych, ruchliwych sklepów i zgodę na obserwowanie każdego wrogiego żądania, które w nie uderza. Przez sześć tygodni rejestrowaliśmy każde złośliwe żądanie — nie tylko te, które się powiodły, i nie tylko te wymierzone w oprogramowanie, którego faktycznie używamy. Jeśli bot sondował moduł, którego nawet nie mamy zainstalowanego, i tak go zapisywaliśmy, bo celem był uczciwy, kompletny obraz presji, pod jaką znajduje się normalny sklep.

Łącznie zebrało się około 1,1 miliona złośliwych żądań z ponad 13 300 różnych adresów IP. Oto, czego naprawdę szukali atakujący — i, dla każdego wniosku, dokładnie co z tym zrobić.

1,1 mlnzarejestrowanych złośliwych żądań
13 300+różnych adresów IP atakujących
~99%automatyczny rekonesans i szum
220 tys.+prób pobrania plików z sekretami
32 tys.trafień w jeden porzucony moduł
6 tyg.okno pomiaru

Jak to zmierzyliśmy

Prowadzimy i chronimy flotę działających, produkcyjnych sklepów PrestaShop oraz budujemy i utrzymujemy ponad sto modułów PrestaShop. Przez sześć tygodni każde żądanie, które wyzwoliło sygnaturę ataku na brzegu serwera WWW — w wielu działających sklepach — trafiało do jednej ustrukturyzowanej bazy danych, z deduplikacją po tożsamości ataku, tak aby jeden skaner uderzający w tysiąc adresów URL liczył się jako jedna kampania, a nie tysiąc incydentów. Co istotne, rejestrowaliśmy też sondowania oprogramowania, którego w ogóle nie używamy, więc obrazu nie zniekształca nasz własny stos. Każda liczba poniżej jest zagregowana i w pełni zanonimizowana: nie publikujemy żadnych danych sklepu, klienta, poświadczeń ani szczegółów exploita.

Pierwsza prawda: około 99% to szum

Najważniejsze jest zrozumienie kształtu tego ruchu. Przytłaczająca większość — grubo ponad milion żądań — to automatyczny rekonesans: masowe skanery przeczesujące internet, wystrzeliwujące te same gotowe ładunki w każdy adres IP, do którego dosięgną, obojętne na to, czy używasz PrestaShop, WordPress, czy aplikacji w Javie.

To jednocześnie uspokajające i niebezpieczne. Uspokajające, bo niemal wszystko odbija się od załatanego, dobrze skonfigurowanego sklepu. Niebezpieczne, bo ta ściana szumu to dokładnie miejsce, w którym ukrywa się ukierunkowana próba. Naprawdę ostry koniec jest realny, ale niewielki — rzędu 34 000 prób wstrzyknięcia SQL i kilku tysięcy prób uruchomienia kodu bezpośrednio na serwerze — cienka warstwa zagrzebana w milionie żądań tła. Jeśli przeglądasz surowe logi dostępu gołym okiem, nigdy niezawodnie nie wychwycisz tego jednego żądania, które ma znaczenie. To cały argument za ustrukturyzowaną detekcją zamiast „zajrzę do logów, jeśli coś wyda się nie tak”.

Oto ten sam obraz w rozbiciu na cele.

Cele ataków według wolumenu, z wyłączeniem ruchu właściciela/infrastruktury. Liczby zaokrąglone.
Czego szukaliWolumenCzym to naprawdę jest
Automatyczny rekonesans i skanowanie~99%Masowe skanery odciskające cały internet, obojętne na to, czego używasz
Pobrania plików z sekretami i konfiguracją220 000+.env, .git, konfiguracja frameworka — kradzież poświadczeń bez potrzeby exploita
Jeden porzucony moduł bloga (LFI)~32 000Pojedynczy nieutrzymywany moduł zewnętrzny — więcej niż wszystkie inne błędy modułów razem wzięte
Próby wstrzyknięcia SQL~34 000Głównie w stare zewnętrzne dodatki: formularze kontaktowe, newslettery i wyszukiwarki
Exploity na obcy stos (WordPress, Java, ASP.NET)dziesiątki tysięcyWystrzeliwane na ślepo w sklepy PHP, które nigdy nie mogłyby być na nie podatne
Próby zdalnego wykonania kodu (RCE)~2 300Naprawdę ostry koniec — ten 1%, który zmienia błąd w pełną kontrolę (próby webshelli liczone osobno)

Najpierw przychodzą po twoje sekrety

Pod względem samego wolumenu najgłośniejszym pojedynczym celem wcale nie była eksploatacja. Była nią kradzież poświadczeń na masową skalę: ponad 220 000 żądań prób pobrania plików z sekretami.env i jego kilkanaście wariantów (.env.local, .env.production, .env.backup, /api/.env i tak dalej), a do tego .git/config, pliki konfiguracyjne frameworków i zapisane w pamięci podręcznej poświadczenia.

Logika jest brutalnie skuteczna. Po co pisać exploita, skoro źle skonfigurowany serwer po prostu wyda hasło do bazy danych, klucz API płatności i poświadczenia poczty w pliku tekstowym? Pojedynczy wyciek .env to często koniec gry — żadna podatność nie jest potrzebna, wystarczy katalog, który nigdy nie miał być publiczny, a jednak jest.

Co robić: upewnij się bez cienia wątpliwości, że twój serwer WWW odmawia serwowania plików kropkowych i konfiguracyjnych. Powinny one zwracać 403 lub 404 z brzegu, a nie swoją zawartość. To pięciominutowa zmiana, która neutralizuje najczęstszy cel, jaki zarejestrowaliśmy:

# Place these ABOVE your generic PHP handler - nginx matches location blocks in order
# Never serve dotfiles (except ACME) or config/secret files
location ~ /\.(?!well-known/) { deny all; }

location ~* \.(env|git|bak|old|dist|sql|log|lock)$ { deny all; }

location ~* /(composer\.(json|lock)|package(-lock)?\.json|yarn\.lock)$ { deny all; }

# PrestaShop config/credential files (all supported versions)
location ~* /(settings\.inc\.php|parameters\.(php|ya?ml))$ { deny all; }
# Block dotfiles and config/secret files
RedirectMatch 404 /\.(?!well-known)

<FilesMatch "\.(env|git|bak|old|dist|sql|log|lock)$">
    Require all denied
</FilesMatch>

<FilesMatch "^(composer\.(json|lock)|package(-lock)?\.json|yarn\.lock)$">
    Require all denied
</FilesMatch>

# PrestaShop config/credential files (all supported versions)
<FilesMatch "^(settings\.inc\.php|parameters\.(php|ya?ml))$">
    Require all denied
</FilesMatch>

Zweryfikuj to

Z zewnątrz serwera zażądaj /.env i /.git/config przez HTTPS. Chcesz zobaczyć 403 lub 404 — jeśli dostaniesz jakąkolwiek zawartość pliku albo nawet puste 200, napraw to, zanim zajmiesz się czymkolwiek innym z tej listy.

Cel numer jeden: porzucony moduł

Kiedy zawęziliśmy analizę do ataków wymierzonych konkretnie w PrestaShop, jeden cel przyćmił całą resztę: luka typu local file inclusion w starym, nieutrzymywanym już module bloga — mniej więcej 32 000 prób, więcej niż wszystkie pozostałe podatności modułów razem wzięte.

To schemat, który po cichu rujnuje sklepy. Prawie nigdy to nie rdzeń PrestaShop wpuszcza atakujących do środka. To zewnętrzny moduł, który zainstalowałeś trzy lata temu, przestałeś aktualizować i zapomniałeś, że go masz. Atakujący prowadzą starannie dobrane listy takich modułów — nazwa modułu, podatna ścieżka, gotowy exploit — i rozpylają je po całym internecie w pętli.

Dalej na liście znaleźli się zwykli podejrzani: próby wstrzyknięcia SQL w moduły formularzy kontaktowych i newsletterów, znana podatność w module listy życzeń oraz garść dodatków ze sliderami i wyszukiwarkami. Wszystkie zewnętrzne. Wszystkie tego rodzaju, co odkłada się w sklepie przez lata, a potem tkwi tam niezałatane, długo po tym, jak ktokolwiek pamięta ich instalację.

Co robić: zinwentaryzuj swoje moduły i usuń te, których nie używasz — zainstalowany, ale nieużywany moduł to czysta powierzchnia ataku bez żadnej korzyści. Łataj te, które zostawiasz, a jeśli deweloper zniknął, wymień moduł zamiast liczyć na szczęście. Jeśli utknąłeś na wersji, której nie da się bezpiecznie zaktualizować, nasz przewodnik po utwardzaniu sklepu, którego nie możesz zaktualizować pokazuje, jak wirtualnie załatać dokładnie taką dziurę.

Zestaw włamywacza: webshelle i backdoory

Za rekonesansem i polowaniem na sekrety siedzi ostry koniec. Atakujący raz po raz próbowali podrzucić lub zlokalizować webshelle — narzędzia, które zmieniają pojedynczą podatność w pełną zdalną kontrolę. Same nazwy plików są niemal sygnaturą: adminer.php, alfa.php, wso.php, pojedyncze sondowania phpinfo oraz skrypty menedżerów baz danych pozostawione po wcześniejszym włamaniu.

Wychwyciliśmy też coś bardziej wycelowanego niż zwykłe skanowanie. Kiedy jeden sklep w grupie zostaje przejęty, atakujący biorą dokładnie ten ładunek, który tam zadziałał, i rozpylają go po każdym powiązanym sklepie, jaki znajdą, obstawiając, że ten sam backdoor wciąż siedzi na kolejnym. Wytrwałość popłaca: backdoor zagrzebany w rzadko sprawdzanym pliku może przetrwać wiele powierzchownych „czyszczeń” i tygodniami ponownie infekować sklep. Jeśli kiedyś posprzątałeś po włamaniu, usuwając tylko widoczny złośliwy JavaScript, a ono wróciło — to właśnie dlatego; przeszliśmy przez dokładnie taką porażkę w naszej anatomii skimmera w stylu Magecart.

Co robić: zablokuj wykonywanie PHP w każdym katalogu, który powinien przechowywać wyłącznie przesłane pliki, obrazy, pamięć podręczną lub narzędzia. Jeśli botowi uda się zapisać shell.php w twoim folderze z obrazami, różnica między złym dniem a pełnym włamaniem sprowadza się do tego, czy serwer go uruchomi:

# Put this ABOVE your existing "location ~ \.php$" block - nginx is first-match-wins
# A bot that writes shell.php into an image folder must never get it executed
location ~* ^/(img|upload|uploads|cache|var|download)/.*\.(php|phar|phtml|php[0-9])$ {
    deny all;
}
# Drop this .htaccess inside an uploads folder: turn PHP off for the whole tree
<FilesMatch "\.(php|phar|phtml|php[0-9])$">
    Require all denied
</FilesMatch>

Po każdym podejrzeniu włamania zakładaj utrzymywanie się zagrożenia

Usunięcie widocznego objawu to nie naprawa. Poluj na pliki wykonywalne w ścieżkach zapisywalnych, wymień wszystkie poświadczenia, które znajdowały się w czytelnym pliku konfiguracyjnym, i odtwórz sklep z pewnej, czystej kopii zapasowej, zamiast czyścić go w miejscu.

Nawet nie sprawdzają, czego używasz

Wymowna ilustracja tego, jak bardzo jest to zautomatyzowane: zarejestrowaliśmy dziesiątki tysięcy prób exploitów wymierzonych w zupełnie inne stosy technologiczne — ładunki Java i JSF, exploity wtyczek WordPress, sztuczki ASP.NET — wszystkie wystrzeliwane na ślepo w sklepy PHP, które nigdy nie mogłyby być na nie podatne.

Wniosek nie brzmi „cha, chybili”. Jest odwrotny: jesteś atakowany bez przerwy, przez napastników, którzy ani nie wiedzą, ani nie dbają o to, czego używasz. Nie musisz być celem, żeby stać się ofiarą. Wystarczy, że jesteś osiągalny i nieaktualny.

Sprawdź własny sklep już teraz

Czytanie o tym to jedno; poniżej znajdziesz cztery testy, które w ciągu pięciu minut uruchomisz na własnym sklepie. Odpowiadają dokładnie temu, czego szukają opisani wyżej napastnicy.

1. Czy Twoje sekrety są faktycznie dostępne? Z własnego komputera poproś o pliki, o które pytają skanery. Każda linia powinna zwrócić 403 lub 404 — nigdy 200 z zawartością:

# From your own machine: 403/404 = safe, 200 = exposed, 000 or 3xx = check by hand
for f in .env .git/config app/config/parameters.php composer.json; do
  printf '%s -> ' "$f"
  curl -s -o /dev/null --connect-timeout 5 --max-time 15 -w '%{http_code}\n' "https://your-store.com/$f"
done

2. Czy w miejscach przeznaczonych tylko na zasoby ukrywa się PHP? Przez SSH, z katalogu głównego sklepu, poszukaj plików wykonywalnych w folderach, które powinny przechowywać wyłącznie pliki wgrywane przez użytkowników oraz obrazy. To polecenie nie powinno wypisać niczego:

# PHP hiding in folders that should only hold assets (a clean store prints nothing)
find img upload uploads download -type f \
  \( -iname '*.php' -o -iname '*.php[0-9]' -o -iname '*.phtml' -o -iname '*.phar' \) \
  ! -iname index.php 2>/dev/null

3. Co zmieniło się ostatnio? Świeżo podrzucony backdoor to niedawno zmodyfikowany plik PHP, którego sam nie tykałeś. Wypisz zmiany z ostatniego tygodnia i przyjrzyj się wszystkiemu, co wygląda nieznajomo:

# PHP changed in the last 7 days, cache excluded (GNU/Linux find) - review anything unfamiliar
find . \( -path ./var/cache -o -path ./cache \) -prune -o \
  -type f -iname '*.php' -mtime -7 -printf '%TY-%Tm-%Td  %p\n' | sort

4. Kto może zalogować się do Twojego back office? Każde konto to klucz do drzwi wejściowych. Sprawdź każdego pracownika, którego nie rozpoznajesz, oraz każdego, kto nie logował się od miesięcy:

-- Back-office accounts: investigate any you do not recognise
-- Run in phpMyAdmin or the mysql client; change the ps_ prefix if yours differs
SELECT id_employee, email, active, last_connection_date
FROM ps_employee
ORDER BY last_connection_date DESC;

Wolisz sprawdzenie jednym kliknięciem?

Te same testy zamknęliśmy w gotowym narzędziu. Nasz darmowy, otwartoźródłowy Security Scan sprawdza twój sklep dokładnie pod kątem tych zagrożeń — odsłoniętych plików konfiguracyjnych i kopii zapasowych, przypadkowego kodu PHP w folderach z zasobami, modułów ze znanymi podatnościami CVE, trybu debugowania i słabego utwardzenia — i przekazuje ci uporządkowany według priorytetów raport, całkowicie za darmo. Dla stałej ochrony Security Revolution dokłada firewall żądań, ograniczanie liczby zapytań, nagłówki bezpieczeństwa, monitorowanie zmian w plikach i skanowanie podatności — wszystko z poziomu back office. A jeśli wolisz oddać całość w nasze ręce, nasz Security & Hardening Audit to przegląd wykonany od początku do końca przez nasz zespół.

Co naprawdę robimy we własnych sklepach

Ponieważ to również nasze sklepy, powyższa lista obronna nie jest teoretyczna. W sklepach objętych tym badaniem blokujemy pliki kropkowe i konfiguracyjne na brzegu, odmawiamy wykonywania PHP we wszystkich ścieżkach zapisywalnych, celowo utrzymujemy niewielki zestaw modułów i usuwamy wszystko, co nieużywane, wymuszamy uwierzytelnianie dwuskładnikowe w panelu administracyjnym i osadzamy całość za warstwą brzegową, która ogranicza tempo skanerów i odrzuca oczywiste ładunki wstrzyknięć. I nie wyłączamy rejestratora — tego samego logowania na poziomie żądań, które dało tę publikację — aby naprawdę ukierunkowana próba wypłynęła na wierzch, zamiast utonąć w 99% szumu. Nic z tego nie jest egzotyczne. Wszystko jest nudne, a nudne jest tym, co działa.

  • Blokuj pliki z sekretami na brzegu. .env, .git, composer.json i pliki konfiguracyjne muszą zwracać 403/404 — nigdy swojej zawartości.
  • Przetnij listę modułów. Usuń wszystko, czego nie używasz; nieużywany moduł to czysta powierzchnia ataku.
  • Łataj lub wymieniaj to, co zostawiasz. Zwłaszcza zewnętrzne dodatki: blogi, slidery, formularze i wyszukiwarki.
  • Zablokuj PHP w folderach zapisywalnych. Przesyłane pliki, obrazy, pamięć podręczna i tmp nigdy nie powinny wykonywać kodu.
  • Zabezpiecz logowanie do panelu. Silne, unikalne poświadczenia i uwierzytelnianie dwuskładnikowe.
  • Pozostań na wspieranej wersji. Platforma po zakończeniu wsparcia ma na stałe komplet znanych kluczy.
  • Postaw detekcję między sobą a szumem, żeby ten 1%, który ma znaczenie, nie mógł się ukryć w 99%, które go nie ma.

Najczęściej zadawane pytania

Czy PrestaShop jest bezpieczny?

Rdzeń PrestaShop jest aktywnie utrzymywany i rzadko bywa drogą wejścia. W naszych danych prawie nic nie celowało w rdzeń — ataki wyglądające na skuteczne wymierzone są w moduły zewnętrzne, źle skonfigurowane serwery wyciekające pliki z sekretami oraz instalacje po zakończeniu wsparcia. Załatany, dobrze skonfigurowany sklep PrestaShop na aktualnej wersji to trudny cel. Zaniedbany — nie.

Skąd mam wiedzieć, czy mój sklep został już przejęty?

Szukaj plików PHP w katalogach, które powinny przechowywać tylko obrazy lub przesłane pliki, niespodziewanych kont administratorów, zmodyfikowanych plików .htaccess lub index.php oraz nieznanych zadań zaplanowanych. Backdoor często przeżywa „czyszczenie”, które usunęło jedynie widoczny złośliwy JavaScript — jeśli infekcja wciąż wraca, gdzieś na dysku nadal leży plik wykonywalny. Aby uporządkować samodzielną kontrolę, dobrym kolejnym krokiem jest nasz przewodnik po sygnałach, że sklep potrzebuje audytu bezpieczeństwa.

Które moduły są najbardziej niebezpieczne?

Każdy zewnętrzny moduł, którego już nie aktualizujesz — zwłaszcza starsze dodatki: blogi, slidery, formularze kontaktowe, newslettery, listy życzeń i wyszukiwarki, które mają dobrze znane publiczne exploity. Najczęściej atakowanym pojedynczym komponentem w naszej flocie był jeden porzucony moduł bloga. Jeśli deweloper zniknął, potraktuj moduł jako obciążenie i wymień go.

Czy potrzebuję Cloudflare lub WAF-a?

Warstwa brzegowa, która potrafi blokować żądania plików kropkowych, ograniczać tempo skanerów i filtrować oczywiste ładunki wstrzyknięć, pochłania dużą część tego szumu, zanim dotrze on do PHP. To nie zastępuje łatania i usuwania nieużywanych modułów, ale wyraźnie obniża presję i kupuje ci czas.

Jestem na starej wersji PrestaShop, której nie mogę bezpiecznie zaktualizować. Co teraz?

Agresywnie ograniczaj powierzchnię ataku: usuń każdy nieużywany moduł, zablokuj na serwerze pliki z sekretami i wykonywanie PHP w folderach z zasobami oraz wirtualnie załataj znane dziury na brzegu. Nasz przewodnik po utwardzaniu sklepu, którego nie możesz zaktualizować omawia to szczegółowo.

Jak często normalny sklep jest faktycznie atakowany?

Bez przerwy. W całej naszej flocie było to około miliona złośliwych żądań w sześć tygodni. Przytłaczająca większość jest automatyczna i nieszkodliwa dla utrzymywanego sklepu — ale nigdy nie ustaje, a wystarczy jedne zaniedbane drzwi.

Sedno sprawy

Odejmij wolumen, a obraz staje się prosty. Ataki, które się udają, prawie nigdy nie opierają się na jakimś egzotycznym zero-dayu. Opierają się na nudnych rzeczach: czytelnym pliku z sekretami, niezałatanym lub porzuconym module zewnętrznym, katalogu, który uruchomi przesłany plik PHP, logowaniu do panelu ze słabym lub powtórnie użytym hasłem, nieaktualnej platformie. Żadnej z tych rzeczy nie jest trudno naprawić. Wszystkie to sprawy, które utrzymywany sklep załatwia poprawnie, a zaniedbany nie. Atakujący zautomatyzowali poszukiwanie zaniedbań — milion razy w sześć tygodni. Jedyną prawdziwą obroną jest po prostu nie być zaniedbanym: łataj, przycinaj, zamykaj oczywiste drzwi i postaw prawdziwą detekcję między sobą a tą ścianą szumu.

Napisane przez zespół mypresta.rocks. Od ponad dekady budujemy moduły PrestaShop oraz prowadzimy i chronimy flotę działających, produkcyjnych sklepów w kilku krajach — tych samych, których logi dały powyższe dane. Ten artykuł relacjonuje, co naprawdę widzimy i co naprawdę z tym robimy. Wszystko tutaj działa z PrestaShop 1.6, 1.7, 8.x i 9.x. Okno danych: około sześć tygodni do lipca 2026, zanonimizowane.

Nota metodologiczna: liczby są zagregowane z logowania ataków na poziomie żądań w wielu działających, produkcyjnych sklepach w oknie około sześciu tygodni kończącym się w lipcu 2026. Wszystkie dane są zanonimizowane; nie zawierają żadnych szczegółów sklepu, klienta ani poświadczeń, a żadne szczegóły exploitów nie są publikowane.

Udostępnij ten wpis:
David Miller

David Miller

Founder, mypresta.rocks

David Miller to specjalista PrestaShop z ponad dekadą praktycznego doświadczenia i założyciel mypresta.rocks — studia programistycznego z Tychów. Tworzy i utrzymuje katalog 152 modułów PrestaShop — w tym 21 pakietów „Revolution" obejmujących SEO, checkout, bezpieczeństwo, wydajność, marketing, wyszukiwanie, wsparcie i operacje magazynowe — które każdego dnia usprawniają realne sklepy, testowanych na PrestaShop 1.7.8, 8.x i 9.x. Sprawuje również opiekę nad sklepami produkcyjnymi generującymi miliony rocznego obrotu, dlatego jego pracę ocenia się po realnej sprzedaży, a nie po wersjach demo. Jego doświadczenie obejmuje pełen zakres e-commerce — wydajność, bezpieczeństwo, SEO i marketing — oraz wykracza poza PrestaShop, sięgając WooCommerce, Shopify i systemów tworzonych na zamówienie. Na blogu pisze o technicznej stronie PrestaShop: co platforma naprawdę robi pod maską, co psuje się na produkcji i które rozwiązania faktycznie się sprawdzają.

Spodobał Ci się ten artykuł?

Otrzymuj nasze najnowsze porady, przewodniki i aktualizacje modułów prosto na swoją skrzynkę.

Komentarze

Brak komentarzy. Bądź pierwszy!

Bądź pierwszy: zadaj pytanie albo podziel się przydatną opinią.

Ładowanie...
Do góry