00-A Tokeny · jasny i ciemny · próbki · test desaturacji · odcienie color-mix

Tokeny — dwa bloki, te same nazwy, wartości v2 AIOS

Motyw jasny :root · klient / team · domyślny

--bgf3f1ectło aplikacji · ciepła szarość papieru
--cardffffffkarta · bez obrysu na jasnym
--surface-2ebe8e1pole formularza · nagłówek tabeli · hover wiersza
--surface-3dfdbd1tor toggle · licznik · shimmer
--lined3cec3obrys interaktywnych · nagłówki tabel
--line-softe6e2d9separator wierszy list
--text1f1d19tekst główny · aktywny tab · krok aktywny
--muted625d54etykiety · meta · stan „brak pomiaru” · BLOCKED
--teal0f6e56zarezerwowany (kontrakt) · nie używany w Admin
--blue2a4a8clink zewnętrzny w tabeli spec · nie status
--purple5b3d7aw kontrakcie · ZAKAZ użycia w UI
--ok2e7d4fkrawędź StatusTile ok · ikona check · linia diff add
--warn9a6400badge warn/stale · licznik menu · quota
--criticalb3261ebadge critical · krawędź error · chip „missing”
--accent-op4a3208akcent operatora: aktywna pozycja menu · primary CTA · focus
--accent-cl1f5f8bakcent klienta (owner/member): to samo zastosowanie

--accent = var(--accent-op); [data-role="client"] przełącza na var(--accent-cl). Kontrast (AA, tekst 11 px na --card): muted 6,5 · ok 5,1 · warn 5,0 · critical 6,5 · accent-op 12,0 · accent-cl 6,8.

Motyw ciemny [data-theme="operator"] · operator · wariant świadomy

--bg15171btło · neutralny grafit (nie niebieski)
--card1e2126karta
--surface-2262a30pole · nagłówek tabeli · hover
--surface-330353ctor toggle · licznik · shimmer
--line3b4149obrys interaktywnych
--line-soft2a2f36separator wierszy
--textece9e2tekst główny
--muteda8a297etykiety · meta · BLOCKED
--teal4fb59azarezerwowany
--blue8fa9e6link zewnętrzny
--purpleb79ad6ZAKAZ użycia w UI
--ok5cbf86krawędź ok · check
--warnbd8a26badge warn/stale · quota
--criticale5695fbadge critical · error
--accent-opf7cd78akcent operatora — jasny, wyraźnie jaśniejszy niż warn
--accent-cl7fb6e0akcent klienta

--accent = var(--accent-op). Kontrast na --card: muted 6,4 · ok 7,1 · warn 5,3 · critical 5,0 · accent-op 10,6 · accent-cl 7,4. Tekst na primary CTA = --bg (11,3).

Test desaturacji — akcent ≠ warn po zdjęciu koloru

Lewa kolumna: kolor. Prawa: filter:grayscale(1). Primary CTA i badge warn muszą różnić się jasnością, nie tylko odcieniem. Jasny: accent-op (lum 0,04) vs warn (0,16) → stosunek 2,4. Ciemny: accent-op (0,65) vs warn (0,30) → 2,0. Wynik: przechodzi w obu motywach i obu rolach.

rola operator 3 blockery · harness FAIL · snapshot · BLOCKED brak pomiaru OK Exit
rola client 3 blockery · harness FAIL · snapshot · BLOCKED brak pomiaru OK Exit
rola operator 3 blockery · harness FAIL · snapshot · BLOCKED brak pomiaru OK Exit
rola client 3 blockery · harness FAIL · snapshot · BLOCKED brak pomiaru OK Exit
rola operator 3 blockery · harness FAIL · snapshot · BLOCKED brak pomiaru OK Exit
rola client 3 blockery · harness FAIL · snapshot · BLOCKED brak pomiaru OK Exit
rola operator 3 blockery · harness FAIL · snapshot · BLOCKED brak pomiaru OK Exit
rola client 3 blockery · harness FAIL · snapshot · BLOCKED brak pomiaru OK Exit

Odcienie — wyłącznie color-mix(in srgb, var(--token) N%, transparent)

