Przejdź do treści
Arteon — strona stowarzyszenia artystycznego

Arteon — strona stowarzyszenia artystycznego
Dwujęzyczna strona krakowskiego stowarzyszenia artystycznego — Next.js 16 + Strapi v5, cinematic noir, własne i18n na ciastku, headless CMS na wydarzenia, WCAG 2.2 AA, od strategii po wdrożenie na VPS.

KLIENTStowarzyszenie Artystyczne Arteon (Mateusz Kluza, Prezes)
TERMIN2026-07
ROLAFull-Stack Developer / Architekt / UX Designer
STATUSZakończone

"Firma miała za sobą ludzi sceny i realizacje, ale w internecie nie było tego widać. Zbudowałem stronę, która w kilka sekund pokazuje statut, dane rejestrowe i dorobek — a klient sam dodaje wydarzenia, bez programisty."

Arteon to krakowskie Stowarzyszenie Artystyczne tworzone przez czynnych, uznanych muzyków — koncerty, spektakle, inicjatywy muzyczne, muzykoterapia. Organizacją zarządza Mateusz Kluza (Prezes, kontrabasista, nominacja do Fryderyka 2024, koncerty z Andrea Bocelli i Krzysztofem Pendereckim).

Stowarzyszenie istniało w sieci rozproszone przez social media — bez własnej domeny, bez portfolio wydarzeń, bez danych rejestrowych czytelnych dla urzędnika. Zbudowałem od podstaw nową stronę, którą rozbudowałem o panel do samodzielnego zarządzania wydarzeniami, pełne SEO, dwujęzyczność i wdrożenie na serwer.

📋 Metryki projektu

  • Status: Zakończone, strona działa na produkcji (arteon.org.pl)
  • Rola: Full-Stack Developer / Architekt / UX Designer — cały projekt od strategii po wdrożenie
  • Zakres: Strategia i planowanie treści, design system, panel administracyjny (CMS), implementacja frontu, SEO, dostępność, wdrożenie produkcyjne
  • Cel: Zamienić nieobecność w sieci w stronę, która w kilka sekund przekonuje partnera instytucjonalnego, że Arteon to poważna, wiarygodna organizacja

🚀 Jak powstawał projekt

Zaczęliśmy (razem z klientem) od zrozumienia, kim właściwie jest Arteon — nie agencją eventową, która koordynuje, i nie urzędowym NGO, ale stowarzyszeniem tworzonym przez muzyków-scenowców z prawdziwej pasji. Ta różnica musiała być widoczna w każdej warstwie strony: w treściach, w strukturze wydarzeń, w samym designie.

Dalej praca poszła w kilku kierunkach równolegle: dwujęzyczność strony (polski i angielski, ten sam adres URL — treść przełącza się po ciastku), własny system do zarządzania wydarzeniami oparty na Strapi, żeby klient samodzielnie dodawał koncerty, galerie i program bez pisania kodu. Nowa treść z panelu pojawia się na stronie w ciągu kilku minut — bez ręcznego redeployu.

Kolejny duży etap to design system: kinowy noir, złoto na głębokiej czerni, lapidarna typografia Cinzel (inskrypcja rzymska, Trajan) spójna z monogramem A klienta. Świadome negative space, bez gradient blobs, glassmorphism i tanich efektów — wizualność niosą zdjęcia, typografia i złoto.

