Files
roa2web-service-auto/docs/service-auto/tabele-service-auto.md
Claude Agent 6aceb85bf1 docs(service-auto): design review + VFP audit (Correction 12)
plan-design-review pass: 6/10 → 9/10. Added interaction-states table
(6-state PrimeVue spec matching ReceiptCreateUnifiedView.vue toast
conventions), design-system inheritance clause (DESIGN.md/TOKENS/
CSS_PATTERNS), a11y one-liner, week-3 subtask for enum+labels
extraction from VFP source.

Cloned gitea.romfast.ro/romfast/vfp_roaauto and wrote a 300+ line
ground-truth audit (docs/service-auto/tabele-service-auto.md)
covering: DEV_ORDL parent/child inheritance with NOM_LUCRARI,
DEV_TIP_DEVIZ enum (1-7, including user-confirmed Productie/
Constatare for 6/7), dev_adauga_lucrare v1 (pack_devize, 12+1
params, body visible in packages.sql) vs v2 (pack_auto, 17+1,
body only in MARIUSM_AUTO), and the pack_sesiune.dev_idLucrare
trigger/session-state pattern (ROA ERP convention from pre-
RETURNING era, not a bug).

Plan Correction 12 added: the prototype needs a ~40-line SP doing
two INSERTs parent→child with RETURNING id_lucrare (bypassing
pack_sesiune), targeting dev_ordl via nom_lucrari. Original
assumption of a 4-param new SP was wrong. Week 3 subtask updated
to reference the audit draft. ACT/RUL untouched at creation time
— Correction 3 still valid.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-06-05 09:37:09 +00:00

24 KiB

Tabele + SP-uri Service Auto — VFP ground truth audit (v2)

Status: v2 generat 2026-04-11 de Claude pe baza analizei gitea.romfast.ro/romfast/vfp_roaauto (clonat în /workspace/vfp_roaauto). Acum se bazează și pe Scripturi_instalare/packages.sql, initializari.sql, triggere.sql, tabele.sql — nu doar pe .prg files. DE CONFIRMAT în săpt 3 prin interogări reale pe schema MARIUSM_AUTO.

Scop: înlocuiește task-ul "deschide VFP producție cu grijă" din planul v2. Sursa e gitea, zero risc de modificare accidentală.

Corecție v2 (2026-04-11): v1 presupunea că tabela principală e comenzi. REALITATE: tabela fizică e DEV_ORDL (PK: id_ordl). vcomenzi e un view denormalizat care face JOIN cu dev_tip_deviz, dev_masiniclienti, parteneri, etc. Planul v2 referință corectă: DB = dev_ordl, UI = "comandă".


1. Entități — terminologie reconciliată

Confirmat de Marius 2026-04-11: terminologia vine din ierarhia ROA (ERP generic) vs ROAAUTO (extensie service auto). Pattern de inheritance prin două tabele:

Nivel Termen Tabelă Ce conține
Base (ROA ERP) comandă nom_lucrari Doar numele/nrord-ul comenzii — vizibil în ACT (registrul jurnal) și RUL (rulaje gestiune) când comanda e referențiată la facturare
Extension (ROAAUTO) deviz auto dev_ordl Toate detaliile specifice auto: mașină, km, termen, asigurator, tip deviz, inspector, observații

"Comandă" = generic (valabil pentru orice industrie — service, construcții, producție...). "Deviz" e mai specific: e calculul costului (manoperă + materiale consumate) pentru o comandă într-un context de industrie: deviz auto, deviz construcții, etc. În ROAAUTO, fiecare comandă de service auto ARE un deviz auto atașat (prin dev_ordl + dev_oper + dev_mat).

Relația FK:

nom_lucrari (id_lucrare PK)
    ↑
    │ FK (id_lucrare)
    │
dev_ordl (id_ordl PK, id_lucrare FK → nom_lucrari.id_lucrare)

Confirmat în tabele.sql:634:

alter table DEV_ORDL add constraint FK_...
  references NOM_LUCRARI (ID_LUCRARE);

Consecință pentru prototype: crearea unei comenzi face INSERT în AMBELE tabele, în ordine:

  1. INSERT INTO nom_lucrari (nrord, id_mod) VALUES (...) — creează header-ul generic
  2. INSERT INTO dev_ordl (id_lucrare, id_tip, id_masiniclient, kmint, ...) VALUES (...) — creează extensia auto, legată prin id_lucrare