--accent 12% tło aktywnej pozycji menu
--warn 12% / 30% tło i obrys badge warn
--critical 10% / 30% badge critical · chip missing
--ok 12% linia diff „+” · --critical 10% linia „−”

Brak tokenów tintowych. Procenty stałe: tło 10–12 %, obrys 30 %, scrim 24 % --text, focus ring 40 % --accent. Przy nowym tincie mierzyć kontrast osobno — nie kopiować procentu.

00-B Typografia · 7 stopni · mono tylko dane · wagi

Skala typograficzna — 7 stopni, stack systemowy

--fs-mini10px · etykieta osi wykresu · countdown conceal · licznik AionLineQuota 50 USD · 03:07 · dzień 1 … 30
--fs-meta11px · etykieta pola · badge · linia weryfikacji · meta wierszaOstatnia rotacja 2026-08-14 · LIVE · 03:07 · operator
--fs-body13px · treść · wiersz tabeli · przycisk · pozycja menuWynik skanu dist/ — 3 wystąpienia URL *.aionflow.pl w 2 plikach.
--fs-title15px · tytuł karty · wartość StatusTile · nagłówek draweraExitHarness · FAIL · 3 wystąpienia
--fs-h218px · nagłówek sekcji · tytuł kill-gateEject wizard — 6 kroków runbooka
--fs-h126px · tytuł strony (jedyny bold 700)Exit / eject
--fs-num28px · liczba w StatCard (mono)3 / 6

Mono tylko dla danych

ID · hash · czas · kod · subject · host · slug · wartości modules.json. Nigdy dla etykiet, tytułów, opisów.

poprawnie
tenantaion-marketing·https://id.aionflow.pl/application/o/hub|andrzejniemiec52@gmail.com
ostatni skan·_astro/hoisted.ab12cd.js
źle — etykieta w mono, „cisza” zastąpiona badge’em ok
Ostatni skanwszystko OK

Wagi i przypadki

  • 700 tylko tytuł strony (h1).
  • 650 nagłówki sekcji, tytuły kart, aktywna pozycja menu, wartość StatusTile.
  • 600 przyciski, badge, mocne słowa w meta.
  • 500 reszta: treść, pozycje menu, wiersze.
  • Sentence case wszędzie. Zero wielkich liter w CSS, zero rozstrzelenia. Skróty typu LIVE, SEO, ZIP, URL zostają skrótami w treści.
  • Interlinia 1,45 treść · 1,2 tytuły · 1,7 kod w diff.
00-C Komponenty — jasny · klient / owner · data-role=client

Biblioteka komponentów — jasny · klient/owner

