Audit: handoff-ul Dublin (PRD + prototip) către Prodi — read-only, 19 sep 2026
PRD-ul și prototipul Dublin, contra skill-urilor folosite și contra a ce avea nevoie implementarea. Verdict și exemplul „De plată”.
Întrebarea BGN: „Am făcut PRD-ul și prototipul Dublin cu Claude Code și am crezut că am urmat instrucțiunile din bono-skills și convențiile proiectelor lui Prodi. A fost așa? Ce trebuia făcut altfel?"
Metodă. Citit artefactul local (/Users/bgnpro17/Desktop/Proiecte IT/Bono/Dublin/), site-ul live, skill-urile folosite (bono-prd / bono-prototype / bono-product-flow, Bruce v3/bruce-v3-master.md) și 6 repo-uri bono-ro clonate shallow în scratchpad (bono-skills, dublin, nucleu-product, company-directory, vertigo-product, facturare-prd). Nimic modificat. Folderul Dublin nu e repo git; versiunea „de la 3–7 aug" e reconstruită din datările interne (jurnal §9).
1. Ce a conținut handoff-ul
1.1 Cele două momente
| 3–7 aug 2026 (predarea inițială) | după 25 aug (reorganizarea la cererea Prodi) | |
|---|---|---|
/prd | 2 tab-uri: „Arhitectura" (analiza de implementare) + „Specificații" (= PRD v1, jurnalul) — jurnal §9: „Tab PRD live (3.aug) — cu 2 tab-uri" | 3 tab-uri: Funcțional (nou, default) · Arhitectura · Jurnal (fost Specificații) — build-prd.py modificat 25 aug 11:37 |
dublin-prd-v1.md (jurnal) | ~100+ KB (§5–5b scrise 9 iul–7 aug) | 160 KB · 522 linii · 23.445 cuvinte; 264 mențiuni datate; 173 valori în px; „hover" 28×, „bej" 38× |
dublin-analiza-implementare-3aug2026.md | v1 3 aug, v2 4 aug | 68 KB · 9.643 cuvinte; inventar componente cu coloana „Sursa datelor", NFR, repo-uri explorate, arhitectură propusă, dimensionare, faze F0–F6, fluxuri A–E |
dublin-prd-functional.md | nu exista | 21 KB · 2.960 cuvinte; shell + 10 pagini + reguli globale; tag de sistem pe fiecare informație ([NUCLEU] 27×, [SAGA→NUCLEU] 10×, [F] 8×, [IRIS] 8×, [S] 7×…); 10 acțiuni „→ [sistem]" |
| Prototip | 9 pagini desktop | 40 fișiere HTML, 2,3 MB (10 desktop, 22 mobil în două serii, 2 pagini „-38", dublin-prd.html 289 KB, 2 pagini istorice) |
| Live | dublin.bgn.ro/prd = 276 KB într-o pagină · / = 118 KB | idem |
Notă de încredere: antetul funcționalului spune „Actualizat: 6 august 2026", dar conține decizii din 25 aug, 31 aug și 8 sep, iar jurnalul îl declară „nou" pe 25 aug. Pentru un cititor ca Chris („nu pot da mai departe un PRD scris de Claude pe care nu l-am citit"), un antet stale costă mai mult decât pare.
1.2 Raportul spec funcțională : jurnal de decizii : detaliu de design
Pe volum: Funcțional 8 % · Arhitectură 27 % · Jurnal 64 % din 249 KB. Jurnalul e istorie de UI: „De plată — v1 construit" (liniile 249–260) are ~9.000 de caractere despre grile (230px · repeat(3, 1fr) · 90px), materiale bej/dark/alb, durata pill-ului „✓ COPIAT" (1,4 s → 5 s), versiuni v1.3…v2.7 — și zero propoziții despre de unde vine cifra 8.740 lei sau ce se vede când SAGA n-a închis luna. Bruce v3 cerea „decision-log subțire"; a ieșit cel mai gros document din pachet.
1.3 Ce spune, ecran cu ecran, versiunea de după 25 aug
| Criteriu de handoff | Funcțional (25 aug+) | Dovadă |
|---|---|---|
| Sursa per informație afișată | Parțial — tag de sistem, nu de câmp/endpoint | §6: „obligațiile pe 5 categorii … [SAGA→NUCLEU]"; Nucleul nu avea niciun API (Atom fără rute) |
| Acțiuni cu sistemul-țintă | Da | 10× „→ [F]/[NUCLEU]/[NUCLEU→IRIS]/[Rex]/[BILL]" |
| Stări UI (empty / loading / error) | Nu — „Reguli & stări" = stări de business, nu de ecran; jurnal §9 le are încă la „De făcut" | „empty/gol" 0×; „eroare/eșec" 2× |
| Permisiuni / roluri | Parțial — „un cont = o firmă, fără roluri"; nimic despre contul suspendat per pagină | §11, §12 |
| Cerințe nefuncționale | Da, în alt document — Arhitectura §2: 30.000 clienți, 10 ani, on-prem | auditul Nucleu 16 sep: „scrise — dar în PRD-ul Dublin, nu aici" |
| Criterii de acceptare | Nu — niciun ID de cerință, niciun „dat fiind/când/atunci" | 0 apariții |
| Out of scope | Da — §12 + jurnal §6 | |
| Contracte I/O per sistem | Nu — Arhitectura §7: „Contractul API al NUCLEULUI … îl pot drafta ca spec". Nu a fost draftat |
Prototipul: date hardcodate în HTML (De plată: 80 de sume, 0 tablouri JS; Facturi: 22 rânduri <tr data-st data-suma data-cui…> pentru filtrare client-side), 0 apeluri fetch//api, 0 atribute de sursă pe vreo cifră. Prototip de design, nu de date — nimeni nu poate deriva din el ce câmp vine de unde.
2. Contra a ce cereau skill-urile
2.1 Cerințele impuse și cum au fost îndeplinite
| Cerință (sursa) | Stare | Dovadă |
|---|---|---|
| bono-prd §6: fiecare ecran cu ACTOR · JOB · INFORMAȚII · ACȚIUNE PRINCIPALĂ · STĂRI | Îndeplinit (funcțional 25 aug+: Afișăm / Acțiuni / Reguli & stări per pagină) | dublin-prd-functional.md §1–§11 |
| bono-prd §2 state machine a entității principale | Îndeplinit — statusuri canonice document (5) + factură (Încasată/Neîncasată + e-Factura) | §3, §4 |
| bono-prd §4 parametri configurabili (tabel opțiuni + default) | Parțial — scadență default 10 zile, fereastra 5 zile lucrătoare, ~6 iteme rail — împrăștiate, fără tabel | §1, §3 |
| bono-prd §5 comunicare / mesaje trimise | Neîndeplinit — nicio listă de notificări (email/push) către client | — |
| bono-prd §7 non-goals | Îndeplinit | §12, jurnal §6 |
| bono-prd §8 metrici de succes | Neîndeplinit | — |
| bono-prd „Date existente & integrări" | Peste cerință — Arhitectura §3 explorează 5 repo-uri | §3.1–3.5 |
| bono-prd „După prototip — PRD update (obligatoriu)": adaugă „interacțiuni (hover, popup, validări)", „layout decisions (grid, coloane, carduri)" — „Acesta e PRD-ul final care se predă la development" | Îndeplinit literal — exact asta a produs jurnalul de 160 KB | jurnal §5–§5b |
| bono-prototype: un artefact, mock data românesc, „fiecare element din PRD e în prototip" | Îndeplinit (audit 8 agenți, 3 aug) | jurnal „Audit de conformitate" |
| bono-product-flow: discovery → research → PRD → prototip | Îndeplinit — fluxul se termină aici; nu există pasul 5 | bono-product-flow/SKILL.md |
| Bruce v3 §5: „prototipul DEVINE spec", „decision-log subțire + stări (empty / onboarding / erori)" | Parțial — log-ul nu e subțire; stările lipsesc | bruce-v3-master.md l.144–152 |
| Bruce v3 rutare: UI-heavy (Dublin) → „IA + home + secțiuni"; contractele doar la Logic-heavy | Îndeplinit conform rutării — dar rutarea e greșită pentru un shell: Dublin nu calculează nimic, deci e 100 % contracte | l.155–160 |
bono-skills (Prodi): react-19-vite-frontend, dotnet-api-blueprint, nhibernate-cqrs, edge-33, edge-audit, qa-* | Nu se aplică unui PRD — convenții de cod și DS. Singurul „handoff" din tot repo-ul: edge-audit „when an application built by product enters handoff to implementation" — verifică DS-ul, nu datele | bono-skills/plugins//skills//SKILL.md |
qa-spec (bono-skills): compilează prototip + PRD în screens.json (stări default/empty/loading/error) + flows.yaml (source: "PRD §06") | Nu a fost rulat pe Dublin — dar e singura definiție scrisă în casă a unui PRD verificabil | qa-skills/skills/qa-spec/SKILL.md |
2.2 Constatarea despre skill-uri
Niciun skill folosit nu definește un format de handoff către inginerie. bono-prd se oprește la „PRD-ul final care se predă la development" fără să spună ce conține un PRD predabil — ba cere să se adauge grile și hover-uri. bono-product-flow are 4 pași și se termină la prototip. Bruce v3 declară limita („NU dă deciziile fine de layout"), dar nu are un pas „contract cu sistemele". bono-skills e inginerie și DS; qa-spec presupune PRD-ul deja bun. BGN a urmat instrucțiunile; instrucțiunile nu conțineau pasul care lipsea.
Ce au în plus PRD-urile vecine (reper, nu acuză): facturare-prd/PRD_Modul_Facturare_MVP.md (54 KB, Teo/Octav) — §4 „Bootstrap payload" JSON complet, §5 catalog de endpoints (method · route · pentru ce · frecvență), §8 „Erori și fallbacks", §10 statusurile facturii; vertigo-product/PRD_Vertigo.md (40 KB, Cristi) — la fiecare tab un tabel de stări + o linie „Sursă." + changelog cu autor; company-directory/docs/search-lucene-spec.md (Prodi, 56 KB, „forma de referință") — Scope in/out, constrângeri C-1…C-4, marcaje [CONFIRM] pe presupunerile de verificat. Toate trei sunt mai lungi decât funcționalul Dublin; diferența nu e lungimea, e contractul.
3. Contra a ce avea nevoie implementarea
3.1 Repo-ul dublin (Prodi)
17 commit-uri, 1–9 sep, toate Prodi: „BFF scaffolding", „Adapted Edge theme onto shadcn", „Showcased design system components". Router: customers, ui-showcase, desire, formular, setari (placeholder-ele șablonului); DashboardPage.tsx: „Static mock numbers". Zero referințe la PRD, prototip sau dublin.bgn.ro în README, CLAUDE.md, BFF-ARCHITECTURE.md sau cod. La 6 săptămâni de la handoff, implementarea canonică consumase doar design system-ul. Prodi la retreat: „Greșeala mea a fost să întreb cum ajung datele în Dublin" — a pornit de la contracte și nu le-a găsit.
3.2 Ce a trebuit să reconstruiască Chris (nucleu-product)
data/fluxuri.js: 32 de fluxuri — 16 „de făcut", 6 „neclar", 4 „există", 3 „de testat", 3 „azi, un om". Ating Dublin direct 3: f01 client→Dublin (există), f02 Dublin→Findocs (de făcut — Prodi: „direct în baza de date … sau prin API"), f24 Atom→Dublin „cifrele fiecărui ecran" (de făcut — „Fiecare cifră are un drum"). Celelalte 29 sunt în spatele lui f24.
data/ecrane.js — „Circuitul apei", refăcut de Chris: 60 de rânduri pe 9 ecrane, toate 60 cu „gap"; din 192 de salturi, 41 „ok", 135 „plan", 16 „gap". Întrebările la care PRD-ul nu răspundea:
- De unde vin taxele. PRD: „[SAGA→NUCLEU]". Prodi: SAGA ține taxele „pe conturi contabile, nu defalcate — am aflat acum două săptămâni". Circuitul apei: micro „din balanță, nu din declarație; contul după regimul perioadei"; TVA „în contul lui, nu în contul unic"; taxe salarii = două plăți (cont unic + CAM), PRD zice „UN singur transfer".
- Detaliile de plată (beneficiar, IBAN trezorerie). PRD: „[SAGA→NUCLEU]". Chris: „Nu vin din SAGA; le ținem noi."
- Statusul Încasată/Plătit. PRD: „reconcilierea de lângă nucleu". fluxuri.js: f14 „citire directă din Firebird, de testat"; f11 robotul de bifat „de testat"; Lotus retras 9 sep; regula de stingere = caseta 5.3, deschisă.
- Când Iris nu poate interpreta. Analiza §6: „fluxul se propune ÎN IRIS … de așteptat propunerea" — amânat, nu răspuns; Dublin n-are stare de ecran pentru el.
- Identitate / firmă curentă. PRD: „[ID], claim CUI". Repo: parolă demo
"bono", CUI din config; registrul firmelor Holo → Nucleu → sesiune, 3 salturi „plan". - Ce API per cifră. Niciuna; tag-ul e sistemul, nu endpoint-ul.
- „LIVE · 24.apr" — Chris: „Nu există live: contabilitatea vine din SAGA o dată pe lună. Eticheta trebuie schimbată." „Totul e ok azi" — depinde de task-uri, care sunt V2.
- Luna curentă vs. luni închise — venituri din facturile emise (curentă) vs. balanță 70x (închise); PRD arată o singură cifră.
- Impozit pe dividende se înregistrează la plată, nu la hotărâre; impozite locale au analitic per bun, în profilul firmei (Vertigo), nu în Dublin; firma nouă n-are balanță în prima lună — nicio stare pentru asta.
- Arhitectura propusă a fost răsturnată — Arhitectura §4.0.c: „nu bază partajată". Audit Nucleu 16 sep: „arhitectura din PRD-ul Dublin nu se preia." Documentul de produs luase o decizie de CTO; CTO-ul a luat-o invers.
Prodi la retreat: „în PRD-ul Dublin găsești în fiecare ecran lucruri de rezolvat … poate SAGA nu ține evidența în felul în care Dublin vrea să le prezinte." Nu pentru că PRD-ul e prost, ci pentru că a fost scris dinspre client spre sisteme, iar sistemele nu fuseseră întrebate.
4. Cum arăta un handoff bun — exemplu pe „De plată"
Standard: Integral plan-first (REQ-ID cu ≥2 criterii de acceptare, integrări, constrângeri, NFR) + Shape Up (problemă, apetit, rabbit holes, no-gos). Două pagini per ecran. Mai jos, numai cu informație care există azi în PRD; ce lipsește e [LIPSEȘTE].
DE PLATĂ — /de-plata · owner produs: BGN · owner tehnic: [LIPSEȘTE] · apetit: [LIPSEȘTE] (Prodi: „2–3 săpt. tot Dublin")
PROBLEMA „Cât am de plătit, până când — și dă-mi tot ce-mi trebuie ca să plătesc în 30 s." (jurnal, 22 iul)
NO-GOS fără plată din Dublin (card→ANAF = în analiză) · fără calcul fiscal în Dublin · fără CASS pe dividende (obligația persoanei)
CE AFIȘĂM · SURSA · CONTRACT
REQ-DP-01 KPI „De plată acum" = Σ obligații scadente neplătite
sursa: SAGA→Nucleu · [LIPSEȘTE] câmpul (balanță XML? cont 4423/444/431x?) · [LIPSEȘTE] endpoint · [LIPSEȘTE] cadență (la închidere de lună)
AC1 suma = Σ rândurilor „De plată" afișate · AC2 când nu există lună închisă → [LIPSEȘTE] stare „fără situație închisă"
REQ-DP-02 5 categorii: TVA · taxe salarii · impozit micro/profit · impozit dividende · impozite locale, fiecare: sumă / scadență / stare
sursa TVA, micro: SAGA→Nucleu (Circuitul apei: „din balanță, nu din declarație") · salarii: [S] · locale: decizia încărcată de client → Iris
AC1 micro vs profit se alege după vectorul fiscal al PERIOADEI (firma poate schimba regimul în an) · AC2 scadența legală alunecă peste weekend (25→luni 27)
[LIPSEȘTE] taxe salarii = UN rând, dar DOUĂ plăți (cont unic + CAM) — care e regula de afișare?
REQ-DP-03 Detalii de plată per obligație: beneficiar · IBAN trezorerie · sumă · detalii (CUI)
sursa: [LIPSEȘTE] — PRD zice SAGA→Nucleu; Nucleu zice „le ținem noi": tabel trezorerie per județ × 3 conturi (unic/CAM/TVA), owner [LIPSEȘTE]
AC1 IBAN copiat fără spații · AC2 suma copiată „8740,00" · AC3 detalii = „<tip> <perioadă> · CUI <cui>"
REQ-DP-04 Stare „Plătit" + istoric 3 luni
sursa: reconciliere lângă Nucleu (owner Prodi, fezabilitate 1 oct) · [LIPSEȘTE] regula de stingere (legea: pe bugete, proporțional, reținut la sursă, apoi cea mai veche — caseta 5.3)
AC1 „Plătit" apare doar după potrivirea cu extrasul · AC2 până la reconciliere: rândul rămâne „De plată" cu nota „așteptăm extrasul"
REQ-DP-05 Impozite locale fără decizie → „Așteptăm decizia" + upload
AC1 upload = doar confirmare de primire · AC2 după procesare Iris: sumă + rate + primărie pe rând · [LIPSEȘTE] ce se întâmplă dacă Iris nu citește decizia
STĂRI DE ECRAN [LIPSEȘTE] empty (firmă nouă, nicio lună închisă) · loading · eroare sursă (SAGA nu a livrat) · abonament suspendat
PERMISIUNI un cont = o firmă (MVP) · [LIPSEȘTE] ce vede contul suspendat
NFR citire; polling 30–60 s nu se aplică (date lunare) · [LIPSEȘTE] termen maxim de propagare închidere SAGA → ecran
PUNCTE DE INTEGRARE Nucleu (citire obligații + plăți) · Iris (decizie de impunere) · SalarEasy (baza salarii) · [LIPSEȘTE] care e apelul pentru fiecare
RABBIT HOLES stingerea parțială a unei taxe · regimul schimbat în cursul anului · mai multe primării · „Plătește taxele" (legal ConsAudit)
DEFINIȚIA LUI GATA [LIPSEȘTE] — propunere: o firmă sintetică cu lună închisă în SAGA afișează 5 rânduri corecte, verificate de contabil (Raluca)
Diferența față de §6 din funcțional nu e volumul (aproape egal), ci că fiecare rând poate primi „da/nu" de la Prodi și „confirm/infirm" de la Raluca — și că cele 14 [LIPSEȘTE] sunt vizibile înainte de cod, nu descoperite după.
5. Verdict
A fost muncă de produs bună? Da, peste standardul casei: nevoie închisă cu research pe 12 platforme, IA validată, 9 pagini + mobil în DS, audit PRD↔prototip cu 8 agenți, decizii fine (locale „deducem + cerem", „Plătit" ≠ „Plătită", „Banii tăi" pe 3 niveluri) pe care niciun PRD anterior din echipă nu le are. Prodi: „documentația și PRD-urile cu prototip sunt la all-time high". Auditul Nucleului a găsit retenția, on-prem-ul, volumele și izolarea între firme doar în PRD-ul Dublin.
A fost un handoff bun către inginerie? Nu. Trei motive concrete, în ordinea greutății:
- Tag-ul de sistem nu e un contract. „[SAGA→NUCLEU]" pe 10 cifre, când SAGA ține taxele pe conturi și Nucleul n-avea API, înseamnă că fiecare cifră a rămas de negociat cu 3 oameni. Chris a scris 60 de rânduri de „Circuit al apei", toate cu gap.
- Analiza de arhitectură a intrat în artefactul de produs (faze, dimensionare, broker, „nu bază partajată") și a fost răsturnată de CTO pe 16 sep. Din momentul în care o parte e „nu se preia", tot documentul devine „de verificat".
- 64 % jurnal / 8 % funcțional și 40 de fișiere HTML pentru cititori care n-au fost în sesiuni. Chris: „nu pot da mai departe un PRD … pe care nu l-am citit"; Alexandra: „40 de pagini, două săptămâni". Funcționalul din 25 aug a rezolvat lungimea, nu contractul.
A cui e vina? A metodei (60 %) — bono-product-flow se oprește la prototip, bono-prd cere grile în PRD-ul „final", Bruce v3 rutează Dublin ca „UI-heavy" fără contracte, deși un shell e numai contracte; nimeni în casă nu avea un format de handoff (nici Prodi — company-directory are spec pentru un serviciu, nu pentru un produs cu 6 dependențe). A skill-urilor lui Prodi (10 %) — bono-skills nu spune ce primește inginerie de la produs. A lui BGN (30 %) — nu pentru ce a scris, ci pentru ce putea face fără skill: (a) să nu lase Claude să scrie arhitectură și faze într-un document semnat „BGN + Claude" fără sign-off de CTO — regula proprie „doc extern care atinge decizii = diff + OK înainte de scriere" se aplica și aici; (b) „Contractul API al Nucleului — îl pot drafta ca spec" a rămas propoziție din 4 aug până azi; fără el handoff-ul nu era terminat; (c) 264 de datări și „v2.7 (4 aug)" într-un document predat unui om care n-a fost acolo — jurnalul trebuia să fie pentru autor, funcționalul pentru cititor, de la început.
6. Ce facem altfel — schița skill-ului bono-handoff (pasul 5, după prototip)
- Handoff-ul e un document separat de PRD și de jurnal, max 2 pagini per ecran, cu antet care spune versiunea reală, data reală și cine l-a citit (owner produs · owner tehnic · contabil).
- Fiecare cifră afișată primește un rând: sursă → câmp/fișier → transport → owner → cadență; un tag de sistem fără cont contabil sau nume de câmp nu e acceptat.
- Fiecare acțiune primește sistemul-țintă + apelul (sau „apel de definit, owner X, până la Y") + ce vede clientul dacă apelul eșuează.
- Fiecare cerință are REQ-ID și cel puțin două criterii de acceptare testabile pe o firmă sintetică; „gata" îl verifică un contabil, nu autorul.
- Patru stări de ecran obligatorii — empty (firmă nouă), loading, eroare de sursă, cont suspendat — în text, înainte de desen.
- Un tabel de presupuneri
[CONFIRM](modelul lui Prodi dinsearch-lucene-spec.md) cu cine confirmă și până când; documentul nu e „predat" cât are rânduri fără răspuns. - Zero arhitectură în handoff: faze, broker, dimensionare, „cine deține ce" merg ca întrebări pentru CTO într-o anexă, nu ca decizii.
- Zero pixeli: culori, grile, durate rămân în prototip și edge-33; un detaliu vizual care e regulă de produs (IBAN fără spații) intră ca REQ, nu ca CSS.
- Prototipul se predă cu
qa-specrulat (screens.json+flows.yamlcusource: PRD §N) și cu datele demo marcatesample_data. - Sesiune de citire împreună, nu link trimis: 60 de minute cu owner-ul tehnic, ecran cu ecran, fiecare rând ✅ / ❓ / ✗ în aceeași zi; gata când nu mai există ❓.
- Jurnalul rămâne al autorului: publicat separat, marcat „istorie, nu spec", nenumărat în „paginile PRD-ului".
- Retro la 30 de zile: procentul de rânduri dovedite false sau incomplete (la Dublin: 60/60) e metrica skill-ului; sub 20 % = handoff bun.
Surse: /Users/bgnpro17/Desktop/Proiecte IT/Bono/Dublin/{dublin-prd-functional,dublin-prd-v1,dublin-analiza-implementare-3aug2026}.md + prototype/ · skill-uri bono-prd/bono-prototype/bono-product-flow (pluginul Claude.ai, ~/Library/Application Support/Claude/…/skills/) · Diverse/Claude/Bruce v3/bruce-v3-master.md · repo-uri bono-ro/{bono-skills,dublin,nucleu-product,company-directory,vertigo-product,facturare-prd} (clone shallow în scratchpad) · citate retreat din extras-ziua-1.md, extras-ziua-2-tehnic.md, 02_ce-s-a-discutat-la-retreat.md.
The Bono Way · v2 · Planul de lansare · 19 septembrie 2026 · pregătit de Claude pentru Bogdan; capitolele se rescriu de owner-ii lor. Sursa: repo „Bono Waiy", Markdown.