ACT și RUL: nom_lucrari.nrord e vizibil în ACT (registrul jurnal) și RUL (rulaje gestiune) când comanda e referențiată la facturare. Dar crearea comenzii NU touch-uiește nici ACT nici RUL — acestea sunt hit-uite doar la facturare, care e NOT IN SCOPE pentru prototype. Correction 3 din planul v2 rămâne validă.

Componente backend Pydantic: ComandaCreate, ComandaCreated (termen UI), backend service face cele două INSERT-uri într-o tranzacție, returnează id_ordl și nr_comanda.


2. Tabela principală: comenzi (view: vcomenzi)

Schema extrasă din COMUN/programe/onom_comenzi.prg:72-79. Partea vizibilă în UI:

Coloană Tip VFP Tip Oracle probabil Note
id_comanda N(20) NUMBER(20) PK, alias-ul pentru id_ordl
id_ordl NUMBER(20) Numele intern în PL/SQL (OUT param din SP)
comanda_externa C(20) VARCHAR2(20) Nr. comandă extern client
id_codclient C(20) VARCHAR2(20) FK client (char, nu numeric!)
id_lucrare N(20) NUMBER(20) FK la vlucrari_detalii
id_part N(20) NUMBER(20) FK partener
id_agent N(20) NUMBER(20) FK agent vânzări
id_delegat N(20) NUMBER(20) FK delegat
id_masina N(20) NUMBER(20) FK la masini_client (id_mc)
nr_comanda C(100) VARCHAR2(100) Nr. comandă intern cu prefix tip (ex: G123, R456)
data_comanda T TIMESTAMP Data creării
nume C(70) VARCHAR2(70) Nume client (denormalizat)
tip_comanda C(20) sau C(50) VARCHAR2(50) Display name denormalizat (ex: "Garanție")
data_livrare T TIMESTAMP Termen execuție/livrare
nume_agent C(70) Denormalizat
nume_delegat C(70) Denormalizat
nrinmat C(10) VARCHAR2(10) Nr. înmatriculare mașină
nrord C(30) VARCHAR2(30) Nr. ordine (intern)
facturat N(1) NUMBER(1) Flag facturat (0/1)
dataora T TIMESTAMP Audit
utilizator C(40) VARCHAR2(40) Username creator
data_livrat T TIMESTAMP Data livrării efective
interna N(1) NUMBER(1) Flag comandă internă
nr_livrare C(50) VARCHAR2(50) Nr. bon livrare
inchisa N(1) NUMBER(1) Flag închisă
id_sectie N(5) NUMBER(5) Secția care a creat comanda (MANDATORY)
id_sectie2 N(5) NUMBER(5) Secția care execută (dacă diferă)
id_facturare N(5) NUMBER(5) FK adresa facturare
id_livrare N(5) NUMBER(5) FK adresa livrare
id_ctr N(10) NUMBER(10) FK contract (pentru clienți B2B cu discount-uri)
numar_contract C(100) VARCHAR2(100) Nr. contract denormalizat

Total: ~28 coloane în view-ul vcomenzi. Planul prototype-ului (4 fields: tip, client, mașină, operații) e o simplificare agresivă — e OK pentru learning, dar să fii conștient că VFP-ul real captează mult mai multă informație.


3. Tabele conexe (referențiate la create)

Tabelă / view Rol Folosită de prototype?
vcomenzi_elemente Linii detaliu (articole, cantități) — "rețeta" comenzii NU — prototype scope wall, doar header
vlucrari_detalii Lucrări / operații finalizate NU — execuție post-creare
vlucrari_elemente Articole consumate pe o lucrare NU
masini_client Mașinile clienților (FK id_mc) NU — dropdown hardcodat în Vue
parteneri Clienți (FK id_codclient) NU — dropdown hardcodat
optiuni Configurare per-secție (Key/Value) Doar indirect prin pack_comenzi.extrage_optiuni
adrese_parteneri Adrese facturare/livrare NU — valoare default din partener
contracte Contracte cu discount-uri B2B NU — scope wall

Pentru prototype: insert-ul simplificat atinge doar comenzi (view vcomenzi), zero JOIN-uri cross-table. Scope wall ține.


4. SP-ul real de creare — DOUĂ versiuni