Potem pełne SEO: metadane, dane strukturalne rozpoznawane przez Google (Organization z KRS/NIP/REGON, Event, BreadcrumbList, Person), mapa strony, dynamicznie generowane obrazy podglądu social media (Open Graph + Twitter), dane rejestrowe czytelne przy weryfikacji stowarzyszenia. Na końcu runda poprawek pod dostępność — żeby strona dała się obsłużyć klawiaturą, czytnikiem ekranu, i żeby kontrast złota na czerni spełniał standard WCAG 2.2 AA. Wdrożenie na serwer VPS przez Docker Compose z Traefik (TLS, Let's Encrypt), healthcheckami i noindex dla panelu CMS.

🎯 Problem biznesowy

Młode stowarzyszenie artystyczne istniało w sieci rozproszone przez social media — bez własnej domeny, bez portfolio wydarzeń, bez czytelnych danych rejestrowych. Osoba szukająca w Google informacji o Arteonie trafiała na profile społecznościowe, nie na miejsce, które pokazuje kim jest organizacja i co już zrobiła.

❌ Konkretne problemy

  • Brak jednego, wiarygodnego miejsca w sieci. Instytucja, scena czy partner sprawdzający Arteon w kilka chwil musi zobaczyć statut, KRS/NIP/REGON, dorobek i skalę produkcji. Tego nie było — tylko rozproszone wpisy w social media.
  • Dwie grupy odbiorców, jeden przekaz. Strona ma przekonać osoby decyzyjne (instytucje, sceny, partnerów), nie bawić masowej publiczności. Publiczność jest beneficjentem wydarzeń, nie celem perswazji. Główny odczyt: telefon, w biegu.
  • Brak portfolio wydarzeń. Każdy zrealizowany koncert to potencjalny dowód rozmachu, ale dodanie nowego wydarzenia wymagało programisty, więc nikt tego nie robił.
  • Dwujęzyczność bez duplikacji. PL/EN wymagane ze względu na partnerów zagranicznych.
  • SEO dla niszy. Konkurencja o nazwisko i lokalne frazy wymaga danych strukturalnych i dynamicznego sitemap — a decydenci najpierw googlują Arteon.
  • Dostępność jako misja. Arteon deklaruje sztukę dla osób z niepełnosprawnością — strona musi spełniać WCAG 2.2 AA.
  • Wąskie okno dostawy. ~10 dni na MVP, gotowe do rozbudowy bez przebudowy.

💡 Jak to zostało rozwiązane

  • Perswazja, nie wizytówka. Każda sekcja prowadzi decydenta przez dowody wiarygodności w kolejności, w jakiej sam ich szuka: hero z rozmachem → o nas (misja, zarząd z linkami do portfolio członków) → wydarzenia (nadchodzące + archiwum) → wesprzyj nas (darowizna odliczana od podatku) → kontakt z danymi rejestrowymi. Mobile-first, bo decydent sprawdza z telefonu w biegu.
  • Cinematic noir jako narzędzie statusu. Głębokie cienie, złoto na czerni (kontrast 6.43:1 — WCAG AA), kapitaliki Cinzel, świadome negative space. Wizualność niosą zdjęcia, typografia i złoto, nie tanie efekty. Kinowy noir celowy: miniatury kart i hero w odcieniach szarości, galeria szczegółów wydarzenia w kolorze.
  • Dwujęzyczność bez drugiej kopii strony. Język w ciastku, domyślnie polski. Ten sam adres /wydarzenia/[slug] dla obu języków — przełącznik odświeża treść, nie przenosi na inną ścieżkę. Mniej zależności, jeden URL do wysłania partnerowi.
  • Panel, po którym strona się nie wywala. Dane z CMS-a mapowane na płaski kształt — puste pole daje fallback, nie biały ekran. Build przechodzi nawet gdy panel jest chwilowo niedostępny, treść pojawia się przy pierwszym żądaniu po starcie.
  • Angielski draft powstaje sam. Nowe wydarzenie po polsku dostaje automatycznie szkic angielski (pola tekstowe + program) do ręcznego tłumaczenia. Edycja polskiej wersji nie nadpisuje już przetłumaczonego angielskiego.
  • Adres wydarzenia działa w obu językach. Identyfikator URL jest wspólny i w panelu nie kopiuje się do wersji angielskiej. Front skleja polski wpis (adres, data, zdjęcia) z angielskim (tytuł, miejsce, opis, program) — gdy tłumaczenia brak, pokazuje polski.
  • Podział wydarzeń automatyczny. Koncerty pobierane raz, dzielone na nadchodzące i archiwum po dacie — bez ręcznego oznaczania.
  • SEO pod decydenta i crawlery. Metadane na każdej stronie, dane strukturalne (organizacja z KRS/NIP/REGON, wydarzenie, okruszki, osoba), mapa strony, plik dla botów, generowane obrazy podglądu social z fallbackiem okładki.
  • Dostępność od początku. Landmark + SkipLink, złoty focus, etykiety ARIA, semantyczny HTML, lightbox z pułapką fokusa i klawiaturą, kontrast złota na czerni pod AA.
  • Statut jako tekst, nie PDF. Osobna strona /statut z pełnym tekstem (nie załącznik do pobrania) — czytelna dla urzędnika i robotów. Na stronie głównej tylko teaser w akordeonie i link.

📈 Efekt

ObszarPrzedPo wdrożeniu
Obecność w sieciTylko social media, brak domenyWłasna domena + dwujęzyczna strona
Wiarygodność dla partneraRozproszone social media, brak danych rejestrowychStatut, KRS/NIP/REGON, dorobek, skala — czytelne w kilka sekund
Zarządzanie wydarzeniamiRęczne, wymagało programistyPanel CMS — klient dodaje wydarzenia sam, bez kodu
Czas publikacji nowego wydarzeniaRedeploy stronyOdświeżenie w ciągu kilku minut, bez redeployu
Podział wydarzeńBrakAutomatyczny nadchodzące/archiwum po dacie
Widoczność w GoogleBrak danych strukturalnychJSON-LD + dynamic sitemap + obrazy OG/Twitter
DostępnośćNie sprawdzanaWCAG 2.2 AA — focus trap, ARIA, skip link, kontrast zweryfikowany
JęzykiTylko polskiPolski i angielski, przełącznik cookie-based

„Firma miała za sobą ludzi sceny i realizacje, ale w internecie nie było tego widać. Zbudowałem stronę, która w kilka sekund pokazuje statut, dane rejestrowe i dorobek — a klient sam dodaje wydarzenia, bez programisty.”

🛠️ Wyzwania techniczne

  • Wada systemu CMS z tłumaczeniami. Panel nie kopiuje adresu URL wydarzenia do wersji angielskiej — pole zostaje puste. Front zawsze odczytuje polski wpis (adres, data, zdjęcia) i dokłada do niego angielskie teksty. Brak tłumaczenia = polski fallback, strona się nie wywala.
  • Szkielet EN tylko przy pierwszym utworzeniu. Przy dodaniu polskiego wydarzenia hook w panelu kopiuje teksty i program do angielskiego szkicu. Przy publikacji hook odpala się ponownie — najpierw sprawdza, czy angielska wersja już jest, żeby jej nie zdublować. Późniejsza edycja polskiego nie nadpisuje tłumaczenia.
  • Build niezależny od panelu. Gdy CMS nie odpowiada przy budowaniu obrazu, lista wydarzeń jest pusta i obraz i tak powstaje. Po starcie pierwsze wejście na stronę dociąga treść.
  • Filtr dat poza panelem. Filtrowanie po dacie w CMS-ie jest zawodne. Pobieram wszystkie wydarzenia i dzielę je na froncie po dzisiejszej dacie.
  • Obrazy z panelu przez publiczny adres. Optymalizator Next.js sam pobiera plik — wewnętrzny adres kontenera jest dla niego niewidoczny. Adresy mediów zamieniam na publiczny URL panelu.
  • Obrazy social bez fontu z CSS. Generator podglądu Open Graph nie czyta fontów strony — potrzebuje plików TTF. Lokalne Cinzel i Inter, kompozycja jak w hero. Osobny obraz dla X (kapryśny fallback z og:image). Wydarzenie: własny kadr social albo okładka.
  • Lightbox poza warstwami sekcji. Modal wychodzi do document.body, żeby nadrzędne overflow go nie przycinało. Pułapka fokusa, Esc i strzałki.
  • HTML z panelu nie idzie na surowo. Richtext z CMS-a przechodzi przez sanityzację, zanim trafi na stronę.
  • Własna sieć na współdzielonym VPS. Prefiks nazw kontenerów i wolumenów, osobny alias DNS do panelu (żeby nie zderzyć się z Traefikiem innych projektów), panel z noindex.

🛠️ Architektura i stack techniczny

  • Frontend: Next.js 16 (App Router, Turbopack), React 19, TypeScript (strict, noUncheckedIndexedAccess), Tailwind CSS 4
  • Typografia: next/font/google — Cinzel (serif, cała warstwa display) + Inter (sans, body)
  • Panel treści (CMS): Strapi v5 + PostgreSQL 16 (headless, server-side only)
  • Content type wydarzenia: dwujęzyczne pola w panelu Strapi (PL/EN, wbudowane i18n CMS-a — nie biblioteka na froncie), szkice i publikacja, program jako powtarzalny komponent, okładka pozioma/pionowa, galeria, osobny obraz social
  • Dostęp do danych: REST Strapi, jeden kształt wydarzenia na froncie, sklejanie PL/EN, cache na żądanie, odświeżanie treści co 5 min
  • i18n na froncie: własne, bez biblioteki (ciastko, polski domyślny, ten sam URL), paczki messages/pl.json i messages/en.json
  • Sanityzacja: isomorphic-dompurify na richtext z panelu
  • Obrazy: next/image (AVIF/WebP, lazy load, remotePatterns dla panelu), dynamiczne OG/Twitter (Satori + lokalne TTF)
  • Dane strukturalne: JSON-LD (Organization z PropertyValue KRS/NIP/REGON, Event, BreadcrumbList, Person)
  • Dostępność: WCAG 2.2 AA — SkipLink, złoty focus-visible, focus trap (lightbox), ARIA, semantyczny HTML, kontrast zweryfikowany
  • SEO: metadata per strona, alternates.canonical, dynamic sitemap + robots, obrazy OG/Twitter
  • Wdrożenie: Docker Compose (dev + prod), Traefik (TLS Let's Encrypt), multi-stage Dockerfile (node:22-alpine), healthchecki, noindex CMS, prywatny alias sieciowy

🎨 Kluczowe decyzje projektowe

  • Cinematic noir + inskrypcja rzymska. Głęboka czerń, złoto, Cinzel (kolumna Trajana) spójna z monogramem A klienta. Powściągliwy prestiż — sztuka traktowana z namaszczeniem, bez marketingowego hałasu i bez gen-AI estetyki (gradient blobs, glassmorphism, parallax).
  • Monogram A jako świadome sacrum. Klejnot w poprzeczce A — intencja marki (art + teon = sztuka + Bóg), nie ukrywanie symbolu.
  • Logo PNG zatwierdzone przez klienta. Monogram w headerze + wordmark z kropkami nad A i E w hero (sygnatura w jednym miejscu, nie rozwodniona w stopce). SVG pozostaje fallback — ostre, themeable, 4.5 KB, odwracalne.
  • Jednostronicowa perswazja. Prosta struktura: O nas / Wydarzenia / Kontakt + osobny widok wydarzeń i statut. Bez rozbudowanej architektury podstron — decydent przewija dowody wiarygodności w jednym rzucie.
  • Statut jako tekst, nie PDF. Osobna strona /statut z pełnym tekstem — czytelna dla urzędnika i crawlerów. Na głównej tylko teaser w akordeonie.
  • Wesprzyj nas z instrukcją darowizny. Numer konta, tytuł przelewu, link do oficjalnej ulgi podatkowej Ministerstwa Finansów — jasna ścieżka dla darczyńcy, bez bramki płatności.
  • Tokeny jako jedyna prawda. Kolory, typografia, spacing, radius w @theme w globals.css. Komponenty trzymają się tokenów, hex hardkodowany tylko w stałych dla generatora obrazów OG (zsynchronizowanych z tokenami, by się nie rozminęły).
  • Server Components domyślnie. use client tylko tam, gdzie niezbędne (stan, eventy, hooki przeglądarki — header, przełącznik języka, lista wydarzeń, lightbox, provider i18n). Warstwy: app/ (routing, metadata, JSON-LD), lib/ (czyste funkcje, dostęp do danych), components/ (atomy, sekcje, chrome, i18n), content/ (dane encji organizacji i statutu), messages/ (stringi UI).

Artefakty

Kontakt

Masz podobne wyzwanie? Napisz do mnie — wrócę z propozycją kolejnych kroków.

Napisz wiadomość