.badge · .state · .verify — status = ikona + tekst + LIVE hh:mm / UNVERIFIED
3 blockery · FAIL · STALE · BLOCKEDLOCAL-GATEDbrak pomiaru4 sloty·OK — bez badge’auwagabłądnieznane
LIVE · STALE · UNVERIFIEDBLOCKED
.btn — primary / focus / secondary / active / ghost / danger / disabled (kreskowany + powód) / loading
aktywne po ExitHarness PASS
.gate-table — blockery per rekord, deep link do Directusa; wiersz OK = cisza
RekordBlockeryAutor
lejek-dwustopniowy
missing descriptionmissing canonical
andrzej-niemiecDirectus
intencja-nie-keyword
missing Article JSON-LD
aion-niemiecDirectus
nie-sprzedajemy-pakietowbez blockerówandrzej-niemiecDirectus
koszt-pozyskania-klienta-cac
missing sources
aion-niemiecDirectus
.conceal — ukryty · pokaż 5 s · rotacja · brak
AION_TENANT_KEY· ukryty
••••••••••••••••••••••••
ostatnia rotacja LIVE ·
AION_TENANT_KEY· pokazany na 5 s
atk_live_9f3c2e7a41b8d05e6c17f2a9b3d4e5f6ukryję za
AION_TENANT_KEY· rotacja w toku
generuję nowy klucz w hub…
stary klucz ważny jeszcze · zaktualizuj .env tenanta
PEXELS_API_KEY· brak
nie skonfigurowano
.mode-badge aion | standalone
tryb aiontryb standalonew stopce menu systemu; w standalone znikają quota, tenant key, Chaos seed
.kill-lock + .toggle
aios-commerceBLOCKED
kill-gate Discovery — wymaga katalog + inventory + fulfillment · profiles: [] · werdykt Discovery
toggle offtoggle ontoggle zablokowany — kreskowany, bez wygaszania
.diff-panel — JSON przed/po
przed · modules.json
po · modules.json
{  "mode": "aion",  "tenant_id": "aion-marketing",  "plugins": [    "aios-seo", "aios-articles",    "aios-images", "aios-webmcp",    "aios-tracking"  ],  "profiles": [],  "hub": {    "usage_url": "https://hub.aionflow.pl/api/usage"  }}
{  "mode": "standalone",  "tenant_id": null,  "plugins": [    "aios-seo", "aios-articles",    "aios-images", "aios-webmcp",    "aios-tracking"  ],  "profiles": [],  "usage": { "sink": "directus:usage_log" }  }
3 usunięte · 3 dodaneUNVERIFIED
.event-stream — czas mono · ikona · treść · źródło
build data → seo-gate → astro build → pagefind · 41 spipeline
ExitHarness FAIL · 3 wystąpienia w dist/exit-harness
flush usage → hub · 128 rekordów · cost_usd_month 41,20 / 50usage-meter
zmiana modules.json · packs +content-credentialsoperator
ingest obrazu lejek-dwustopniowy-hero.jpg · tor A · 4 wariantyaios-images
.empty-checklist — co widać → dlaczego → kroki runbooka → jedna CTA

Brak wyniku skanu — nie ma jeszcze dist/

ExitHarness czyta artefakty builda. Zbuduj stronę, a wynik pojawi się tu z czasem weryfikacji.

  1. Directus health 200curl directus/server/health
  2. Zbuduj stronęnpm run build
  3. Uruchom skannpm run exit-harness -- apps/starter/dist
runbook §5
.skeleton — shimmer przez przesuwany blok (bez gradientu, bez opacity)
.blocked-banner · .banner--error · .banner--warn
Eject wymaga roli owner lub operatora BLOCKED
Zalogowano jako member. Widok jest tylko do odczytu — to nie jest „partial done”.
Skan dist/ niedostępny z panelu LOCAL-GATED
Harness działa lokalnie na buildzie. Uruchom npm run exit-harness -- dist i wgraj wynik JSON.
.wizard / .step — done · active · fail · lock; kto może
1
Tryb sieci → standaloneoperator · owner
modules.json: "mode": "standalone", "tenant_id": null
LIVE · mode=standalone
3
UsageMeter → lokalny sinkoperator
źródło = Directus usage_log; brak quoty hub
UNVERIFIED
5
ExitHarness PASSoperator · owner
3 wystąpienia *.aionflow.pl w dist/
LIVE · FAIL
6
Odłącz huboperator
usuń symlink / wpis w clients.json · po kroku 5
.chart-bars — czyste div-y, linia quoty, brak danych = surface-3
80 % quoty
1 sie15 sie30 sie
units / dzień≥ 80 % quotybrak danych (dziś)
.tabs (aktywny = tekst + pasek --text, nie akcent) · .form / .input / .seg
aion-marketing
Aion Marketing
hub.aionflow.pl/api/usage
wymagany schemat https://
dayserviceprovider
.drawer — panel boczny 360 px; w widoku: nad treścią, pod topbar, na lewo od AionLine

Rotacja klucza tenanta

Nowy AION_TENANT_KEY zostanie wygenerowany w hub. Stary klucz działa jeszcze 24 h — w tym czasie zaktualizuj .env w repo tenanta i zrób rebuild.

klucz w logu CI · 2026-09-02
Wyślij nowy klucz ownerowi przez hub inbox
00-D Komponenty — ciemny · operator · data-theme=operator

Biblioteka komponentów — ciemny · operator