Surpriză importantă: există două versiuni ale dev_adauga_lucrare în sursele ROAAUTO, în pachete diferite.

4.1. Versiunea INSTALL-TIME: pack_devize.dev_adauga_lucrare (12 IN + 1 OUT)

Sursa: Scripturi_instalare/packages.sql:182-212 — body-ul complet e vizibil.

Semnătura:

procedure dev_adauga_lucrare(
  v_gcs    in varchar2,   -- schema
  tnan     in number,     -- an
  tnluna   in number,     -- luna
  tnIdUtil in number,     -- id user
  pcNr     in varchar2,   -- nr comandă cu prefix (ex: 'G12345')
  pnIdInsp in number,     -- id inspector
  pnIdAsig in number,     -- id asigurator
  pnIdMC   in number,     -- id mașină client (dev_masiniclienti.id_masiniclient)
  pnKmInt  in number,     -- km la bord
  pdTermen in date,       -- termen execuție
  pnTipCom in number,     -- id tip (FK dev_tip_deviz.id_tip)
  pnIdOrdl out number     -- OUT: id_ordl generat
)

Body real (din packages.sql:196-212):

begin
  -- 1. Side effect: creează rând în NOM_LUCRARI cu id_mod=1200
  execute immediate 'INSERT INTO ' || v_gcs || '.NOM_LUCRARI (NRORD, ID_MOD)
      VALUES (:1, 1200)'
    using pcNr;

  -- 2. Insert principal în DEV_ORDL
  execute immediate 'insert into ' || v_gcs || '.dev_ordl
      (an, luna, id_inspector, id_lucrare, datai, id_util_ad,
       id_masiniclient, id_asigurator, id_tip, kmint, termen, dataoraad)
      values (:1, :2, :3, :4, :5, :6, :7, :8, :9, :10, :11, :12)
      returning id_ordl into :13'
    using tnAn, tnLuna, pnIdInsp,
          pack_sesiune.dev_idLucrare,   -- <-- session state dependency!
          v_dataora, tnIdUtil, pnIdMC, pnIdAsig, pnTipCom,
          pnKmInt, pdTermen, V_DATAORA
    returning into pnIdOrdl;

  -- 3. Side effect: update km la mașina clientului
  execute immediate 'update ' || v_gcs || '.dev_masiniclienti
      set kmint=:1 where id_masiniclient=:2'
    using pnKmInt, pnIdMC;
end;

Observații critice (post-clarificare Marius 2026-04-11):

  • Cele două INSERT-uri sunt pattern de inheritance, nu side effects:
    • Step 1 = INSERT în NOM_LUCRARI (parent, base ROA ERP) — creează header-ul generic al comenzii (numele care va fi vizibil în ACT/RUL la facturare)
    • Step 2 = INSERT în DEV_ORDL (child, extensie ROAAUTO) — creează extensia auto legată prin id_lucrare
    • Ambele sunt esențiale. Fără step 1, dev_ordl e orphan FK violation.
  • Side effect real (step 3): UPDATE pe dev_masiniclienti.kmint — actualizează odometrul mașinii clientului pentru a reflecta ultima intrare în service. Nu e parte din creare, e sincronizare colaterală. Poate fi omis în prototype.
  • Dependency pe pack_sesiune.dev_idLucrare — după step 1, trigger-ul pe nom_lucrari (probabil TRG_NOM_LUCRARI_BEFOINS) populează pack_sesiune.dev_idLucrare := :new.id_lucrare. Step 2 citește acest state session pentru a completa id_lucrare în dev_ordl. Pattern-ul vine din ROA ERP-ul mainframe-era, unde session state era modul standard de comunicare între trigger și procedură. Nu e bug, e convenție istorică.
  • Pentru roa2web bypass e trivial: folosim RETURNING id_lucrare INTO v_local după INSERT-ul pe nom_lucrari — trigger-ul încă populează pack_sesiune.dev_idLucrare (dacă există în MARIUSM_AUTO), dar noi îl ignorăm și citim direct prin RETURNING clause. Standard Oracle, zero dependency. Confirmat prin pattern-ul identic la dev_ordl (TRG_DEV_ORDL_BEFOINS la triggere.sql:1165-1172 — SEQ_DEV_ORDL.NEXTVAL INTO :new.id_ordl + pack_sesiune.dev_idOrdl := :new.id_ordl).
  • datai și dataoraad sunt ambele sysdate local — nu primite ca param.

