Strona firmowa · Topolowa Medicenter, Kraków · 2026 · 8 miesięcy

Topolowa Medicenter – statyczny HTML zamiast WordPressa

Pacjent nie ląduje na ogólnym formularzu: przycisk przy konkretnym badaniu otwiera widżet rejestracji z już wybranym lekarzem i usługą, więc od kliknięcia do kalendarza jest jeden krok, nie pięć.

  • HTML
  • Tailwind CSS
  • Vanilla JS
  • nginx
  • GitHub Actions
  • ProAssist
Zobacz działającą stronę ↗
Topolowa Medicenter – statyczny HTML zamiast WordPressa

Wyzwanie

Centrum medyczne działało na WordPressie 5.9 na hostingu współdzielonym, z wygasłym certyfikatem SSL i kosztem odnowienia, który nijak się nie zwracał. Do tego strona nie odpowiadała na to, po co pacjent w ogóle na nią wchodzi: żeby zapisać się na konkretne badanie u konkretnego lekarza i dowiedzieć się, jak się do niego przygotować. Rejestracja online była jednym ogólnym widżetem, w którym trzeba było samemu odnaleźć właściwą usługę wśród kilkudziesięciu.

Nasze rozwiązanie

Zbudowaliśmy stronę od nowa jako statyczny HTML – 34 podstrony, bez bazy danych i bez panelu administracyjnego, który trzeba by aktualizować. Nagłówek, mega-menu i stopka żyją w jednym pliku JavaScript wstrzykiwanym do każdej podstrony, więc zmiana numeru telefonu to jedna linia, nie 34 pliki. Rejestracja dostała siatkę usług z bezpośrednimi linkami: każdy kafelek otwiera widżet ProAssist z już wybranym lekarzem i badaniem. Deploy leci z gałęzi main przez GitHub Actions na VPS, ze skryptem rollbacku i monitoringiem sprawdzającym co 15 minut, czy strona i certyfikat żyją.

23 ms

Czas do pierwszego bajtu

0,18 s

Pierwsze renderowanie treści

34

Statycznych podstron

Co zbudowaliśmy

  • 01 34 statyczne podstrony, zero bazy danych i panelu do aktualizowania
  • 02 Nagłówek, megamenu i stopka z jednego pliku JS na wszystkie podstrony
  • 03 Rejestracja z bezpośrednimi linkami: kafelek usługi otwiera widżet z wybranym lekarzem
  • 04 Osobne strony przygotowania do sześciu badań, z PDF-ami do pobrania
  • 05 Cennik, grafik przyjęć i profile lekarzy jako pełnoprawne podstrony
  • 06 Przekierowania 301 ze starych adresów WordPressa, żeby nie stracić pozycji
  • 07 Cache-busting zasobów skrótem commita przy każdym deployu
  • 08 Monitoring co 15 minut: HTTP 200, treść strony i ważność certyfikatu
  • 09 Skrypt rollbacku z backupem bazy i smoke testem przed przełączeniem
  • 10 Skip-link, obsługa klawiatury i aria-expanded w nawigacji
  • 11 FAQ na 26 podstronach, napisane na podstawie odpowiedzi klientki, z danymi strukturalnymi FAQPage
  • 12 GA4 uruchamiane dopiero po zgodzie, wycofanie zgody wyłącza pomiar i czyści ciasteczka
Spis treści +

Punkt wyjścia

Stary WordPress 5.9 stał na hostingu współdzielonym z wygasłym certyfikatem. Odnowienie certyfikatu i przedłużenie hostingu kosztowały tyle, że sensowniej było postawić stronę na nowo niż łatać coś, czego i tak nikt nie aktualizował od lat.

Ale koszt hostingu to był tylko pretekst. Prawdziwy problem był w tym, po co pacjent wchodzi na stronę przychodni. Nie po to, żeby przeczytać o misji i wartościach. Wchodzi z jednym z trzech pytań: ile to kosztuje, kiedy przyjmuje ten lekarz i jak się przygotować do badania. Stara strona odpowiadała na nie po drodze, przy okazji, w akapitach.