.badge · .state · .verify — status = ikona + tekst + LIVE hh:mm / UNVERIFIED
3 blockery · FAIL · STALE · BLOCKEDLOCAL-GATEDbrak pomiaru4 sloty·OK — bez badge’auwagabłądnieznane
LIVE · STALE · UNVERIFIEDBLOCKED
.btn — primary / focus / secondary / active / ghost / danger / disabled (kreskowany + powód) / loading
aktywne po ExitHarness PASS
.gate-table — blockery per rekord, deep link do Directusa; wiersz OK = cisza
RekordBlockeryAutor
lejek-dwustopniowy
missing descriptionmissing canonical
andrzej-niemiecDirectus
intencja-nie-keyword
missing Article JSON-LD
aion-niemiecDirectus
nie-sprzedajemy-pakietowbez blockerówandrzej-niemiecDirectus
koszt-pozyskania-klienta-cac
missing sources
aion-niemiecDirectus
.conceal — ukryty · pokaż 5 s · rotacja · brak
AION_TENANT_KEY· ukryty
••••••••••••••••••••••••
ostatnia rotacja LIVE ·
AION_TENANT_KEY· pokazany na 5 s
atk_live_9f3c2e7a41b8d05e6c17f2a9b3d4e5f6ukryję za
AION_TENANT_KEY· rotacja w toku
generuję nowy klucz w hub…
stary klucz ważny jeszcze · zaktualizuj .env tenanta
PEXELS_API_KEY· brak
nie skonfigurowano
.mode-badge aion | standalone
tryb aiontryb standalonew stopce menu systemu; w standalone znikają quota, tenant key, Chaos seed
.kill-lock + .toggle
aios-commerceBLOCKED
kill-gate Discovery — wymaga katalog + inventory + fulfillment · profiles: [] · werdykt Discovery
toggle offtoggle ontoggle zablokowany — kreskowany, bez wygaszania
.diff-panel — JSON przed/po
przed · modules.json
po · modules.json
{  "mode": "aion",  "tenant_id": "aion-marketing",  "plugins": [    "aios-seo", "aios-articles",    "aios-images", "aios-webmcp",    "aios-tracking"  ],  "profiles": [],  "hub": {    "usage_url": "https://hub.aionflow.pl/api/usage"  }}
{  "mode": "standalone",  "tenant_id": null,  "plugins": [    "aios-seo", "aios-articles",    "aios-images", "aios-webmcp",    "aios-tracking"  ],  "profiles": [],  "usage": { "sink": "directus:usage_log" }  }
3 usunięte · 3 dodaneUNVERIFIED
.event-stream — czas mono · ikona · treść · źródło
build data → seo-gate → astro build → pagefind · 41 spipeline
ExitHarness FAIL · 3 wystąpienia w dist/exit-harness
flush usage → hub · 128 rekordów · cost_usd_month 41,20 / 50usage-meter
zmiana modules.json · packs +content-credentialsoperator
ingest obrazu lejek-dwustopniowy-hero.jpg · tor A · 4 wariantyaios-images
.empty-checklist — co widać → dlaczego → kroki runbooka → jedna CTA

Brak wyniku skanu — nie ma jeszcze dist/

ExitHarness czyta artefakty builda. Zbuduj stronę, a wynik pojawi się tu z czasem weryfikacji.

  1. Directus health 200curl directus/server/health
  2. Zbuduj stronęnpm run build
  3. Uruchom skannpm run exit-harness -- apps/starter/dist
runbook §5
.skeleton — shimmer przez przesuwany blok (bez gradientu, bez opacity)
.blocked-banner · .banner--error · .banner--warn
Eject wymaga roli owner lub operatora BLOCKED
Zalogowano jako member. Widok jest tylko do odczytu — to nie jest „partial done”.
Skan dist/ niedostępny z panelu LOCAL-GATED
Harness działa lokalnie na buildzie. Uruchom npm run exit-harness -- dist i wgraj wynik JSON.
.wizard / .step — done · active · fail · lock; kto może
1
Tryb sieci → standaloneoperator · owner
modules.json: "mode": "standalone", "tenant_id": null
LIVE · mode=standalone
3
UsageMeter → lokalny sinkoperator
źródło = Directus usage_log; brak quoty hub
UNVERIFIED
5
ExitHarness PASSoperator · owner
3 wystąpienia *.aionflow.pl w dist/
LIVE · FAIL
6
Odłącz huboperator
usuń symlink / wpis w clients.json · po kroku 5
.chart-bars — czyste div-y, linia quoty, brak danych = surface-3
80 % quoty
1 sie15 sie30 sie
units / dzień≥ 80 % quotybrak danych (dziś)
.tabs (aktywny = tekst + pasek --text, nie akcent) · .form / .input / .seg
aion-marketing
Aion Marketing
hub.aionflow.pl/api/usage
wymagany schemat https://
dayserviceprovider
.drawer — panel boczny 360 px; w widoku: nad treścią, pod topbar, na lewo od AionLine