4.2. Versiunea PRODUCȚIE: pack_auto.dev_adauga_lucrare (17 IN + 1 OUT)

Sursa: Programe/oproceduri_devize.prg:147-148 — doar CALL-ul VFP. Body-ul NU e în Scripturi_instalare/packages.sql — pachetul pack_auto a fost adăugat după install. Body-ul real trăiește doar în DB-ul MARIUS-ului.

Call-ul din VFP:

begin
  pack_auto.dev_adauga_lucrare(
    ?gcS, ?gnAn, ?gnLuna, ?gnIdUtil, ?pcNr, ?pnIdInsp,
    ?pnIdAsig, ?pcNrDosar, ?pnIdMC, ?pnKmInt, ?pnOreFct,
    to_date(?, 'DD/MM/YYYY'),
    ?pntipcom, ?pcSirIDOperatiiClient, ?pcObservatii,
    ?pcDefectiuni, ?pnIdPartRef, ?@pnIdOrdl
  );
end;

5 params adăugați în v2 față de v1:

  • pcNrDosar — nr dosar daună (pentru garanție cu asigurator)
  • pnOreFct — estimare ore manoperă la intrare
  • pcSirIDOperatiiClient — listă operații pre-selectate de client (CSV de IDs)
  • pcObservatii / pcDefectiuni — notes structurate
  • pnIdPartRef — partener referent

Sursa body-ului real în MARIUSM_AUTO — de extras în săpt 3 cu:

SELECT text FROM all_source
WHERE owner='MARIUSM_AUTO' AND name='PACK_AUTO' AND type='PACKAGE BODY'
ORDER BY line;

4.3. Implicații pentru prototype — trei opțiuni

# Strategie Pro Contra
1 Reuse pack_auto.dev_adauga_lucrare v2 direct (17 params, majoritatea defaults hardcodate în Python) Hedge max: dovedește reuse pachet producție inclusiv side-effects. Template deliverable max value. Depinde de pack_sesiune.dev_idLucrare care nu e inițializat în sesiunea roa2web. Risc că pică la primul call pentru context lipsă.
2 Reuse pack_devize.dev_adauga_lucrare v1 (12 params, body vizibil în sursă) Știi exact ce face SP-ul (body în packages.sql). 5 params mai puțin. Același bug pack_sesiune. 12 params sunt încă mult pentru 2h/săpt.
3 SP nou minimal SP_CREEAZA_COMANDA_PROTOTIP cu INSERT direct în dev_ordl cu câmpurile minime + returning id_ordl Control total. Zero dependențe. Simplu. Testable. Hypothesis #1 probată la fel de bine. Bypass-uie business logic. Template deliverable e "SP simplu", nu "reuse pachet legacy". Hedge slăbit puțin.

Recomandare actualizată (după descoperirea pack_sesiune):

Opțiunea 3 (SP nou minimal) e acum recomandarea principală. Motivul: pack_sesiune introduce un coupling invizibil cu session state VFP care ar sabota prototype-ul la prima tentativă — iar ipoteza #1 (Python+oracledb apelează PL/SQL cu OUT params) e probată la fel de bine de un SP simplu ca de unul complex. Reuse-ul production-logic rămâne pentru phase 2.

Hedge-ul rămâne valabil: template-ul deliverable poate documenta ambele pattern-uri ("pentru SP-uri simple: pattern X; pentru SP-uri legacy cu pack_sesiune: investigă în phase 2 cum să inițializezi session state în Python").

Decision point săpt 3/4: verifică body-ul pack_auto.dev_adauga_lucrare în MARIUSM_AUTO. Dacă e refactored fără pack_sesiune, revin-o la opțiunea 1. Altfel, opțiunea 3.

SP minimal propus (opțiunea 3) — corectat pentru inheritance pattern:

CREATE OR REPLACE PROCEDURE MARIUSM_AUTO.SP_CREEAZA_COMANDA_PROTOTIP(
  p_id_tip          IN NUMBER,      -- FK dev_tip_deviz.id_tip (1-7)
  p_id_masiniclient IN NUMBER,      -- FK dev_masiniclienti.id_masiniclient
  p_kmint           IN NUMBER,      -- km la bord
  p_termen          IN DATE,        -- termen execuție
  p_id_util         IN NUMBER,      -- user creator
  p_nr_comanda      IN VARCHAR2,    -- generat în Python cu prefix (G/R/P/PR/C)
  p_id_ordl         OUT NUMBER,     -- id-ul din dev_ordl (pentru UI)
  p_numar_out       OUT VARCHAR2    -- ecou al nr_comanda (simetrie API)
) AS
  v_id_lucrare NUMBER;              -- local, bypass pack_sesiune.dev_idLucrare
  v_dataora    DATE := SYSDATE;
