Files
roafacturare/docs/cercetare/idfact_refolosire_si_documente.md
Marius Mutu d9f5ca4226 docs: planurile, proiectarile si rapoartele de lucru intra in versionare
Folderul docs\ era pana acum in afara oricarui control de versiuni - nici git,
nici SVN - desi contine planurile pe puncte, proiectarile si rapoartele de
cercetare pe care se sprijina modificarile din cod. O stergere acolo era
definitiva.

Fisierele intermediare (handoff-uri intre sesiuni, diff-uri deja aplicate) au
fost sterse inainte, nu versionate: ce era durabil in ele a intrat in antetele
fisierelor de test la care se refereau.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01SN8snvkk94KuhWwoXUUey3
2026-08-11 22:17:17 +03:00

338 lines
20 KiB
Markdown

Cercetare S9: reemiterea unui document cu acelasi ID_FACT (SET_IDFACT + DOCUMENTE)
====================================================================================
Verdict (rezumat)
------------------
**DA, dar cu conditii — nu e o schimbare izolata.** `SET_IDFACT` activ (`PACK_CONTAFIN.pck:3037-3040`)
ia neconditionat un `ID_FACT` nou din `SEQ_IdFact`; niciun apelant din toata suita (~25-30 copii
identice ale `oscrie_in_fisiere.prg`, cate una per produs) ii impune un `ID_FACT`. Varianta comentata
(`:3016-3035`, cauta pe `NRACT+SERIE_ACT+DATAACT+ID_CTR` cu `STERS=0`) **nu rezolva S9** ca atare:
dupa stergerea soft a documentului vechi, `STERS` e deja 1, cautarea nu-l gaseste, si cade tot pe
secventa — plus riscul de coliziune cu un document viitor neinrudit care are aceleasi 4 campuri.
Blocajul real nu e in `SET_IDFACT`, ci in scrierea din `DOCUMENTE`: acolo e un `INSERT` simplu
(`:796-817`) pe `ID_DOC`, care e **PRIMARY KEY** (`PK_DOCUMENTE`, unic, `fn_script.sql:5192-5198`).
Stergerea (`STERGE_DIN_ACT:1835-1855`) e soft-delete pur — `ACT.STERS=1`, apoi `DOCUMENTE.STERS=1`
pentru id_fact-urile gasite pe acel `COD` — randul vechi **nu se sterge fizic**. Deci reemiterea cu
acelasi `ID_FACT`, cu codul de azi neschimbat, ar arunca `ORA-00001` la insertul in `DOCUMENTE`,
pentru ca randul cu acel `ID_DOC` inca exista (doar marcat `STERS=1`). Varianta `MERGE` deja
comentata (`:818-847`) nu ajuta din prima: are doar `WHEN NOT MATCHED`, fara `WHEN MATCHED`, deci
daca randul exista deja l-ar ignora tacit — documentul reemis ar ramane cu `DOCUMENTE.STERS=1`.
Concluzie operationala: reutilizarea e posibila, dar cere trei schimbari simultane (detaliate la C.7),
nu doar reactivarea codului comentat din `SET_IDFACT`.
A. SET_IDFACT
--------------
### A.1 — Ramura activa vs. ramura comentata
Cod integral, `PACK_CONTAFIN.pck:3014-3040`:
```
------------------------------------------------------------------------------------
/* -- 25.02.2013 : am comentat pentru ca se face unirea id_fact pe listarea din JC/JV
PROCEDURE SET_IDFACT(tdDataAct ACT_TEMP.DATAACT%TYPE,
tcSerie_Act ACT_TEMP.SERIE_ACT%TYPE,
tnNrAct ACT_TEMP.NRACT%TYPE,
tnId_Ctr ACT_TEMP.ID_CTR%TYPE) IS
V_ID_FACT DOCUMENTE.ID_DOC%TYPE;
BEGIN
BEGIN
SELECT ID_DOC
into pack_contafin.nIdFact
FROM DOCUMENTE
WHERE NRACT = tnNrAct
AND NVL(SERIE_ACT, '+-') = NVL(tcSerie_Act, '+-')
AND DATAACT = tdDataAct
AND NVL(ID_CTR, 0) = NVL(tnId_Ctr, 0)
AND STERS = 0;
EXCEPTION
WHEN NO_DATA_FOUND THEN
SELECT SEQ_IdFact.NEXTVAL into pack_contafin.nIdFact FROM DUAL;
END;
END SET_IDFACT;*/
------------------------------------------------------------------------------------
PROCEDURE SET_IDFACT(V_GCS IN VARCHAR2) IS
BEGIN
SELECT SEQ_IdFact.NEXTVAL into pack_contafin.nIdFact FROM DUAL;
END SET_IDFACT;
```
Diferenta de comportament daca s-ar reactiva varianta comentata: in loc sa genereze mereu un
`ID_FACT` nou, ar cauta intai in `DOCUMENTE` un document **nesters** (`STERS=0`) cu aceeasi
combinatie `NRACT + SERIE_ACT + DATAACT + ID_CTR`, si doar daca nu gaseste nimic ar cere secventa.
Doua probleme pentru S9:
- **nu se aplica la reemitere**: documentul vechi e deja marcat `STERS=1` inainte de rescriere
(vezi B.6), asa ca filtrul `STERS=0` nu-l gaseste — cade tot pe `SEQ_IdFact.NEXTVAL`, exact ca azi;
- **risc de coliziune**: daca NRACT/SERIE_ACT/DATAACT/ID_CTR ar coincide intamplator cu alt document
nesters (nu neaparat cel pe care il reemitem), i-ar imprumuta ID_FACT-ul aceluia.
Semnatura veche are 4 parametri de identitate diferiti de semnatura activa (1 parametru `V_GCS`,
folosit doar ca "user"/context, nefolosit in corp) — deci reactivarea ar cere fie o supraincarcare,
fie schimbarea semnaturii peste tot unde e chemata (vezi A.2).
### A.2 — Apelanti
**Un singur punct de apel in PL/SQL**: `PACK_CONTAFIN.pck:721`, in bucla din `SCRIE_IN_ACT`:
```
pack_contafin.set_idfact(V_GCS);
/* 25.02.2013 : se face cumularea id_fact pe listarea din RC/RJ
PACK_CONTAFIN.SET_IDFACT(itemfact.dataact, itemfact.serie_act, itemfact.nract, itemfact.id_ctr);*/
lnIdFact := get_idFact();
```
buclat pe grupuri distincte `(NRACT, DATAACT, DATAIREG, SERIE_ACT, ID_CTR, ID_SET)` extrase din
`ACT_TEMP WHERE ID_FACT = -1` (`:713`) — deci `-1` e sentinela "acest rand cere un `ID_FACT` nou".
`SCRIE_IN_ACT` insusi e apelat **doar pe drumul de scriere**, niciodata pe cel de stergere —
in `finalizeaza_scriere_act_rul` (`:8449-8459`):
```
if tnScrieSterge <> 2 then
pack_contafin.SCRIE_IN_ACT(user);
...
else
pack_contafin.STERGE_DIN_ACT(user, lnAn, lnLuna, tnCod, tnIdUtil, tnModificareNota);
...
```
Deci `SET_IDFACT` nu se atinge deloc la stergere — confirma ca azi cele doua operatii (stergere +
reemitere) sunt independente unele de altele in privinta ID_FACT.
**Cine cheama `final_scriere_act_rul_local` / `SCRIE_IN_ACT` din VFP**: acelasi fisier
`COMUN\programe\oscrie_in_fisiere.prg`, replicat identic in ~25-30 produse ROA (verificat prin grep
pe `*.prg` in tot `D:\ROA`): `ROAFACTURARE`, `ROACONT` (output), `ROAGEST`, `ROAIMOB`, `ROAEFACTURA`,
`ROADEVIZE`, `ROAVIN`, `ROACASA`, `ROASAL`, `ROAPRETURI`, `ROAOBINV`, `ROARESTAURANT`,
`ROACOMENZI`, `ROAAPROV`, `ROASITOP`, `ROASITFIN`, `ROADECL`, `ROASALSPEC`, `ROABAVERT`,
`ROACONIMPORT`, `ROAPRINT`, s.a. — plus doua variante care apeleaza `SCRIE_IN_ACT` direct, fara
wrapper-ul local: `CONTAFIN2ORA\VFP2ORA\Programe\oscrie_in_fisiere.prg:367`,
`ROADEFSALARII\COMUN\programe\oscrie_in_fisiere.prg:141`,
`ROARESTAURANTCONFIG\COMUN_ROA\programe\oscrie_in_fisiere.prg:135`.
Un al doilea import vechi (`COMUN\datemenu\xold\import_xdbf\oscrie_in_fisiere.prg`) apare in multe
produse dar e **comentat integral** (`*!*`) — inactiv.
**Niciun apelant nu impune un `ID_FACT`.** Toti trimit `ID_FACT = -1` in `ACT_TEMP` (via
`sql_temp_insert` in `oscrie_in_fisiere.prg:126-137`, care copiaza direct campurile din cursorul VFP,
inclusiv `id_fact`) si lasa `SCRIE_IN_ACT` sa-l completeze din secventa. Confirmare suplimentara in
`COMUN\clase\omodificari.vc2:4131-4132`: `"daca se schimba partenerul, se pune id_fact = -1 in loc
de 0 pentru a se putea genera un nou id_fact"` — exact sentinela pe care se bazeaza bucla din
`SCRIE_IN_ACT`.
### A.3 — Variabila/parametru existent pentru un ID_FACT dorit
**Nu exista azi.** `PACK_CONTAFIN` are o variabila de pachet `nIdFact` (setata de `SET_IDFACT`,
citita de `GET_IDFACT`), dar e scrisa neconditionat de fiecare apel al lui `SET_IDFACT` — nu poate
fi folosita ca "intrare" fara sa se schimbe corpul procedurii. Nu exista niciun `nid_...` global, nici
alt parametru de sesiune care sa transmita un `ID_FACT` dorit lui `SET_IDFACT` sau lui `SCRIE_IN_ACT`.
Ar trebui adaugata o variabila noua de pachet (ex. un "ID_FACT fortat", implicit `NULL`), citita
**doar** in corpul activ al lui `SET_IDFACT`, consumata si resetata la prima folosire — vezi C.8.
Acelasi diagnostic e deja notat in planul de proiect, `plan_13_unificare_formular_facturare.md:1717-1719`:
`"ID_FACT. Se citeste inainte de stergere ... si se impune documentului nou, printr-un comutator
folosit numai de regenerare. SET_IDFACT nu se schimba neconditionat — e cod comun intregii suite."`
B. DOCUMENTE la reemitere cu acelasi ID_FACT
----------------------------------------------
### B.4 — INSERT sau UPDATE/MERGE azi
`PACK_CONTAFIN.pck:788-817`, in interiorul buclei din `SCRIE_IN_ACT`, cod activ (INSERT simplu):
```
-- SCRIE IN DOCUMENTE
lnTvaIncasare := case when itemfact.tva_incasare > 0 then 1 else 0 end;
-- 25.02.2013 : am repus insertul pentru ca se face cumularea id_fact pe listarea din RC/RJ
INSERT INTO DOCUMENTE
(ID_DOC, ID_UTIL, DATAORA, TVA_INCASARE, SERIE_ACT, NRACT, DATAACT, DATAIREG, ID_CTR, ID_SET)
VALUES
(lnIdFact, lnID_Util, LD_DATAORA, lnTvaIncasare, itemfact.serie_act, itemfact.nract,
itemfact.dataact, itemfact.dataireg, decode(itemfact.id_ctr, 0, NULL, itemfact.id_ctr),
itemfact.id_set);
/*
-- modificare ROACONT v 2.4.0 (27.12.2012): am adaugat serie_act, nract, dataact
-- modificare 21.02.2013: am adaugat id_ctr
MERGE INTO DOCUMENTE A
USING (SELECT lnIdFact as ID_DOC, itemfact.serie_act as SERIE_ACT, itemfact.nract as NRACT,
itemfact.dataact as DATAACT,
decode(itemfact.id_ctr, 0, NULL, itemfact.id_ctr) AS ID_CTR
FROM DUAL) B
ON (A.ID_DOC = B.ID_DOC)
WHEN NOT MATCHED THEN
INSERT (ID_DOC, ID_UTIL, DATAORA, TVA_INCASARE, SERIE_ACT, NRACT, DATAACT, ID_CTR)
VALUES (B.ID_DOC, lnID_Util, LD_DATAORA, lnTvaIncasare, B.SERIE_ACT, B.NRACT, B.DATAACT, B.ID_CTR);*/
```
Deci **azi e mereu un INSERT nou** — pe drumul normal (ID_FACT vine din secventa, mereu inexistent
in `DOCUMENTE`) asta e corect, dar pentru cazul S9 (ID_FACT reutilizat, deja existent — chiar si
soft-sters) INSERT-ul ar da eroare de unicitate (vezi B.5). Varianta `MERGE` comentata are doar
`WHEN NOT MATCHED` — daca s-ar reactiva neschimbata, un `ID_DOC` deja existent ar fi pur si simplu
ignorat (fara `WHEN MATCHED`), documentul reemis ramanand cu randul vechi din `DOCUMENTE`
(cu `TVA_INCASARE`/`ID_SET` nemodificate si, mai grav, cu `STERS` neresetat — vezi B.6).
### B.5 — Constrangere de unicitate pe DOCUMENTE
DDL gasit in `D:\ROA\DATABASE\ALTELE\Creare_server_scripturi\FirmaNoua\fn_script.sql:5162-5198`:
```
CREATE TABLE "DOCUMENTE" ("ID_DOC" NUMBER(20, 0) NOT NULL ENABLE, "DATAORA" DATE NOT NULL ENABLE,
"ID_UTIL" NUMBER(5, 0) NOT NULL ENABLE, "STERS" NUMBER(1, 0) NOT NULL ENABLE,
"DATAORAS" DATE, "ID_UTILS" NUMBER(5, 0) NOT NULL ENABLE) ...
...
CREATE UNIQUE INDEX "PK_DOCUMENTE" ON "DOCUMENTE" ("ID_DOC") ...
ALTER TABLE "DOCUMENTE" ADD CONSTRAINT "PK_DOCUMENTE" PRIMARY KEY ("ID_DOC") USING INDEX ... ENABLE
```
**Da: `ID_DOC` e PRIMARY KEY, unic.** (Coloanele `SERIE_ACT/NRACT/DATAACT/DATAIREG/ID_CTR/ID_SET/
TVA_INCASARE` din INSERT-ul de la B.4 nu apar in acest script — script vechi de firma noua,
probabil tabela a fost alterata ulterior cu `ALTER TABLE ADD COLUMN`; constrangerea de PK insa e
stabila si nu are motiv sa fi fost scoasa.) Un `INSERT INTO DOCUMENTE (ID_DOC=...)` cu o valoare de
`ID_DOC` care exista deja (chiar si `STERS=1`) arunca `ORA-00001: unique constraint (PK_DOCUMENTE)
violated`. Nu am gasit alta constrangere de unicitate pe `DOCUMENTE`; nici FK de la `ACT.ID_FACT`
catre `DOCUMENTE.ID_DOC` (`ACT.ID_FACT` e doar indexat, `IDX_ID_FACT`, `fn_script.sql:1637`, fara
constrangere de integritate referentiala gasita) — deci reinserarea de randuri in `ACT` cu
`ID_FACT` reutilizat **nu** e blocata de vreo constrangere pe `ACT` insusi; blocajul e exclusiv pe
`DOCUMENTE`.
### B.6 — Randurile vechi la stergere: fizic sterse, STERS=1, sau raman
**Soft-delete pur, pe toate cele patru tabele relevante — nimic nu se sterge fizic.**
`STERGE_DIN_ACT` (`PACK_CONTAFIN.pck:1815-1859`), apelata din `finalizeaza_scriere_act_rul` cand
`tnScrieSterge = 2`:
```
PROCEDURE STERGE_DIN_ACT(V_GCS VARCHAR2, tnAn in number, tnLuna in number, tnCod in number,
tnId_utils in number, tnTip IN NUMBER) is
-- tnTip : 0 = modificare ; 1 = stergere
...
BEGIN
...
UPDATE /*+ index(ACT IDX_COD) */ ACT
SET STERS = 1, DATAORAS = LD_DATAORA, ID_UTILS = lnId_util
WHERE COD = tnCod and an = tnAn and luna = tnLuna;
IF lnTip = 1 THEN
UPDATE DOCUMENTE
SET STERS = 1, ID_UTILS = LNID_UTIL, DATAORAS = LD_DATAORA
WHERE ID_DOC IN
(SELECT /*+ index(ACT IDX_COD) */ DISTINCT ID_FACT
FROM ACT
WHERE COD = tnCod and an = tnAn and luna = tnLuna
AND ID_FACT <> 0
and ID_SET not in (90501, 90021)
AND NOT (SCD = '4426' AND SCC = '4428')
AND NOT (SCD = '4428' AND SCC = '4427'));
END IF;
update act_temp set suma = -suma, suma_val = -suma_val;
END STERGE_DIN_ACT;
```
`ACT` -> `STERS=1` (randurile raman fizic, pe acelasi `COD`). Cand `tnTip=1` (stergere, nu simpla
modificare), **`DOCUMENTE` primeste si el `STERS=1`**, pentru toate `ID_FACT` distincte gasite pe
acel `COD` in `ACT` (cu exceptiile de mai sus pentru seturi/conturi speciale). Nicaieri nu am gasit
un `UPDATE DOCUMENTE ... SET STERS = 0` — cautare exhaustiva in `PACK_CONTAFIN.pck` (`grep -i
"UPDATE DOCUMENTE"`) a dat un singur rezultat, cel de mai sus. Deci nu exista azi niciun mecanism
care sa "reinvie" un rand din `DOCUMENTE`.
La fel, `STERGE_DIN_RUL` / `STERGE_DIN_RUL_OBINV` (`:1861-1893`) fac `UPDATE ... SET STERS = 1` pe
`RUL`/`RUL_OBINV`, fara stergere fizica.
Pentru `IREG_PARTENERI` si `JV2007` situatia e diferita in mod util pentru S9: acestea nu sunt copii
1:1 ale documentului, ci **agregate recalculate prin `MERGE`** pe chei de business (an, luna, cont /
`ID_FDOC`, `ID_FACT`, `NRACT`, `SERIE_ACT`, `DATAACT`, `DATAIREG`, `ID_PART`, ...) — vezi
`SCRIE_JV_2007` (`:3328-3373+`) si `SCRIE_IN_IREG_PARTENERI`/`EXECUTA_SCRIE_IN_IREG` (`:7030+`,
`:7607+`). Ambele sunt apelate **si pe drumul de scriere, si pe cel de stergere**
(`finalizeaza_scriere_act_rul:8495-8578`, fara conditie pe `tnScrieSterge` in afara sursei: `act_temp`
la scriere/stergere, `act` la refacere). La stergere, `sterge_document` (`:7699-8118`) reinsereaza in
`ACT_TEMP` copii ale randurilor vechi din `ACT`/`RUL`/`RUL_OBINV`, **cu acelasi `ID_FACT` ca inainte**
(coloana `id_fact` e copiata direct din sursa, nu resetata la `-1`), asa ca `MERGE`-ul din
`SCRIE_JV_2007`/`SCRIE_IN_IREG_PARTENERI` recalculeaza (compenseaza) exact randul cu acel `ID_FACT`
— nu creeaza duplicate. Deci reutilizarea `ID_FACT`-ului **nu produce dubluri in `JV2007`/
`IREG_PARTENERI`**; problema e strict izolata la `DOCUMENTE`.
Nota din plan, care confirma independent aceasta zona de risc:
`plan_13_unificare_formular_facturare.md:1737`: `"De verificat si daca DOCUMENTE primeste un al
doilea rand pe acelasi ID_DOC sau il refoloseste."` — raspunsul, dupa aceasta cercetare: **niciuna
din cele doua, in starea actuala a codului — ar arunca eroare de unicitate**, nu ar produce liniste
tacuta cu duplicat sau refolosire.
C. Verdictul care conteaza
----------------------------
### C.7 — Se poate reemite cu acelasi ID_FACT fara sa se strice nimic?
**DA, dar cu conditii** — niciuna dintre ele nu e implementata azi:
1. **Nu folosi varianta comentata a lui `SET_IDFACT` ca atare.** Cautarea `STERS=0` nu gaseste
documentul (deja sters soft inainte de rescriere) si e vulnerabila la coliziuni pe chei de
business partajate cu alt document. In loc de cautare, ID_FACT-ul trebuie **citit explicit
inainte de stergere** (VFP il are deja in cursorul documentului editat) si **transmis** pe drumul
de scriere — exact ce zice planul S9.
2. **`SET_IDFACT` are nevoie de o cale de intrare noua, inerta implicit.** O variabila de pachet
noua (ex. "ID_FACT fortat", `NULL` default) + o procedura noua de setat-o explicit inainte de
scriere; corpul activ al `SET_IDFACT` verifica intai variabila, o consuma si o reseteaza; daca e
`NULL` (cazul general — toate celelalte ~25-30 apeluri din suita), comportamentul e identic cu
azi (secventa). Nu se toarna in semnatura existenta `SET_IDFACT(V_GCS)`, ca sa nu se schimbe
apelul de la niciun alt caller.
3. **Scrierea in `DOCUMENTE` trebuie sa devina un upsert real, cu `WHEN MATCHED`.** Nici INSERT-ul
activ, nici MERGE-ul comentat (fara `WHEN MATCHED`) nu revigoreaza un rand soft-sters. E nevoie de
un `MERGE ... WHEN MATCHED THEN UPDATE SET STERS = 0, DATAORA = ..., ID_UTIL = ..., TVA_INCASARE
= ..., SERIE_ACT = ..., NRACT = ..., DATAACT = ..., DATAIREG = ..., ID_CTR = ..., ID_SET = ...`
pe langa `WHEN NOT MATCHED THEN INSERT` (cazul normal, ID_FACT nou din secventa).
4. **Succesiunea corecta**, in aceeasi tranzactie (deja planificata in S9 la nivel de VFP — vezi
`plan_13...md:1713-1719`, mutarea stergerii in tranzactia deschisa de scriere): sterge documentul
vechi (soft-delete, ca azi) -> seteaza variabila de la punctul 2 cu `ID_FACT`-ul citit inainte de
stergere -> scrie documentul nou prin drumul obisnuit (`ACT_TEMP` cu `ID_FACT = -1` ca de obicei,
dar acum grupul respectiv va primi ID_FACT-ul fortat in loc de unul nou) -> commit doar dupa ce
ambele operatii au avut succes; orice eroare -> rollback total, documentul vechi ramane intact.
- **NU** (fara aceste conditii): `INSERT INTO DOCUMENTE` cu `ID_DOC` reutilizat, cat timp randul vechi
e inca prezent cu `STERS=1`, arunca `ORA-00001` pe `PK_DOCUMENTE` — asta e dovada, nu presupunere
(B.5 + B.4).
### C.8 — Suprafata de risc pentru restul suitei
- **~25-30 cai de apel** trebuie sa ramana neafectate: toate copiile `COMUN\programe\
oscrie_in_fisiere.prg` din fiecare produs ROA (listate in A.2), plus cele 3 variante care apeleaza
`SCRIE_IN_ACT` direct. Toate trec prin acelasi punct final: `SET_IDFACT(V_GCS)` in
`PACK_CONTAFIN.pck:3037`.
- **Garantia structurala propusa**: variabila de pachet noua, default `NULL`/inert, citita **doar**
in interiorul corpului activ al lui `SET_IDFACT` (nu in semnatura, nu in vreun parametru propagat
de apelanti); se seteaza explicit **doar** de codul de regenerare din ROAFACTURARE, chiar inainte
de a incepe scrierea documentului reemis, si se consuma/reseteaza la prima citire (fie in
`SET_IDFACT`, fie la finalul tranzactiei, ca sa nu "scurgi" valoarea catre urmatoarea scriere
neinrudita din aceeasi sesiune Oracle — relevant daca `goExecutor`/conexiunea e reutilizata intre
operatii ale aceluiasi utilizator in acelasi produs). Cu default inert si citire localizata strict
in corpul lui `SET_IDFACT`, toate celelalte ~25-30 cai raman byte-for-byte identice cu azi — nu e
nevoie sa se verifice fiecare apelant individual, garantia e la sursa (variabila neinitializata =
comportament vechi).
- **Riscul real nu e in `SET_IDFACT`, ci in `DOCUMENTE`.** Schimbarea INSERT->MERGE cu `WHEN MATCHED`
la `PACK_CONTAFIN.pck:796-817` e riscanta pentru toata suita in alt sens: `WHEN MATCHED` s-ar
declansa doar cand `ID_DOC` (generat din secventa) coincide cu unul existent — ceea ce, pe drumul
normal, nu se intampla niciodata (secventa e monoton crescatoare, nu se repeta), deci practic
ramura noua e inerta pentru toti apelantii actuali si activa doar cand variabila de la C.8 a fost
setata explicit. Totusi orice modificare la acest INSERT/MERGE e in cod comun apelat de toata
suita si trebuie testata pe cel putin un ciclu normal de scriere (fara variabila fortata) in
fiecare produs care scrie facturi/note, nu doar in ROAFACTURARE.
Ramas de verificat pe baza vie
--------------------------------
- Structura curenta reala a tabelei `DOCUMENTE` (DDL-ul citat e dintr-un script vechi de "firma
noua"; coloanele `SERIE_ACT/NRACT/DATAACT/DATAIREG/ID_CTR/ID_SET/TVA_INCASARE` folosite de
INSERT-ul activ nu apar in acel DDL — probabil adaugate ulterior prin `ALTER TABLE`). De rulat pe
baza vie: `SELECT column_name, nullable FROM user_tab_columns WHERE table_name = 'DOCUMENTE'
ORDER BY column_id;` si `SELECT constraint_name, constraint_type FROM user_constraints WHERE
table_name = 'DOCUMENTE';` — sa se confirme ca `PK_DOCUMENTE` e inca activa si ca nu exista alta
constrangere aparuta intre timp.
- Daca exista deja documente reale in productie unde `DOCUMENTE.ID_DOC` a fost, intr-un fel sau
altul, reutilizat (ex. printr-o interventie manuala) — de verificat cu
`SELECT id_doc, count(*) FROM documente GROUP BY id_doc HAVING count(*) > 1;` (ar trebui sa fie
gol, dat fiind PK-ul, dar merita confirmat inaintea oricarei schimbari).
- Comportamentul exact al `finalizeaza_stergere_nota`/`finalizeaza_modificare_nota` (`:8601+`,
nu au fost citate integral aici) fata de `ID_FACT`/`ID_FACTD` — relevante daca reemiterea schimba
seria/numarul, nu doar continutul (cazul S9 "de baza" e cel mai simplu: acelasi NRACT/SERIE_ACT).
- Comportamentul lui `EXECUTA_SCRIE_TVA`/`SCRIE_JC_2007` (mentionate la `:8504-8540`, cazul an <
2007 sau JC) fata de reutilizarea ID_FACT — nu au fost verificate in detaliu, doar `SCRIE_JV_2007`.
- Nu am putut testa efectiv (fara acces la baza vie) daca `ORA-00001` e chiar eroarea ridicata de
Oracle in acest scenariu exact — e o deductie directa din DDL (PK unic + INSERT simplu pe coloana
respectiva), dar merita o rulare de proba pe o baza de test inainte de a proiecta solutia finala.