- Salesforce Composite Batch API per describe SObject: le describe sono ora
raggruppate in chunk da 25 e inviate come singole POST a /composite/batch,
riducendo le chiamate API da N a ceil(N/25); per 200 SObject: da 201 a 9 chiamate.
- Discovery entita' REST in parallelo: DiscoverEntitySummariesAsync e
DiscoverEntitiesAsync avviate simultaneamente; la lista entita' diventa
interattiva subito dopo le summaries, i dettagli completano in background
con StateHasChanged() per aggiornare l'UI istantaneamente.
- Fix scheduler - preservazione ExternalIdRelationshipsJson e DefaultValuesJson:
in DataCoupler.razor.cs entrambi i blocchi di update profilo esistente
(riattivazione profilo inattivo e sovrascrittura profilo attivo) omettevano
questi campi nella copia, causandone l'azzeramento silenzioso ad ogni
re-salvataggio. Ora entrambi i percorsi propagano correttamente i campi JSON.
- Fix scheduler - esclusione campi sorgente External ID dal mapping normale:
in ScheduledProfileExecutionService.TransformRecordForRest i campi sorgente
usati nelle External ID Relationships venivano inclusi anche nel loop di
field mapping standard, generando dati duplicati nell'entita' destinazione.
Ora il comportamento e' allineato alla UI manuale (TransformRecordToRestEntity).
- Aggiornata documentazione: README.md, AGENTS.md, copilot-instructions.md
- Implementata funzionalità completa External ID Relationships nell'interfaccia di mapping
- Corretto bug double-mapping: i campi sorgente usati per External ID non vengono più inclusi nei mapping normali
- Risolto errore MALFORMED_ID causato dall'invio duplicato di campi come proprietà dirette e nested objects
- Implementata logica corretta per relationship names: oggetti standard usano il nome diretto, custom objects usano suffisso __r
- Aggiunta UI a 3 colonne (Object, External ID Field, Source Field) per configurazione External ID Relationships
- Migrazione database per supporto External ID Relationships nei profili
- Aggiornato ProfileSaver.razor.cs per salvare/caricare External ID Relationships
- Aggiornato ScheduledProfileExecutionService.cs per gestire External ID nelle esecuzioni schedulate
- Formato JSON output corretto: { 'Account': { 'CardCode__c': 'V50000' } }
Documentazione: EXTERNAL_ID_RELATIONSHIPS_IMPLEMENTATION.md
- Aggiunta validazione percorsi file prima del salvataggio profili
- Implementati metodi di lettura file CSV e Excel per schedulazioni
- Supporto doppia modalità: caricamento browser (preview) e percorso manuale (schedulazione)
- Gestione completa deletion sync anche per file CSV/Excel
- Rilevamento automatico separatori CSV (virgola, punto e virgola, tab, pipe)
- Supporto formati Excel legacy (.xls) e moderni (.xlsx)
- Abilitati profili file nella UI di schedulazione
- Logging dettagliato per troubleshooting
- Documentazione completa in CSV_SCHEDULING_IMPLEMENTATION.md
- Aggiornati README.md e copilot-instructions.md con nuove feature
- Rimosso testo 'TEST' dalla pagina di login
- Disabilitata completamente la sincronizzazione eliminazioni nei trasferimenti manuali (DataCoupler.razor.cs)
- Aggiunto campo EnableDeletionSync al modello ProfileSchedule (default: false)
- Implementata logica condizionale in ScheduledProfileExecutionService per deletion sync
- Aggiunta sezione 'Opzioni Avanzate' nell'interfaccia schedulazione con warning
- Creata migration Entity Framework AddEnableDeletionSyncToProfileSchedule
- Aggiornato BackupModels per supporto backup/restore del nuovo campo
- Aggiornata documentazione README.md e copilot-instructions.md
- La deletion sync è ora disponibile solo per schedulazioni con configurazione esplicita per massima sicurezza
Creato AssociationService per eliminare duplicazione codice e migliorare manutenibilità
Nuovo servizio:
- Data_Coupler/Services/AssociationService.cs (276 righe)
* Interfaccia IAssociationService con metodi pubblici
* PreDiscoveryRequest DTO per parametri configurabili
* FindOrCreateAssociationAsync(): ricerca locale + Pre-Discovery REST
* IsPreDiscoveryAssociation(): verifica marker associazioni Pre-Discovery
Refactoring DataCoupler.razor.cs:
- Injected IAssociationService nel componente
- StartDataTransferOriginal(): ridotto da 98 a 20 righe (-78)
- StartDataTransferWithComposite(): ridotto da 93 a 20 righe (-73)
- Verifica Pre-Discovery: ridotto da 20 a 2 righe (-18)
- Sostituito logica inline con chiamate al servizio centralizzato
Refactoring ScheduledProfileExecutionService.cs:
- Injected IAssociationService nel costruttore
- ExecuteDataTransferWithCompositeAsync(): ridotto da 99 a 20 righe (-79)
- Verifica Pre-Discovery: ridotto da 20 a 2 righe (-18)
- Parametro IsScheduledTransfer=true per tracciabilità
Dependency Injection:
- Registrato IAssociationService in Program.cs come Scoped
- Disponibile per dependency injection in tutti i componenti
Vantaggi:
- Eliminata duplicazione: 3 implementazioni → 1 servizio centralizzato
- Codice ridotto di 266 righe (330 → 64 nelle chiamate)
- Manutenibilità: modifiche future in un solo file
- Testabilità: interfaccia facilmente mockabile per unit test
- Riusabilità: servizio disponibile per futuri componenti
- Separazione responsabilità: logica associazioni isolata
Comportamento invariato:
- Nessuna modifica alla logica Pre-Discovery esistente
- Compatibilità completa con database e API
- Stessi marker e metadata nelle associazioni create
Docs: PRE_DISCOVERY_REFACTORING.md
Build: ✅ Successo (0 errori, 25 warning pre-esistenti)
- Fix FindEntitiesByKeysAsync: SOQL query universale al posto di External ID GET
* Disabilitato External ID GET (funziona solo per campi marcati External ID)
* Query SOQL come metodo primario funzionante per tutti i campi
* Logging dettagliato per diagnostica ricerche Salesforce
- Pre-Discovery nei trasferimenti manuali (DataCoupler.razor.cs)
* Ricerca automatica nella destinazione quando KeyAssociation non esiste
* Creazione associazione con marker CreatedBy="PreDiscovery"
* Aggiornamento forzato senza controllo hash per associazioni Pre-Discovery
* Supporto parallel processing thread-safe
- Pre-Discovery nei trasferimenti schedulati (ScheduledProfileExecutionService.cs)
* Logica identica a trasferimenti manuali
* Marker aggiuntivo ScheduledTransfer=true per tracciabilità
* Aggiornamento forzato per prima sincronizzazione
- Sistema aggiornamento forzato
* Verifica AdditionalInfo per identificare associazioni Pre-Discovery
* Skip controllo hash per associazioni appena scoperte
* Garantisce sincronizzazione dati al primo trasferimento
Vantaggi:
- Prevenzione automatica duplicati in Salesforce
- Recupero record esistenti senza associazioni
- Parità funzionale tra esecuzioni manuali e schedulate
- Performance ottimizzate con controllo hash per esecuzioni successive
Docs: PRE_DISCOVERY_SYSTEM.md, PRE_DISCOVERY_FORCED_UPDATE.md, SALESFORCE_FIND_ENTITIES_FIX.md
- Aggiunto campo MappedDestinationField al modello KeyAssociation per tracciare il campo destinazione mappato alla chiave sorgente
- Creata migration AddMappedDestinationFieldToKeyAssociation per aggiungere la colonna al database
- Implementata logica di popolamento in CreateAssociationAsync e StartDataTransferOriginal per salvare il campo destinazione mappato
- Aggiornato SaveAssociationParallelAsync per includere MappedDestinationField nelle query SQL UPDATE e INSERT
- Corretti indici parametri nella query UPDATE (da {7-9} a {8-10}) per includere il nuovo campo
- Aggiunta visualizzazione campo nell'interfaccia KeyAssociations (tabella, dettagli, export CSV)
- Implementato controllo validazione per impedire trasferimenti se il campo chiave non è mappato
- Aggiunto logging diagnostico dettagliato per debug del mapping dei campi
- Aggiornato ScheduledProfileExecutionService per popolare MappedDestinationField nelle esecuzioni schedulate
- Rimosso file BackgroundServices.cs obsoleto
- Documentazione completa creata (4 markdown files)
Fixes: Campo MappedDestinationField rimaneva NULL perché le query SQL raw non includevano il nuovo campo