Decyzje, które ukształtowały projekt

Strona statyczna zamiast kolejnego WordPressa

Strona przychodni zmienia się kilka razy w roku: cennik, grafik, nowy lekarz w zespole. To nie jest obciążenie, które uzasadnia bazę danych, panel administracyjny i comiesięczne aktualizacje wtyczek. Nowa strona to pliki HTML serwowane przez nginx – nie ma logowania, więc nie ma czego przejąć, i nie ma wersji, która się przeterminuje. To ten sam wybór, który rozkładamy szerzej w tekście o tym, czy wybrać WordPressa, czy Next.js – tu odpowiedź brzmiała: żaden z nich, bo strona firmowa zmieniana kilka razy w roku go nie potrzebuje.

Ma to swoją cenę: klientka nie edytuje treści sama. W zamian nie ma też sytuacji, w której nieaktualizowana wtyczka wystawia na zewnątrz stronę z danymi kontaktowymi pacjentów.

Nagłówek i stopka w jednym pliku

assets/js/components.js renderuje nagłówek, pasek z numerami telefonów, megamenu, panel boczny i stopkę – a każda z 34 podstron ma tylko <div id="site-header">. Trzy numery telefonu, godziny otwarcia i adres siedzą w jednym miejscu.

Alternatywą było skopiowanie nagłówka do 34 plików. Działa do pierwszej zmiany numeru, po której trzy podstrony zostają ze starym.

Rejestracja prowadzi do lekarza, nie do formularza

Centrum korzysta z zewnętrznego systemu rejestracji ProAssist. Domyślnie osadza się go jako jeden widżet, w którym pacjent sam szuka swojej usługi na liście kilkudziesięciu pozycji.

Zamiast tego strona ma siatkę kafelków – konsultacja gastroenterologiczna u konkretnego lekarza, USG jelit, test oddechowy, kapilaroskopia – a każdy kafelek trzyma w data-widget-path ścieżkę do widżetu z już wybranym lekarzem i badaniem. Kliknięcie otwiera modal od razu na kalendarzu terminów. Te same bezpośrednie linki prowadzą z podstron badań, więc ktoś czytający o gastroskopii zapisuje się na gastroskopię bez wracania do zakładki „Rejestracja”.

Koszt tej decyzji: identyfikatory usług pochodzą z panelu ProAssist i po zmianie cennika trzeba je odświeżyć. Jest to opisane w komentarzu przy siatce, bo to jedyne miejsce w projekcie, które wymaga ręcznej synchronizacji z systemem zewnętrznym.

Przygotowanie do badania jako osobne strony

Pacjent przed kolonoskopią nie szuka przychodni – on już ją wybrał i teraz szuka instrukcji: co jeść, kiedy przestać, co wziąć ze sobą. Dlatego przygotowania do badań mają sześć własnych podstron i PDF-y do wydrukowania, zamiast jednej zbiorczej strony z rozwijanymi sekcjami. Każde przygotowanie ma własny adres, który da się wysłać SMS-em przy potwierdzaniu wizyty.

Zejście ze starego adresu bez utraty pozycji

Stary WordPress miał adresy typu /personel/, nowa strona to pliki .html. nginx/tmedicenter-redirects.conf trzyma komplet przekierowań 301, więc żaden link z Google ani z wizytówki nie kończy się na 404 – dokładnie ten punkt z checklisty SEO technicznego strony firmowej, który przy migracji najłatwiej pominąć.

Deploy, który da się cofnąć

Push do main uruchamia GitHub Actions: workflow podmienia ?v= w każdym HTML-u na skrót commita i wysyła pliki rsyncem na VPS. Cache-busting po SHA oznacza, że pacjent nigdy nie dostanie nowego HTML-a ze starym CSS-em z pamięci przeglądarki.