Rotacja klucza tenanta

Nowy AION_TENANT_KEY zostanie wygenerowany w hub. Stary klucz działa jeszcze 24 h — w tym czasie zaktualizuj .env w repo tenanta i zrób rebuild.

klucz w logu CI · 2026-09-02
Wyślij nowy klucz ownerowi przez hub inbox
00-E Shell · menu systemu 244/64 · topbar · AionLine 56/200 · oba motywy

Shell — menu systemu 244 px (lewo) · topbar 56 px · AionLine 56 px (prawo)

Góra: jasny, owner, menu 244 + AionLine 56. Dół: ciemny [data-theme="operator"], operator, menu zwinięte 64 + AionLine rozsunięty 200.
Treść widoku — patrz plansze Exit / Ustawienia.
Treść widoku — patrz plansze Exit / Ustawienia.

Menu systemu · 244 / 64

  • Brand AIOS Admin + tenant switcher (tylko operator; owner widzi statyczny kod tenanta w kreskowanej ramce).
  • 12 pozycji IA §1; liczniki tylko przy problemie (SEO 3 warn, Exit 3 critical). Puls bez licznika = cisza.
  • Commerce z kłódką, tooltip „kill-gate Discovery”; nie znika — pokazuje, że gate istnieje.
  • Stopka: .mode-badge + build ok · 12 min.
  • Aktywna pozycja = jedyne użycie --accent poza primary CTA i focus ring (tło 12 % + pasek 3 px).
  • Wariant 64 px: ikony 20 px, aktywny = pasek dolny; etykiety i liczniki ukryte.

AionLine · 56 / 200 (prawo)

  • Warstwa ekosystemu wg AIONLINE-CONTRACT: systemy · inbox uniwersalny (licznik --critical) · wiadomości + obecność (kropka --ok) · profil · wyloguj · rozsuń.
  • Rozsuwa się w lewo do 200 px; nie wypycha menu systemu.
  • Topbar produktu bez dzwonka i profilu — tylko okruszki i ⌘K.
  • Drawer widoku wchodzi między treść a AionLine (right = 56 px).
00-F Ikony · sprite inline · 20/24/16 px

Ikony — jeden zestaw liniowy 1,5 px, inline SVG sprite

pulse
modules
doc
seo
image
webmcp
track
usage
build
exit
cart
settings
lock
unlock
check
check-c
x
x-c
alert
help
clock
refresh
eye
eye-off
copy
rotate
link
unlink
external
arrow
chev-d
chev-l
chev-ll
chev-rr
search
grid
inbox
users
user
logout
server
db
key
shield
zip
file
folder
play
download
plus
minus
trash
edit
globe
terminal
palette
info
history
branch
menu
loader
bell
msg
cloud-off
tag
00-G Spec · decyzje systemowe · mapowanie etykiet · lista komponentów

Spec — decyzje systemowe sesji 03.09

1 · Cisza jako OK

  1. Element bez problemu nie ma badge’a: StatusTile ok = zielona krawędź 3 px + ikona check + tekst wartości + LIVE · hh:mm. Wiersz GateTable bez blockerów = .state--ok „bez blockerów” (ikona + tekst, bez tła).
  2. Badge pojawia się tylko dla: warn · critical · stale · blocked (LOCAL-GATED) · brak pomiaru.
  3. Puls w menu nie ma licznika, gdy nic nie blokuje wydania. Licznik 0 nie istnieje.
  4. Zielony (--ok) wolno użyć tylko z dowodem: tooltip title na .verify niesie komendę lub endpoint.

