funkodrop.pl

Oryginalne figurki Funko Pop i kolekcjonerskie gadżety.

Strona główna jako żywy przykład poprawnych strategii renderowania DoSwiftly — każda sekcja pokazuje inny wzorzec.

Server

Katalog — Server Component (ISR + SEO)

Dane produktów pobierane są po stronie serwera (persisted gql() + export const revalidate) i trafiają do HTML wraz z JSON-LD — crawler indeksuje katalog bez JS. Render nie czyta cookies()/headers(), więc strona zostaje statyczna/ISR, a Worker serwuje z cache (CPU ≈ 0 na trafienie). Sam SDK robi ten odczyt cacheowalnym na edge (documentId → GET). Wewnątrz każdej karty „Dodaj do koszyka” to wyspa kliencka — mutacja leci z przeglądarki prosto do GraphQL, omijając Worker.


Client

Wyszukiwarka na żywo — Client Component

Wynik zależy od tego, co użytkownik wpisze (per-naciśnięcie klawisza) — nie da się tego prerenderować ani cache'ować. Komponent kliencki odpytuje persisted gql() przez useStorefrontClient() bezpośrednio z przeglądarki, z pominięciem Workera. Zamontowanie tej wyspy nie wymusza dynamicznego renderu — serwerowy katalog powyżej pozostaje statyczny.


Server + Client

Podobne produkty — Server seed + Client fetch

Hybryda. Serwer podaje cacheowalny „seed” (ID bestsellera z już pobranego katalogu, bez personalizacji), dzięki czemu strona zostaje statyczna i SEO-friendly. Cienka wyspa kliencka dociąga rekomendacje (productRecommendations) leniwie z przeglądarki. Opcjonalny, podscrollowy fetch trzymamy po stronie klienta, by nie blokować statycznego renderu serwera.


Client

Waluta — personalizacja per-cookie (Client)

Personalizacja per-cookie musi żyć po stronie klienta. Wg strategii renderowania odpowiedź z Set-Cookie jest wykluczona z pełnostronicowego cache, a strona wyrenderowana dla jednej waluty nie może być serwowana z cache dla innej. Dlatego przełącznik czyta/zapisuje cookie waluty w przeglądarce (useCurrency) — katalog wyżej zostaje cacheowalny.


Server

Obrazy przez CDN loader

Obrazy idą przez loader CDN DoSwiftly (next.config images.loaderFile) — responsywny srcset + AVIF/WebP. Dwa wczytane statycznym importem (niosą wymiary + blur placeholder), dwa z public/. Czysty Server Component, bez JS klienta.


Client

Konto — logowanie / rejestracja (Client)

Autoryzacja jest z natury per-użytkownik, więc żyje po stronie klienta. Logowanie/rejestracja/wylogowanie idą przez warstwę BFF (/api/auth/*) na domenie storefrontu — to ona ustawia first-party cookies (access + refresh), dzięki czemu sesja przeżywa twardy refresh, a token odnawia się automatycznie (refresh token nigdy nie trafia do JS). Rejestracja przez useRegister (BFF /api/auth/signup) z natychmiastowym sign-in. Po zalogowaniu panel staje się dashboardem konta (ostatnie zamówienia + profil) czytanym z dedykowanego customer-account surface (CustomerClientProvider + useCustomerClient, nowość SDK 22.11.0) — drugi klient, zawsze świeży i nigdy współdzielony w cache, bramkowany useAuthReady. Hint sesji czytamy client-side (cookie session-expiry), więc render serwera nie woła cookies()/headers() i katalog wyżej zostaje statyczny/ISR.

Twoja sesja
Stan logowania (klient, useAuthStore)