Do tego dwie rzeczy, których statyczna strona zwykle nie ma: scripts/rollback-to-static.sh robi backup bazy i plików przed przełączeniem vhosta i kończy smoke testem, a scripts/check-tmedicenter.sh chodzi z crona co 15 minut i sprawdza, czy strona zwraca 200 z sensowną treścią i czy certyfikat nie wygasa w ciągu 21 dni. Alert idzie mailem i tylko przy zmianie stanu, żeby nie zamienił się w tło.

Po wdrożeniu

Strona nie skończyła się w dniu przełączenia domeny. We wrześniu doszły trzy rzeczy.

FAQ na 26 podstronach. Odpowiedzi napisała klientka. Każda podstrona badania ma własną sekcję pytań, oznaczoną danymi strukturalnymi FAQPage, a odpowiedzi o rejestracji linkują do profilu przychodni w ZnanyLekarz.

Pomiar zgodny z wyborem użytkownika. GA4 startuje dopiero po zgodzie w banerze. Wycofanie zgody najpierw wyłącza pomiar, a dopiero potem kasuje ciasteczka, więc między tymi krokami nic nie zdąży się wysłać. Wejście na stronę rejestracji liczy się jako konwersja raz, a nie przy każdym odświeżeniu.

Treści medyczne 1:1 z dokumentów przychodni. Zalecenia dotyczące leków przeciwkrzepliwych przed gastroskopią i kolonoskopią, uwaga dla chorych na cukrzycę przed testem oddechowym, ulotki do druku. Zmiany wchodzą dosłownie z plików przysłanych przez klientkę, bez redakcji po naszej stronie, bo przy instrukcji przed zabiegiem liczy się każde słowo.

Co z tego wyszło

Pomiar strony głównej z 13 września 2026, headless Chrome 1366×900, bez cache: 23 ms do pierwszego bajtu, 0,18 s do pierwszego renderowania treści – najszybsze FCP z naszych trzech ostatnich realizacji. Dalej jest gorzej: 1,38 s do zdarzenia load i 52 żądania – trzy dokumenty, siedem arkuszy stylów, dwadzieścia jeden obrazów, siedem plików JavaScript i czternaście fontów, razem 1323 kB transferu.

Nie udajemy, że to dobre liczby. Czternaście plików fontów na jedno wejście i 1,38 s do zdarzenia load to rezerwa, nie sukces – i wiemy dokładnie, skąd się bierze: nagłówek i megamenu renderowane z jednego pliku JS ładują komplet czcionek i grafik od razu, niezależnie od tego, którą podstronę ktoś otworzył. To dokładnie przypadek z checklisty Core Web Vitals – subsetting fontów i późniejsze ładowanie obrazów spoza pierwszego ekranu.

Czego nie wiemy: jaki wynik miałby stary WordPress w tym samym pomiarze – certyfikat wygasł, zanim ktokolwiek go zmierzył, więc nie ma punktu odniesienia i nie szacujemy go na wyrost. To jeden pomiar syntetyczny z jednej maszyny, nie dane z ruchu realnych pacjentów.

Technicznie

Statyczny HTML, Tailwind CSS z CDN plus własny arkusz na to, czego klasy narzędziowe nie ogarniają. Dwa pliki JavaScriptu bez frameworka: components.js na wspólne części layoutu, navigation.js na hamburger, rozwijane menu i obsługę klawiatury. nginx na VPS OVH, deploy z main przez GitHub Actions, monitoring i rollback w repozytorium – nie w głowie ani w notatkach na serwerze.

Zrzuty ekranu

Strona główna – pierwszy ekran z dwoma przyciskami i pasek boczny z numerami oraz rejestracją, widoczny na każdej podstronie.
Strona główna – pierwszy ekran z dwoma przyciskami i pasek boczny z numerami oraz rejestracją, widoczny na każdej podstronie. (telefon)

Strona główna – pierwszy ekran z dwoma przyciskami i pasek boczny z numerami oraz rejestracją, widoczny na każdej podstronie.

Podobny problem do rozwiązania?

Napisz krótko, o co chodzi. Wycenę wyślemy w ciągu 24 godzin.

Zapytaj o wycenę →