BEGIN
  -- 1. INSERT parent: nom_lucrari (header generic vizibil în ACT/RUL la facturare)
  INSERT INTO MARIUSM_AUTO.nom_lucrari (nrord, id_mod)
    VALUES (p_nr_comanda, 1200)
    RETURNING id_lucrare INTO v_id_lucrare;
    -- ^ RETURNING bypasses dependency on pack_sesiune.dev_idLucrare
    -- ^ trigger TRG_NOM_LUCRARI_BEFOINS still fires + populates session var,
    --   but we ignore it and use our local v_id_lucrare instead

  -- 2. INSERT child: dev_ordl (extensia auto, FK la nom_lucrari prin id_lucrare)
  INSERT INTO MARIUSM_AUTO.dev_ordl
    (an, luna, id_inspector, id_lucrare, datai, id_util_ad,
     id_masiniclient, id_asigurator, id_tip, kmint, termen, dataoraad)
  VALUES
    (EXTRACT(YEAR FROM v_dataora), EXTRACT(MONTH FROM v_dataora),
     0,                  -- id_inspector = 0 (nu folosim inspector în prototype)
     v_id_lucrare,       -- FK la nom_lucrari
     v_dataora,          -- datai
     p_id_util,
     p_id_masiniclient,
     0,                  -- id_asigurator = 0 (nu folosim asigurator)
     p_id_tip,
     p_kmint,
     p_termen,
     v_dataora)          -- dataoraad
  RETURNING id_ordl INTO p_id_ordl;

  -- Step 3 (UPDATE dev_masiniclienti.kmint) SKIP — side effect opțional
  -- pentru prototype. Dacă vrem să-l includem, adăugăm aici:
  --   UPDATE dev_masiniclienti SET kmint = p_kmint
  --    WHERE id_masiniclient = p_id_masiniclient;

  p_numar_out := p_nr_comanda;
END;
/

~40 linii, două INSERT-uri în ordinea FK-ului parent→child, RETURNING pentru chaining, zero dependency pe pack_sesiune. Testabil din SQL Developer:

DECLARE
  v_id  NUMBER;
  v_num VARCHAR2(100);
BEGIN
  MARIUSM_AUTO.SP_CREEAZA_COMANDA_PROTOTIP(
    p_id_tip => 3,                           -- Regie
    p_id_masiniclient => 1,                  -- prima mașină client existentă
    p_kmint => 150000,
    p_termen => SYSDATE + 10,
    p_id_util => 1,                          -- user test
    p_nr_comanda => 'R' || TO_CHAR(MARIUSM_AUTO.SEQ_NRORD.NEXTVAL),
    p_id_ordl => v_id,
    p_numar_out => v_num
  );
  DBMS_OUTPUT.PUT_LINE('id_ordl: ' || v_id || ', nr: ' || v_num);
  ROLLBACK;  -- pentru test, nu commit
END;
/

Avantaj: exact pattern-ul pe care îl va folosi Python (callproc cu OUT params + manual commit). Dovedește ipoteza #1 pe un SP realist care atinge DOUĂ tabele în ordine corectă, nu pe un test_out trivial.


5. tip_comanda — enum real extras din DDL + seed

Sursa primară: Scripturi_instalare/tabele.sql:763-794 (DDL) + Scripturi_instalare/initializari.sql:199-208 (seed INSERT).

Tabela reală: DEV_TIP_DEVIZ (nu dev_tip_comenzi — user a corectat, dar ground truth din scripturile de instalare zice dev_tip_deviz; confirmă în săpt 3 care e numele în MARIUSM_AUTO — poate au redenumit-o).

DDL

create table DEV_TIP_DEVIZ
(
  ID_TIP   NUMBER(5) not null,      -- PK, auto-generat din SEQ_DEV_TIP_DEVIZ
  DENUMIRE VARCHAR2(50) not null,   -- Label afișat în dropdown
  STERS    NUMBER(1) default 0 not null  -- Soft delete flag
);
alter table DEV_TIP_DEVIZ add constraint PK_TIP_DEVIZ primary key (ID_TIP);

