Convertire da EF6 a EF Core

Entity Framework Core, in breve EF Core, è una riscrittura completa di Entity Framework per architetture di applicazioni moderne. A causa di modifiche fondamentali, non esiste un percorso di aggiornamento diretto. Lo scopo di questa documentazione è fornire una guida end-to-end per il trasferimento delle applicazioni EF6 in EF Core.

Importante

Prima di iniziare il processo di trasferimento, è importante verificare che EF Core soddisfi i requisiti di accesso ai dati per l'applicazione. È possibile trovare tutte le informazioni necessarie nella documentazione di EF Core.

Importante

Esiste un problema noto (microsoft/dotnet-apiport #993) relativo al Portability Analyzer che segnala erroneamente EF Core come non compatibile con .NET 5 e .NET 6. Questi avvisi possono essere ignorati in modo sicuro perché EF Core è compatibile al 100% con i framework di destinazione .NET 5 e .NET 6.

Motivi per l'aggiornamento

Il nuovo sviluppo per Entity Framework viene eseguito completamente in EF Core. Non sono previsti piani per il backport delle nuove funzionalità in EF6. EF Core viene eseguito nei runtime .NET più recenti e sfrutta appieno le funzionalità del runtime, le funzionalità specifiche della piattaforma (ad esempio ASP.NET Core o WPF) e le funzionalità specifiche del linguaggio. Di seguito sono riportati alcuni dei vantaggi offerti dall'aggiornamento:

  • Sfruttare i miglioramenti delle prestazioni continuativi in EF Core. Ad esempio, un cliente che ha eseguito la migrazione da EF6 a EF Core 6 ha rilevato una riduzione di 40 volte nell'uso di una query complessa a causa della funzionalità di suddivisione delle query. Molti clienti segnalano enormi miglioramenti delle prestazioni grazie semplicemente al passaggio alla versione più recente di EF Core.
  • Usare le nuove funzionalità in EF Core. Non verranno aggiunte nuove funzionalità in EF6. Tutte le nuove funzionalità, ad esempio il provider di Azure Cosmos DB e DbContextFactory, verranno aggiunte solo a EF Core. Per un confronto completo tra EF6 ed EF Core, incluse diverse funzionalità esclusive di EF Core, vedere Confronto tra EF Core & EF6.
  • Modernizzare lo stack di applicazioni usando l'inserimento delle dipendenze e integrare facilmente l'accesso ai dati con tecnologie come gRPC e GraphQL.

Nota sulle migrazioni

Questa documentazione usa i termini trasferimento e aggiornamento per evitare confusione con il termine migrazione come funzionalità di EF Core. Le migrazioni in EF Core non sono compatibili con le migrazioni Code First di EF6 a causa di miglioramenti significativi per la modalità di gestione delle migrazioni. Non esiste un approccio consigliato per trasferire la cronologia delle migrazioni, quindi pianificare l'avvio "da zero" in EF Core. È possibile gestire la codebase e i dati dalle migrazioni di EF6. Applicare la migrazione finale in EF6, quindi creare una migrazione iniziale in EF Core. Sarà possibile tenere traccia della cronologia in EF Core in futuro.

Passaggi dell'aggiornamento

Il percorso di aggiornamento è stato suddiviso in diversi documenti organizzati in base alla fase dell'aggiornamento e al tipo di applicazione.

Determinare la "versione" di EF Core

Esistono diversi approcci per il funzionamento di EF Core con il modello di dominio e l'implementazione del database. In generale, la maggior parte delle app seguirà uno di questi modelli e il modo in cui si gestisce il trasferimento dipenderà dalla "versione" dell'applicazione.

Il codice come fonte di informazioni attendibili è un approccio in cui ogni elemento viene modellato attraverso il codice e le classi, indipendentemente dal fatto che si tratti di attributi di dati, configurazione di Fluent o una combinazione di entrambi. Il database viene inizialmente generato in base al modello definito in EF Core e gli aggiornamenti aggiuntivi vengono in genere gestiti tramite migrazioni. Questo approccio viene spesso definito "Code First", ma il nome non è completamente accurato perché un approccio consiste nell'iniziare con un database esistente, generare le entità e quindi mantenere il codice in futuro.

L'approccio database come fonte di informazioni attendibili comporta il reverse engineering o lo scaffolding del codice dal database. Quando vengono apportate modifiche allo schema, il codice viene rigenerato o aggiornato per rispecchiare le modifiche. Questo approccio viene spesso definito "Database First".

Un approccio di mapping ibrido più avanzato segue infine la filosofia secondo cui il codice e il database vengono gestiti separatamente ed EF Core viene usato per eseguire il mapping tra i due. Questo approccio in genere elimina le migrazioni.

La tabella seguente riepiloga alcune differenze generali:

Approccio ruolo di sviluppatore Ruolo DBA Migrazioni Scaffolding Repository
Code First Progettare entità e verificare/personalizzare le migrazioni generate Verificare le definizioni e le modifiche dello schema Per commit N/D Tenere traccia di entità, DbContext e migrazioni
Database First Reverse engineering dopo le modifiche e verifica delle entità generate Informare gli sviluppatori quando il database subisce modifiche in modo che venga eseguito nuovamente lo scaffolding N/D Per modifica dello schema Tenere traccia delle estensioni/classi parziali che estendono le entità generate
Ibrido Aggiornare la configurazione di Fluent per eseguire il mapping ogni volta che le entità o i database cambiano Informare gli sviluppatori quando vengono apportate modifiche al database in modo che sia possibile aggiornare le entità e la configurazione del modello N/D N/D Tenere traccia di entità e DbContext

L'approccio ibrido è un approccio più avanzato con un sovraccarico aggiuntivo rispetto agli approcci tradizionali per codice e database.

Informazioni sull'impatto dell'allontanamento da EDMX

EF6 supporta un formato speciale di definizione del modello denominato EDMX (Entity Data Model XML). I file EDMX contengono più definizioni, incluse le definizioni dello schema concettuale (CSDL), le specifiche di mapping (MSL) e le definizioni dello schema di archiviazione (SSDL). EF Core tiene traccia dei domini, del mapping e degli schemi di database tramite grafici dei modelli interni e non supporta il formato EDMX. Molti post di blog e articoli dichiarano erroneamente che questo significa che EF Core supporta solo l'approccio "Code First". EF Core supporta tutti e tre i modelli di applicazione descritti nella sezione precedente. È possibile ricompilare il modello in EF Core mediante il reverse engineering del database. Se si usa EDMX per una rappresentazione visiva del modello di entità, prendere in considerazione l'uso di EF Core Power Tools open source che forniscono funzionalità simili per EF Core.

Per altre informazioni sull'impatto della mancanza di supporto per i file EDMX, vedere la guida al trasferimento di EDMX.

Eseguire i passaggi di aggiornamento

Non si tratta di un requisito per trasferire l'intera applicazione. EF6 ed EF Core possono essere eseguiti nella stessa applicazione. Vedere: Uso di EF Core ed EF6 nella stessa applicazione. Per ridurre al minimo i rischi, è possibile prendere in considerazione quanto segue:

  1. Passare a EF6 in .NET Core, se non è già stato fatto.
  2. Eseguire la migrazione di una piccola parte dell'app a EF Core ed eseguirla in modalità affiancata con EF6.
  3. Spostare infine il resto della codebase in EF Core e ritirare il codice di EF6.

Per quanto riguarda il trasferimento stesso, a livello generale, si eseguiranno le operazioni seguenti:

  1. Esaminare le modifiche del comportamento tra EF6 e EF Core.
  2. Eseguire le migrazioni finali, se presenti, in EF6.
  3. Creare il progetto EF Core.
  4. Copiare il codice nel nuovo progetto, eseguire il reverse engineering o una combinazione di entrambi gli approcci.
  5. Rinominare riferimenti ed entità e aggiornare i comportamenti:
    • Da System.Data.Entity a Microsoft.EntityFrameworkCore
    • Modificare il costruttore DbContext per utilizzare le opzioni e/o eseguire l'override di OnConfiguring
    • Da DbModelBuilder a ModelBuilder
    • Rinominare DbEntityEntry<T> in EntityEntry<T>
    • Passare da Database.Log a Microsoft.Extensions.Logging (approccio avanzato) o API DbContextOptionsBuilder.LogTo (approccio semplice)
    • Applicare le modifiche per WithRequired e WithOptional. Vedere qui
    • Aggiornare il codice di convalida. Non esiste alcuna convalida dei dati incorporata in EF Core, ma è possibile eseguirla manualmente.
    • Seguire i passaggi necessari per eseguire il trasferimento da EDMX.
  6. Eseguire passaggi specifici in base all'approccio adottato per EF Core:

Esistono molte considerazioni relative a tutti gli approcci, quindi è anche possibile che si vogliano esaminare i modi per affrontare e risolvere le differenze dettagliate tra EF6 ed EF Core.