2 · Gdzie wolno użyć akcentu

  1. Aktywna pozycja menu systemu (tło 12 % + pasek 3 px).
  2. Primary CTA — dokładnie jeden na widok (Exit: „Wygeneruj ZIP klienta”; Ustawienia: „Zapisz zmiany”).
  3. Focus ring 3 px 40 %.
  4. Nic więcej: tabs aktywne = --text; krok aktywny wizardu = krawędź --text; linki = podkreślenie --line; ikony neutralne.
  5. --accent-op jasny = ciemny miód 4a3208, ciemny = jasny bursztyn f7cd78. Oba oddalone jasnością od --warn (test desaturacji ≥ 2,0).
  6. --accent-cl = stalowy niebieski, nie teal (--teal zostaje w kontrakcie nieużyty).

3 · Etykiety wiarygodności → komponenty

EtykietaKomponentWygląd
LIVE.verify--liveikona check-c + LIVE (tekst) + · hh:mm mono; tooltip = komenda/endpoint. Jedyny stan, w którym StatusTile może być ok.
UNVERIFIED.verify + .status-tile--unknown + .badge--unknown „brak pomiaru”ikona help, kolor --muted, krawędź kreskowana. Nigdy zielony.
STALE.badge--stale + .banner--warnikona history, obrys kreskowany --warn 45 %, czas ostatniego pomyślnego odczytu obowiązkowy.
BLOCKED / LOCAL-GATED.blocked-banner + .badge--blocked + .kill-lock + .step--lockkłódka, --muted, obrys kreskowany, zawsze powód + jedna CTA. To nie błąd (--critical) i nie „partial done”.
FAIL (błąd pomiaru).badge--critical + .banner--error + .error-panelikona x-c, --critical, log w pre, przycisk „Spróbuj ponownie”.

4 · Kolor = stan

  • --ok/--warn/--critical wyłącznie na: badge, ikona stanu, lewa krawędź StatusTile/StatCard/banner, słupek ≥ 80 % quoty, linia diff. Nigdy tło karty.
  • Status nigdy samym kolorem: ikona + tekst zawsze (.state, .badge).
  • Wygaszanie bez opacity: --muted + obrys kreskowany + etykieta (disabled, lock, unknown).
  • Hierarchia przez tło (--bg → --card → --surface-2) i odstęp (sekcje 40 px, w sekcji 8–12 px). Obrys 1 px tylko interaktywne i wiersze.

5 · Sekrety i mono

  • .conceal: •••• + „Pokaż 5 s” (countdown mono) + „Kopiuj” (po kliknięciu) + „Rotuj” (drawer potwierdzenia, stary klucz 24 h). Wartość nigdy w DOM stanu ukrytego.
  • DIRECTUS_* tylko operator — owner widzi .blocked-banner „tylko operator”, nie pusty formularz.
  • Mono: ID, hash, czas, kod, subject, host, slug, wartości manifestu. Etykiety zawsze w --font-ui.

6 · Ruch, ikony, gęstość

  • Ruch ≤ 140 ms (--dur) tylko hover/focus; skeleton shimmer 1200 ms = przesuwany blok --surface-3 (bez gradientu i opacity); spinner 1200 ms na loading.
  • Ikony liniowe 1,5 px: 20 px listy/menu, 24 px kafle, 16 px w badge/verify/przyciskach small. Jeden sprite inline.
  • Operator: rytm 8 px w sekcji, wiersz 44 px, tabela 11–13 px. Klient: te same komponenty, jasny motyw, więcej oddechu (gap 24).
  • Zakazy egzekwowane walidatorem: hex poza tokenami, uppercase, letter-spacing, opacity, gradient, glow, blur, pill-cluster, emoji.

Komponenty §5 użyte w sesji

.status-tile · .gate-table · .conceal · .mode-badge · .kill-lock · .diff-panel · .event-stream · .empty-checklist · .skeleton · .blocked-banner · .stat-card · .chart-bars · .tabs · .drawer — plus pomocnicze: .badge .state .verify .btn .wizard/.step .toggle .chk .form/.input/.seg .banner .error-panel.