Notă: update_devize.prg:424 selectează id_tip, denumire, inch_validare from dev_tip_deviz — coloana inch_validare NU e în DDL-ul din tabele.sql, deci a fost adăugată post-install printr-o migrație. Așteaptă-te la diferențe între schema "curată" și MARIUSM_AUTO real.

FK în DEV_ORDL

Linia 203 din packages.sql arată coloana folosită pe tabela de comandă:

insert into <schema>.dev_ordl
    (an, luna, id_inspector, id_lucrare, datai, id_util_ad, id_masiniclient,
     id_asigurator, id_tip, kmint, termen, dataoraad)
    values (...)
    returning id_ordl into pnIdOrdl

Coloana este id_tip (nu tip_comanda). Numele tip_comanda apare doar în view-ul vcomenzi ca alias denormalizat pentru denumire din JOIN-ul cu dev_tip_deviz.

Seed values (install-time, din initializari.sql:199-208)

ID_TIP DENUMIRE Prefix pe nr_comanda (din oproceduri_devize.prg:109-120)
1 POST GARANTIE (niciun prefix)
2 GARANTIE G
3 REGIE R
4 PREGATIRE P
5 REGIE 2 (niciun prefix — skipped în switch)

IDs 6 și 7 (cu prefix PR, respectiv C) NU sunt în seed-ul de install — au fost adăugate în producție prin INSERT INTO dev_tip_deviz (sau prin UI-ul VFP de admin). Denumirea lor o știe Marius — de confirmat în săpt 3.

Verificare în săpt 3

-- Lista completă curentă din MARIUSM_AUTO
SELECT id_tip, denumire, sters
FROM MARIUSM_AUTO.DEV_TIP_DEVIZ
ORDER BY id_tip;

-- Verifică dacă există alias-ul 'dev_tip_comenzi' ca synonym sau view
SELECT object_name, object_type
FROM all_objects
WHERE owner='MARIUSM_AUTO'
  AND UPPER(object_name) LIKE '%TIP%COM%';

Pentru prototype (decision)

ComandaNoua.vue are nevoie de un dropdown cu 4 opțiuni. Hardcodarea în Vue e OK pentru prototype (scope wall: nu există endpoint /tipuri-comanda). Recomandare valori:

  • {id: 1, label: 'Post Garanție'}
  • {id: 2, label: 'Garanție'}
  • {id: 3, label: 'Regie'}
  • {id: 4, label: 'Pregatire'}
  • {id: 5, label: 'Regie 2'}
  • {id: 6, label: 'Productie'}
  • {id: 7, label: 'Constatare'}

Skip ID-ul 5 (REGIE 2, probabil deprecated).


6. Label-uri Romanian pentru formulare

Extrase din context VFP (nume variabile + procese). Aceste label-uri le folosești în ComandaNoua.vue:

Câmp UI Label Romanian Corespondent VFP
Tip comandă Tip comandă tip_comanda / combobox în frm_gencom
Client Client nume (denormalizat) / id_codclient
Mașină Mașină (sau Număr înmatriculare) nrinmat / id_masina
Operații solicitate Operații solicitate pcSirIDOperatiiClient
Km la intrare Km la bord pnKmInt (în VFP se afișează "kmint")
Ore manoperă estimate Ore manoperă pnOreFct
Termen execuție Termen execuție (default = today + gnTermenZileService) pdTermen
Observații Observații pcObservatii
Defecțiuni Defecțiuni pcDefectiuni
Nr. dosar daună Nr. dosar (doar dacă tip=garanție/asigurare) pcNrDosar

Pentru MVP-ul prototype-ului (4 câmpuri): păstrează doar primele 4 din tabel (tip / client / mașină / operații). Restul trec în plan ca TODO-phase2 sau se afișează cu valori default hardcodate.

Toast-uri (Romanian, convenție ROA2WEB din ReceiptCreateUnifiedView.vue):

  • Success: summary="Comandă creată", detail="Nr ${nr_comanda}" (ex: "Nr G12345")
  • Business error: summary="Validare", detail=<mesajul din SP după strip prefix ORA-20xxx>
  • Infra error: summary="Eroare conexiune" (503) / "Eroare internă" (500)

