IMPMER - Criticità e problemi rilevati¶
Analisi critica del programma di importazione/esportazione merci¶
🔴 Criticità ALTE (rischio elevato)¶
1. Concorrenza: Nomi file temporanei fissi¶
Location: Righe 1648-1666
Problema:
string ext-tmp-dir delimited " "
ext-os-slash "impmer.txt"
delimited size into w-ris-name
string ext-tmp-dir delimited " "
ext-os-slash "import." tm-file-ext
delimited size into w-seq-name
I file temporanei hanno nomi fissi senza identificativo univoco:
- impmer.txt (log risultati)
- import.{ext} (file import temporaneo)
- merci.csv (file export) - Riga 9360
Impatto: - ❌ Due utenti che eseguono contemporaneamente il programma si sovrascrivono i file - ❌ Possibile corruzione dati o perdita di log - ❌ Race condition su sistemi multi-utente
Soluzione suggerita:
*> Aggiungere timestamp o PID al nome file
accept ws-timestamp from time
string ext-tmp-dir delimited " "
ext-os-slash "impmer-" ws-timestamp ".txt"
delimited size into w-ris-name
2. Buffer overflow: Mancanza controlli lunghezza record¶
Location: Righe 9394-9462
Problema:
move spaces to c-record
move 1 to c-pnt
*> ... costruzione record senza controllo overflow
move c-valore (1:c-siz) to c-record (c-pnt:c-siz)
add c-siz to c-pnt
Mancanza:
- ❌ Nessun controllo che c-pnt + c-siz < k-len-record (8000)
- ❌ Se la somma dei campi supera 8000, buffer overflow silenzioso
- ❌ Possibile corruzione memoria o crash
Impatto: - Esportazioni con molti campi lunghi possono causare errori - Troncamento dati non segnalato
Soluzione suggerita:
if c-pnt + c-siz > k-len-record
move "S" to tm-errori
string "Record troppo lungo alla riga " tm-r-l
delimited size into ris-rec
write ris-rec
go to c-10-loop
end-if
3. Inconsistenza ubicazioni: Logica di cancellazione parziale¶
Location: Righe 6953-7026, Righe 7031-7104
Problema:
when k-mer-ubi1-piano
*> ... aggiornamento piano ...
if lgm-posizione = spaces
perform del-coglgmer *> Cancellazione solo qui!
end-if
La cancellazione dell'ubicazione vuota avviene solo quando si aggiorna il campo PIANO (ultimo campo).
Scenario problematico:
1. File Excel aggiorna solo MER-UBI1-BOX = vuoto
2. Non viene eseguito il check lgm-posizione = spaces
3. Record ubicazione rimane con campi parziali inconsistenti
Impatto: - ❌ Ubicazioni parzialmente svuotate rimangono nel database - ❌ Dati inconsistenti (es. solo corsia/colonna senza box) - ❌ Query su ubicazioni possono restituire risultati errati
Soluzione suggerita: Aggiungere il controllo di cancellazione in tutti i campi separati, non solo nell'ultimo.
4. Assenza gestione transazionale¶
Location: Tutto il programma
Problema:
*> Nessun START TRANSACTION
perform b3-aggiorna *> Aggiorna record
*> Nessun COMMIT/ROLLBACK
Mancanza:
- ❌ Nessuna gestione transazioni esplicita
- ❌ Se l'import si interrompe a metà, database in stato inconsistente
- ❌ Solo 2 unlock all alle righe 9195, 9203 (insufficienti)
Impatto: - Import di 10.000 righe si interrompe alla 5.000 - Le prime 5.000 rimangono salvate → database semi-aggiornato - Impossibile fare rollback
Soluzione suggerita: Implementare gestione transazionale con commit periodici (es. ogni 100 righe) e rollback in caso di errori critici.
🟠 Criticità MEDIE (rischio moderato)¶
5. Limiti hardcoded insufficienti¶
Location: Righe 67-69
Problema:
78 k-max-campi value 500.
78 k-len-record value 8000.
78 k-len-ris-rec value 256.
Limitazioni: - Max 500 campi nell'import (attualmente 121 dopo aggiunta campi COGMERA4, ma futuro?) - Max 8000 caratteri per riga CSV (insufficiente per record con molti campi lunghi) - Max 256 caratteri per messaggio di log (troppo corto per errori dettagliati)
Impatto: - ⚠️ Impossibile gestire file con più di 500 colonne - ⚠️ Troncamento messaggi di errore nel log
6. Catena IF lunga e fragile per validazione campi¶
Location: Righe 1998-2130
Problema:
if tc-inf (n-tc) <> k-mer-gru and
tc-inf (n-tc) <> k-mer-sot and
tc-inf (n-tc) <> k-mer-cod and
tc-inf (n-tc) <> k-mer-descr and
*> ... 117+ condizioni in AND ...
tc-inf (n-tc) <> k-mer-pua
move "S" to b1-campo-errato
end-if
Problemi: - ❌ 117+ condizioni in AND su singolo IF (difficilissimo da mantenere) - ❌ Se si aggiunge un nuovo campo, si deve ricordare di aggiornare questo IF - ❌ Errore umano facile: dimenticare un campo → campo valido rifiutato - ❌ Performance: O(n) per ogni campo di ogni riga
Impatto: - Manutenibilità pessima - Rischio alto di regressioni
Soluzione suggerita:
*> Usare tabella campi validi
set b1-campo-trovato to false
perform varying i-campo from 1 by 1
until i-campo > n-campi-validi or b1-campo-trovato
if tc-inf (n-tc) = tab-campi-validi (i-campo)
set b1-campo-trovato to true
end-if
end-perform
if not b1-campo-trovato
move "S" to b1-campo-errato
end-if
7. Dipendenza da programma esterno per Excel¶
Location: Righe 1699-1706
Problema:
if function lower-case(tm-file-ext) = "xls" or "xlsx"
call "ESTRXLS" using stringhe util-estrxls
cancel "ESTRXLS"
end-if
Criticità:
- ⚠️ Dipendenza forte da programma esterno ESTRXLS
- ⚠️ Se ESTRXLS fallisce, nessun controllo dello stato di ritorno
- ⚠️ Nessuna gestione errore se conversione fallisce
Impatto: - File Excel corrotto → conversione fallisce silenziosamente - Utente riceve errore generico "Archivio non aperto"
8. 251 GO TO nel programma¶
Location: Tutto il programma
Problema: Il programma contiene 251 istruzioni GO TO, rendendo il flusso molto difficile da seguire.
Esempi:
- Riga 1687: go to a-tm-file
- Riga 1788: go to b-10-loop
- Riga 2079: go to a4
Impatto: - ⚠️ Manutenibilità ridotta - ⚠️ Difficile debugging - ⚠️ Rischio di loop infiniti o flussi errati
Best practice: Preferire PERFORM strutturato
🟡 Criticità BASSE (miglioramenti consigliati)¶
9. Mancanza validazioni campi obbligatori¶
Location: Sezione b3-aggiorna
Problema: Non ci sono controlli espliciti per campi obbligatori come: - MER-GRU (gruppo) - MER-SOT (sottogruppo) - MER-COD (codice) - MER-DESCR (descrizione)
Impatto: - Possibile creazione merci incomplete - Errori scoperti solo in fase di utilizzo
10. Logging insufficiente¶
Location: File impmer.txt
Problema: - ⚠️ Log messaggi troncati a 256 caratteri - ⚠️ Nessun livello di log (INFO/WARNING/ERROR) - ⚠️ Timestamp mancante nei messaggi - ⚠️ Nessuna statistica finale (record OK/KO)
Impatto: - Difficile debug di problemi complessi - Log non analizzabili automaticamente
11. Performance: Lettura sequenziale completa per export¶
Location: Righe 9478-9540
Problema:
c-10-loop.
move "Leggi" to u16-ope
perform z-u16
*> Legge TUTTE le merci sequenzialmente
Criticità: - Esportazione di 100.000 articoli legge tutto l'archivio - Nessuna paginazione o batch processing - Filtri applicati dopo la lettura (non in query)
Impatto: - Performance scarse su archivi grandi - Memoria occupata per buffering
12. Assenza controllo versione formato file¶
Location: Nessuna
Problema: - ❌ Nessun controllo di versione nel formato import/export - ❌ Se cambia struttura file, vecchi file non riconoscibili - ❌ Nessun header con metadati (versione, data export, ecc.)
Impatto: - Import di file vecchi potrebbe causare errori silenti - Impossibile gestire retrocompatibilità
13. Thin client: Path hardcoded¶
Location: Righe 869-879
Problema:
if ext-thin-client = "S"
*> Sostituzioni path server/client hardcoded
move function lower-case(ext-server-path) to us-pub-target
move function lower-case(ext-client-path) to us-pub-source
end-if
Criticità: - Path client/server configurati altrove ma logica qui - Sostituzione stringhe fragile
14. Gestione ubicazioni: Formato stringa vs campi separati¶
Location: Sezione ubicazioni
Problema architetturale:
Supporto di due formati alternativi per ubicazioni:
1. Stringa unica: MER-UBICAZIONE = "A-12-05-03"
2. Campi separati: BOX, CORSIA, COLONNA, PIANO
Criticità: - ⚠️ Se file Excel mescola i due formati, comportamento indefinito - ⚠️ Nessun controllo di mutua esclusione - ⚠️ Documentazione insufficiente per l'utente
Scenario problematico:
MER-COD,MER-UBICAZIONE,MER-UBI1-BOX
00123,A-12-05-03,B
→ Cosa succede? Si sovrascrive o si aggiunge?
Soluzione: Validare che non vengano usati entrambi i formati per la stessa ubicazione.
📊 Riepilogo criticità¶
| Livello | Problema | Impatto | Priorità fix |
|---|---|---|---|
| 🔴 ALTA | Nomi file temporanei fissi | Concorrenza | ⭐⭐⭐⭐⭐ |
| 🔴 ALTA | Buffer overflow export | Sicurezza/Stabilità | ⭐⭐⭐⭐⭐ |
| 🔴 ALTA | Inconsistenza ubicazioni | Integrità dati | ⭐⭐⭐⭐ |
| 🔴 ALTA | Assenza transazioni | Integrità dati | ⭐⭐⭐⭐ |
| 🟠 MEDIA | Limiti hardcoded | Scalabilità | ⭐⭐⭐ |
| 🟠 MEDIA | Catena IF lunghissima | Manutenibilità | ⭐⭐⭐ |
| 🟠 MEDIA | Dipendenza ESTRXLS | Affidabilità | ⭐⭐⭐ |
| 🟠 MEDIA | 251 GO TO | Manutenibilità | ⭐⭐ |
| 🟡 BASSA | Validazioni insufficienti | Qualità dati | ⭐⭐ |
| 🟡 BASSA | Logging migliorabile | Supportabilità | ⭐⭐ |
| 🟡 BASSA | Performance export | Performance | ⭐ |
| 🟡 BASSA | Versioning formato | Evoluzione | ⭐ |
🛠️ Raccomandazioni prioritarie¶
Immediato (settimane)¶
- Fix nomi file temporanei: Aggiungere PID/timestamp
- Aggiungere controlli buffer overflow: Validare c-pnt prima di scrivere
- Fix logica cancellazione ubicazioni: Estendere a tutti i campi
Breve termine (mesi)¶
- Implementare gestione transazionale: Commit batch + rollback
- Aumentare limiti: k-len-record a 16000, k-len-ris-rec a 1024
- Refactoring validazione campi: Usare tabella invece di IF gigante
Medio termine (trimestri)¶
- Ridurre GO TO: Ristrutturare flusso con PERFORM
- Aggiungere validazioni business: Campi obbligatori, vincoli
- Migliorare logging: Livelli, timestamp, statistiche
Lungo termine (anni)¶
- Ottimizzare performance export: Query con filtri, paginazione
- Aggiungere versioning formato: Header file con metadati
- Documentazione utente: Guida completa formato file
🧪 Suggerimenti per testing¶
Test di concorrenza¶
# Lanciare 5 importazioni simultanee
for i in {1..5}; do
impmer input$i.xlsx &
done
wait
# Verificare che non ci siano corruzioni
Test limiti¶
# Creare file con 600 colonne (> k-max-campi)
# Creare riga CSV > 8000 caratteri
# Verificare gestione errore
Test rollback¶
# Import con 1000 righe, interrompere a metà
# Verificare stato database
# Dovrebbero esserci solo le prime N righe
📝 Note finali¶
Nonostante le criticità evidenziate, il programma IMPMER: - ✅ Funziona correttamente per casi d'uso standard - ✅ Ha una copertura funzionale molto ampia (117 campi) - ✅ Gestisce situazioni complesse (thin client, consorzi, ecc.)
Le criticità sono principalmente legate a: - Scenari limite (concorrenza, file molto grandi) - Robustezza e recovery da errori - Manutenibilità del codice
Un programma di refactoring graduale può risolvere le criticità più gravi mantenendo la compatibilità con gli usi esistenti.
Casistica problemi noti¶
Descrizioni aggiuntive con "a capo"¶
- Sintomo: In esportazione, se le descrizioni aggiuntive contengono caratteri di "a capo", la riga di esportazione risulta malformata. In alcuni ambienti il processo termina silenziosamente per timeout del runtime.
- Causa: IMPMER e GESSTR00 non sanificavano i newline nelle descrizioni aggiuntive. Il carattere spezzava la riga del tracciato di output. Nei clienti con molti articoli, l'elaborazione superava il timeout del thin client.
- Correzione: Sanificazione dei newline prima dell'esportazione in IMPMER e GESSTR00. Aggiunta C$SLEEP ogni 10 record per prevenire il timeout.
- Riferimento: dettaglio — ClickUp 8697w9zgp