# Investigatie: discount pe articol (linie de factura) — ROAFACTURARE Intrebare: discountul pe articol e azi doar procentual, sau exista si discount in valoare absoluta pe unitate / pe linie? ## 1. Model de date — DISCOUNT / DISCOUNT_UNITAR **Concluzie**: Exista deja o coloana de discount **in valoare absoluta pe unitate** (`DISCOUNT_UNITAR`) pe `VANZARI_DETALII` (si pe `VANZARI_DETALII_TEMP`, tabela de lucru din care se compune factura), pe langa discountul de document `VANZARI.DISCOUNT` (valoare absoluta rezultata dintr-un procent aplicat la baza, nu procent stocat). Exista si un flag boolean `VANZARI.DISCOUNT_EVIDENTIAT`. **Dovezi**: - Tip coloana: `alter table VANZARI_DETALII modify discount_unitar NUMBER(22,6);` / `alter table VANZARI_DETALII_TEMP modify discount_unitar NUMBER(22,6);` / `alter table CRM_POLITICI_PRET_ART modify discount_unitar NUMBER(22,6);` — `D:\ROA\DATABASE\SCRIPTURI_CLAR\2024\06\ff_2024_06_13_02_COMUN_FACTURARE.sql:3,9,16`. Precizia `(22,6)` e cea folosita la coloane de pret/valoare, nu la procente. - Exista si la nivel de politica de pret (`CRM_POLITICI_PRET_ART.DISCOUNT_UNITAR`), deci discountul unitar poate proveni din politica de pret a clientului, nu doar tastat pe linie. - Coloana e folosita direct ca scadere din pret: `A.PRET - NVL(A.DISCOUNT_UNITAR, 0) AS PRET` — `D:\ROA\DATABASE\SCRIPTURI_CLAR\2026\03\ff_2026_03_23_04_COMUN_PACK_FACTURARE.sql:3315,3500`. - Document-level: `v.discount as disc_fara_tva` / `v.discount_evidentiat` — `D:\ROA\DATABASE\SCRIPTURI_CLAR\2011\08\ff_2011_08_30_02_FACTURARE.sql:36-42,251-252,267,291`. Discountul document e o valoare (lei/valuta), calculata din procent tastat de operator x baza (vezi punctul 3), nu un procent stocat pe `VANZARI`. ## 2. VFP — grid-uri de linii factura (`frm_facturare_articole` si `frm_facturare_articole2`) **Concluzie**: Ambele forme au coloane de grid pentru discountul unitar **in valoare absoluta**, cu etichete explicite "Discount unitar cu TVA" / "Discount unitar in valuta fara TVA". In `frm_facturare_articole` (forma standard) aceste coloane sunt read-only in grid (afisare, nu editare directa pe linie); in `frm_facturare_articole2` (forma "noua", optionala) sunt editabile si exista in plus o coloana de **procent pe linie** ("Procent discount", legata de campul `procdisc`). **Dovezi**: - `frm_facturare_articole`: `Column5.ControlSource = "discountctva"`, `Column5.Name = "cDiscountCTva"`, `Column5.ReadOnly = .T.` si `Column9.ControlSource = "vdiscountftva"`, `Column9.Name = "cVdiscountftva"` (fara `ReadOnly`, deci editabil implicit) — `D:\ROA\ROAFACTURARE\COMUN\clase\ofacturare.vc2:12311-12317, 12340-12345`. Header-e: `Caption = "Discount unitar cu TVA"` (`:12409`), `Caption = "Discount unitar in valuta fara TVA"` (`:12546`). - `frm_facturare_articole2`: `Column5.Name = "cDiscountCTva", Column5.ReadOnly = .F.` (`:16656-16657`), `Column9.Name = "cVdiscountftva", Column9.ReadOnly = .F.` (`:16687-16688`), plus `Column14.ControlSource = "procdisc"`, `Column14.Name = "cProcentDiscount"`, `Column14.Format = "RK"`, `Column14.InputMask = "99 999.99"`, `Column14.ReadOnly = .F.` (`:16720-16727`), header `Caption = "Procent discount"` (`:16934-16940`). - Vizibilitate conditionata: nu de `poDate.tip` direct, ci de `poDate.in_valuta` — `If poDate.in_valuta = 0 ... RemoveObject([cVdiscountftva]) ... Else ... RemoveObject([cDiscountctva])` — `ofacturare.vc2:15269-15278` (pattern analog si la `:19065` pentru `frm_facturare_articole2`). - `frm_facturare_articole2` e optionala, activata prin `gnFacturareNou = 1` cu un dialog Da/Nu ("Facturare noua (DA) sau standard (NU)?") — `COMUN\programe\ofacturare.prg:87-93`, instantiata la `:929` (`lcObject = [frm_facturare_articole2]`). ## 3. Calculul + `discount_evidentiat` **Concluzie**: `DISCOUNT_UNITAR` se scade direct din pretul unitar **fara TVA**, in valuta documentului, inainte de a se aplica TVA-ul, apoi se inmulteste cu cantitatea. Flagul `DISCOUNT_EVIDENTIAT` schimba doar mecanismul aritmetic (scade discountul din valoarea deja calculata vs. din pretul unitar rotunjit), nu semantica — discountul ramane o valoare absoluta pe unitate in ambele ramuri. In VFP, checkbox-ul corespunzator e etichetat "Se pune in evidenta discount-ul pe articole in notele contabile si pe factura" — adica discountul e afisat separat pe document/nota contabila vs. absorbit tacit in pret. **Dovezi** (`FUNCTION calculeaza_total_fara_tva_fact`, `D:\ROA\DATABASE\SCRIPTURI_CLAR\2026\03\ff_2026_03_23_04_COMUN_PACK_FACTURARE.sql:15794-15847`): ``` IF V_DISCOUNT_EVIDENTIAT = 1 THEN V_SUMA_FARA_TVA := ROUND((ROUND(curs*PRET,...) - DIFERENTA)*CANTITATE,...) - ROUND(ROUND(curs*NVL(DISCOUNT_UNITAR,0),...)*CANTITATE,...) ELSE V_SUMA_FARA_TVA := ROUND((ROUND(curs*ROUND(PRET,...),...) - ROUND(curs*ROUND(NVL(DISCOUNT_UNITAR,0),...),...) - DIFERENTA)*CANTITATE,...) ``` Aceeasi structura simetrica in `calculeaza_total_tva_fact` (`:15899-15944`). In VFP, sinteza corespunzatoare: `valdiminuatftva WITH poArticol.pretftva - NVL(poArticol.discount_unitar,0)` — `ofacturare.vc2:13126`, conversia cu-TVA: `discount_unitar_ctva = discount_unitar*(proc_tvav-1) + discount_unitar` — `:13635-13636`. Checkbox: `ADD OBJECT 'ck_discountevidentiat' AS _checkbox WITH ... Caption = "Se pune in evidenta discount-ul pe articole in notele contabile si pe factura", ControlSource = "poDate.discount_evidentiat"` — `:11300-11305`. ## 4. Oracle — parametrii `adauga_articol_factura` **Concluzie**: procedura primeste discountul ca parametru numeric absolut `V_DISCOUNT_UNITAR IN NUMBER` si il scrie direct in `VANZARI_DETALII_TEMP.DISCOUNT_UNITAR`, fara nicio transformare procent->valoare. Discountul de document (`VANZARI.discount`) e separat, aplicat/gestionat la alt nivel (agregare pe factura, cf. `do_calculeaza_discount` in VFP). **Dovezi**: semnatura completa `PROCEDURE adauga_articol_factura(V_ID_TEMP IN NUMBER, ... V_CANTITATE IN NUMBER, V_DISCOUNT_UNITAR IN NUMBER, V_CONT IN VARCHAR2, ...)` — `D:\ROA\DATABASE\SCRIPTURI_CLAR\2026\03\ff_2026_03_23_04_COMUN_PACK_FACTURARE.sql:4972-4998`, parametrul `V_DISCOUNT_UNITAR` la linia `4986`; `INSERT INTO VANZARI_DETALII_TEMP (... DISCOUNT_UNITAR ...) VALUES (... V_DISCOUNT_UNITAR ...)` — `:5219, 5249`. ## 5. Discount unitar in valoare absoluta — exista deja in suita **Concluzie**: Da, exista deja in toata suita ROA — nu doar "conceptual", ci implementat si cablat de la Oracle pana la grid. `COMUN\clase\ofacturare.vc2` (fisierul verificat pentru ROAFACTURARE) e literalmente acelasi fisier partajat cu `D:\ROA\ROAGEST\COMUN\clase\ofacturare.vc2` si `D:\ROA\ROAACNPRO\COMUN\clase\ofacturare.vc2` (confirmat prin grep pe ambele arbore), la fel `pack_facturare`. Nu a fost nevoie de o cautare separata in alt produs — e literalmente acelasi cod, aceeasi coloana. **Dovezi**: `discount_unitar`/`discountunitar` apare identic in `D:\ROA\ROAGEST\COMUN\clase\ofacturare.vc2`, `D:\ROA\ROAGEST\COMUN\clase\ofacturare_comun.vc2`, `D:\ROA\ROAGEST\COMUN\programe\ofacturare*.prg`, `D:\ROA\ROAACNPRO\COMUN\clase\ofacturare.vc2` si `D:\ROA\ROAACNPRO\COMUN\clase\ofacturare_comun.vc2`; SQL-uri de discount identice (ex. `v.discount as disc_fara_tva`) gasite si in `D:\ROA\DATABASE\SCRIPTURI_CLAR\2021\02\ff_2021_02_03_01_VANZARI.sql:19-20,259-260,409-410, 481-482,612`. ## 6. Ce ar presupune un discount unitar in valoare absoluta — inventar (nu solutie, doar puncte de atins) - **Coloana tabela**: deja exista (`VANZARI_DETALII.DISCOUNT_UNITAR`, `NUMBER(22,6)`, plus pe `VANZARI_DETALII_TEMP` si `CRM_POLITICI_PRET_ART`) — nimic de adaugat. - **Parametru Oracle**: deja exista (`adauga_articol_factura(... V_DISCOUNT_UNITAR ...)`, `ff_2026_03_23_04_COMUN_PACK_FACTURARE.sql:4986`) — nimic de adaugat. - **Coloana grid**: deja exista in ambele forme (`cDiscountCTva`/`cVdiscountftva`); in `frm_facturare_articole` (forma standard, majoritara) e read-only — de decis daca se face editabila pe linie sau ramane doar afisaj derivat din politica de pret / discountul procentual de pe factura. - **Intrare pentru operator**: in forma standard nu s-a gasit un punct unde operatorul tasteaza manual `discount_unitar` per linie la adaugarea articolului — pare alimentat din `CRM_POLITICI_PRET_ART.DISCOUNT_UNITAR` (politica de pret a clientului) sau din redistribuirea discountului procentual de pe factura (`do_calculeaza_discount`, `ofacturare.vc2:13405-13424`). De clarificat fluxul exact inainte de a proiecta un input nou. - **Recalcul**: formulele Oracle (`calculeaza_total_fara_tva_fact`/`calculeaza_total_tva_fact`) deja trateaza `DISCOUNT_UNITAR` ca valoare absoluta — nimic de schimbat aritmetic daca se reutilizeaza calea existenta. - **Rapoarte `.frx`**: nu s-a verificat daca discountul unitar apare pe rapoartele tiparite de factura — necunoscut, de verificat separat. - **eFactura / SAF-T**: nu s-a verificat daca `discount_unitar` e mapat in XML-ul UBL/eFactura sau in declaratia SAF-T — necunoscut, de verificat separat (fisierele `COMUN_EFACTURA*.sql` / `COMUN_SAFT*.sql` contin "discount" dar nu au fost citite). ## Raspuns scurt la intrebare Nu doar procentual: **discountul pe articol exista deja si ca valoare absoluta pe unitate** (`DISCOUNT_UNITAR`, `NUMBER(22,6)`), implementat capat la capat — coloana Oracle pe `VANZARI_DETALII`/`VANZARI_DETALII_TEMP`, parametru in `pack_facturare.adauga_articol_factura`, formule de calcul care scad direct din pret, si coloane de grid in VFP cu eticheta explicita "Discount unitar cu TVA"/"...in valuta fara TVA". Discountul de document (`VANZARI.discount`) ramane procentual-la-origine (tastat ca procent, stocat ca valoare calculata). Ce nu e clar e daca operatorul poate tasta liber discountul unitar pe linie in forma standard (`frm_facturare_articole`, unde coloana e read-only) — in forma "noua" optionala (`frm_facturare_articole2`, `gnFacturareNou=1`) e editabila si are si un procent-pe-linie separat. ## Necunoscute ramase - Sursa exacta a valorii `discount_unitar` la adaugarea unui articol in forma standard (politica de pret vs. redistribuire din discountul procentual de pe factura) — nu s-a urmarit tot lantul `do_adauga`/`crsgestarticol`. - Daca `discount_unitar` apare pe rapoartele `.frx` tiparite. - Daca `discount_unitar` e transmis in eFactura (UBL) sau SAF-T. - Cat de folosita e efectiv `frm_facturare_articole2` in productie (e optionala, per sesiune, cu prompt).