7. Funcții PL/SQL utile găsite în VFP source

Din grep pack_auto\. și pack_comenzi\. pe tot repo-ul:

Funcție/Proc Scop Relevantă pentru prototype?
pack_auto.dev_adauga_lucrare Creează comandă (17 params) DA — SP-ul principal
pack_auto.dev_adauga_oper_fact Adaugă operații pe comandă pentru facturare NU — post-facturare
pack_auto.dev_distribuie_timp_n Distribuie timp pe norme NU
pack_auto.citeste_discount_contract Citește discount-uri contract NU
pack_auto.actualizeaza_deviz Updatează deviz NU
pack_auto.getOptiuneInchidere(n) Citește opțiune închidere NU
pack_auto.set_perioada_raport Setează perioadă raport NU
pack_comenzi.extrage_optiuni(varvalue, id_sectie) Citește opțiuni pe secție Poate — pentru tip_comanda default
pack_comenzi.genereaza_nr_lucrare Generează nr. lucrare Poate — alternativ la prefix hardcodat
pack_comenzi.sectii_utilizator(id_util, id_sucursala) Secții accesibile utilizatorului Poate — pentru multi-section support phase 2

Pattern observat: {call pack_auto.proc(?param, ?@out_param)} pentru apeluri cu OUT. Confirmă că oracledb async cu OUT params e un pattern deja stabilit în stack-ul VFP → Oracle.


8. Next steps — săpt 3 task list (actualizat)

În loc de task-ul vag "deschide VFP producție și caută fluxul de creare comandă":

  • Clonează gitea.romfast.ro/romfast/vfp_roaauto local (dacă nu e clonat)
  • Conectează-te la 10.0.20.121/ROA ca ROA_WEB (sau alt user cu acces la all_objects pe MARIUSM_AUTO)
  • Rulează și salvează în week3-verification.sql:
    -- Verifică existența pachetului pack_auto
    SELECT object_name, object_type, status
    FROM all_objects
    WHERE owner='MARIUSM_AUTO'
      AND object_name IN ('PACK_AUTO','PACK_COMENZI');
    
    -- Verifică coloanele din comenzi (confirmă schema de mai sus)
    SELECT column_name, data_type, data_length, nullable
    FROM all_tab_columns
    WHERE owner='MARIUSM_AUTO' AND table_name='COMENZI'
    ORDER BY column_id;
    
    -- Găsește tabela/nomenclatorul pentru tip_comanda
    SELECT table_name
    FROM all_tables
    WHERE owner='MARIUSM_AUTO'
      AND UPPER(table_name) LIKE '%TIP%COM%';
    
    -- Lista procedurilor din pack_auto (pentru a decide opțiunea 1 vs 3)
    SELECT procedure_name, overload
    FROM all_procedures
    WHERE owner='MARIUSM_AUTO' AND object_name='PACK_AUTO'
    ORDER BY procedure_name;
    
  • Decide: opțiunea 1 (reuse dev_adauga_lucrare), 2 (wrapper), sau 3 (INSERT direct)
  • Confirmă denumirile pentru tip_comanda = 4, 6, 7
  • Completează secțiunea 5 și 6 de mai sus cu valorile confirmate
  • Commit pe branch feat/service-auto cu mesaj docs(service-auto): confirm VFP audit against real MARIUSM_AUTO schema

9. Ce NU am găsit încă (gaps pentru săpt 3)

  • Forma UI realăfrm_gencom e definită într-un .vcx (VFP binary class file), nu grep-abil direct. Pentru layout-ul real și ordinea câmpurilor în UI-ul VFP, fie deschid VFP-ul (nu în scope), fie Marius trimite un screenshot în săpt 3.
  • Default values — care sunt valorile default în frm_gencom? pdTermen are DATE() + gnTermenZileService (default 10 zile) — asta e relevant. Restul defaults trebuie verificate.
  • Validările client-side — VFP face probabil validări în frm_gencom.valid(). Pentru prototype, planul deja spune "no client-side validation" — nu e gap real.
  • Permission modelgcAcces=[1;2;3;4;] apare în onom_comenzi.prg:14 — sugerează un sistem de ACL cu 4 nivele. Irelevant pentru prototype (1 user), dar de notat pentru TODO-phase2.

END OF DRAFT — să fie revăzut și completat în săpt 3, 2026-05-05 → 2026-05-09.