Cambios importantes en EF Core 11 (EF11)

En esta página se documentan los cambios de api y comportamiento que pueden interrumpir la actualización de aplicaciones existentes de EF Core 10 a EF Core 11. Asegúrese de revisar los cambios importantes anteriores si actualiza desde una versión anterior de EF Core:

Resumen

Nota:

Si usa Microsoft.Data.Sqlite, consulte la sección independiente a continuación sobre cambios importantes en Microsoft.Data.Sqlite.

Cambio importante Impact
La sincronización de E/S a través del proveedor de Azure Cosmos DB ha sido completamente eliminada Media
Microsoft. Data.SqlClient se ha actualizado a la versión 7.0 Media
EF Core ahora genera un error de forma predeterminada cuando no se encuentran migraciones Low
EFOptimizeContext Se ha eliminado la propiedad MSBuild Low
Los paquetes de herramientas de EF ya no hacen referencia a Microsoft.EntityFrameworkCore.Design Low
Las propiedades sqlVector ya no se cargan de forma predeterminada Low
Cosmos: las colecciones propias vacías ahora devuelven una colección vacía en lugar de null Low

Cambios de impacto medio

Se ha eliminado por completo la E/S sincrónica a través del proveedor de Azure Cosmos DB

Problema de seguimiento n.º 37059

Comportamiento anterior

La E/S sincrónica a través del proveedor de Azure Cosmos DB no se admite desde EF 9.0 (note); llamar a cualquier API de E/S sincrónica, como ToList o SaveChanges, produjo una excepción, a menos que se haya configurado una opción especial. Cuando se configuraba la opción de activación, las API de E/S sincrónica funcionaban como antes, lo que provocaba que el proveedor realizara un bloqueo "sincrónico sobre asíncrono" contra el SDK de Azure Cosmos DB, lo que podía dar lugar a interbloqueos y otros problemas de rendimiento.

Nuevo comportamiento

A partir de EF Core 11.0, EF ahora lanza siempre una excepción cuando se llama a una API de E/S sincrónica. No hay ninguna manera de volver a usar las API de E/S de sincronización.

Por qué

El bloqueo sincrónico en métodos asincrónicos ("sincronización sobre asincronía") es muy desaconsejable y puede provocar interbloqueos y otros problemas de rendimiento. Dado que el SDK de Azure Cosmos DB solo admite métodos asincrónicos, lo hace el proveedor de EF Cosmos.

Mitigaciones

Convierta el código para usar las API de E/S asincrónicas en lugar de las de E/S de sincronización. Por ejemplo, reemplace las llamadas a SaveChanges() por await SaveChangesAsync().

Microsoft. Data.SqlClient se ha actualizado a la versión 7.0

Comportamiento anterior

EF Core 10 usa Microsoft. Data.SqlClient 6.x, que incluía las dependencias de autenticación Azure/Entra ID (como Azure.Core, Azure.Identity y Microsoft.Identity.Client) en el paquete principal.

Nuevo comportamiento

EF Core 11 ahora depende de Microsoft. Data.SqlClient 7.0. Esta versión quita las dependencias de autenticación Azure/Entra ID (anteriormente Azure Active Directory) del paquete principal. Si la aplicación usa Entra ID autenticación (por ejemplo, ActiveDirectoryDefault, ActiveDirectoryInteractive, ActiveDirectoryManagedIdentity o ActiveDirectoryServicePrincipal), ahora debe instalar el paquete Microsoft.Data.SqlClient.Extensions.Azure por separado.

Además, SqlAuthenticationMethod.ActiveDirectoryPassword se ha marcado como obsoleto.

Para obtener más información, consulte las notas de la versión de Microsoft.Data.SqlClient 7.0.

Por qué

Este cambio se realizó en Microsoft. Data.SqlClient para reducir el sobredimensionamiento de dependencias de las aplicaciones que no usan Azure autenticación, lo que es especialmente beneficioso para implementaciones en contenedores y desarrollo local.

Mitigaciones

Si la aplicación usa autenticación de Entra ID con SQL Server, agregue una referencia al paquete Microsoft.Data.SqlClient.Extensions.Azure en su proyecto:

<PackageReference Include="Microsoft.Data.SqlClient.Extensions.Azure" Version="7.0.0" />

No se requiere ningún cambio de código más allá de agregar esta referencia de paquete. Si usa SqlAuthenticationMethod.ActiveDirectoryPassword, migre a un método de autenticación moderno como ActiveDirectoryDefault o ActiveDirectoryInteractive.

Cambios de bajo impacto

EF Core ahora genera un error de forma predeterminada cuando no se encuentran migraciones

Problema de seguimiento n.º 35218

Comportamiento anterior

Anteriormente, al llamar a Migrate o MigrateAsync en una base de datos sin migraciones en el ensamblado, EF Core registró un mensaje informativo y devolvió sin aplicar ningún cambio.

Nuevo comportamiento

A partir de EF Core 11.0, EF Core produce una excepción de forma predeterminada cuando no se encuentra ninguna migración en el ensamblado. Esto es coherente con el PendingModelChangesWarning comportamiento introducido en EF 9.0.

Por qué

Llamar a Migrate() o MigrateAsync() cuando no existe ninguna migración suele indicar una configuración incorrecta. En lugar de continuar y dejar silenciosamente la base de datos en un estado potencialmente incorrecto, EF Core ahora alerta a los desarrolladores a este problema inmediatamente.

Mitigaciones

Si llama intencionadamente a Migrate() sin tener ninguna migración (por ejemplo, porque administra el esquema de la base de datos por otros medios), elimine la llamada a Migrate() o suprima la excepción configurando las advertencias:

options.ConfigureWarnings(w => w.Ignore(RelationalEventId.MigrationsNotFound))

O para registrar el evento en lugar de lanzar una excepción:

options.ConfigureWarnings(w => w.Log(RelationalEventId.MigrationsNotFound))

EFOptimizeContext Se ha eliminado la propiedad MSBuild

Problema de seguimiento n.º 35079

Comportamiento anterior

Anteriormente, la propiedad EFOptimizeContext de MSBuild se podía establecer en true para habilitar la generación de modelos compilados y código de consulta precompilado durante la compilación o la publicación:

<EFOptimizeContext Condition="'$(Configuration)'=='Release'">true</EFOptimizeContext>

Nuevo comportamiento

A partir de EF Core 11.0, se ha quitado la EFOptimizeContext propiedad MSBuild. La generación de código ahora se controla exclusivamente a través de las EFScaffoldModelStage propiedades y EFPrecompileQueriesStage . Cuando PublishAOT se establece en true, la generación de código se habilita automáticamente cuando se publica sin necesidad de ninguna propiedad adicional.

Por qué

Las EFScaffoldModelStage propiedades y EFPrecompileQueriesStage ya proporcionan un control específico sobre cuándo se produce la generación de código. EFOptimizeContext era una puerta de habilitación redundante.

Mitigaciones

Reemplace los usos de EFOptimizeContext por las EFScaffoldModelStage propiedades y EFPrecompileQueriesStage . Estos se pueden establecer en publish o build para controlar en qué fase se produce la generación de código:

<EFScaffoldModelStage>publish</EFScaffoldModelStage>
<EFPrecompileQueriesStage>publish</EFPrecompileQueriesStage>

Cualquier otro valor (por ejemplo, none) deshabilita la generación correspondiente.

Si ha PublishAOT establecido en true, la generación de código se habilita automáticamente durante la publicación y no se necesita ninguna configuración adicional.

Los paquetes de herramientas de EF ya no hacen referencia a Microsoft.EntityFrameworkCore.Design

Problema de seguimiento n.º 37739

Comportamiento anterior

Anteriormente, los paquetes NuGet de Microsoft.EntityFrameworkCore.Tools y Microsoft.EntityFrameworkCore.Tasks tenían una dependencia de Microsoft.EntityFrameworkCore.Design.

Nuevo comportamiento

A partir de EF Core 11.0, los Microsoft.EntityFrameworkCore.Tools y Microsoft.EntityFrameworkCore.Tasks paquetes NuGet ya no tienen una dependencia de Microsoft.EntityFrameworkCore.Design.

Por qué

No había ninguna dependencia rígida en el código en Microsoft.EntityFrameworkCore.Design, y esta dependencia estaba causando problemas al usar la última Microsoft.EntityFrameworkCore.Tools con proyectos destinados a marcos anteriores.

Mitigaciones

Si su proyecto depende de que Microsoft.EntityFrameworkCore.Design se incorpore transitivamente a través de los paquetes de herramientas, agregue una referencia directa en su proyecto.

<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="11.0.0" PrivateAssets="all" />

Las propiedades sqlVector ya no se cargan de forma predeterminada

Problema de seguimiento n.º 37279

Comportamiento anterior

Anteriormente, al consultar entidades con propiedades SqlVector<T>, EF Core incluía la columna vectorial en las instrucciones SELECT y rellenaba la propiedad en la entidad devuelta.

Nuevo comportamiento

A partir de EF Core 11.0, las propiedades SqlVector<T> ya no se incluyen en las instrucciones SELECT al materializar entidades. La propiedad será null en las entidades devueltas.

Las propiedades vectoriales todavía se pueden usar en las cláusulas WHERE y ORDER BY, incluyéndolas con VectorDistance() y VectorSearch(); simplemente no se incluirán en la proyección de entidad.

Por qué

Las columnas vectoriales pueden ser muy grandes, que contienen cientos o miles de valores de punto flotante. En la mayoría de los casos, los vectores se escriben en la base de datos y, a continuación, se usan para la búsqueda, sin necesidad de volver a leerse. Excluirlos de SELECT de forma predeterminada evita la transferencia de datos innecesaria.

Mitigaciones

Nota:

Un mecanismo para volver a optar por las propiedades vectoriales en la carga automática se incorporará más adelante en la versión de EF Core 11.

Si necesita recuperar los valores de vectores, use una proyección explícita.

var embeddings = await context.Blogs
    .Select(b => new { b.Id, b.Embedding })
    .ToListAsync();

Cosmos: las colecciones propias vacías ahora devuelven una colección vacía en lugar de null

Problema de seguimiento n.º 36577

Comportamiento anterior

Anteriormente, al consultar entidades a través del proveedor de Azure Cosmos DB, cuando una colección propia no contenía elementos, la propiedad de la colección era null en la entidad materializada.

Nuevo comportamiento

A partir de EF Core 11.0, el proveedor de Azure Cosmos DB inicializa correctamente colecciones de propiedad vacías, devolviendo una colección vacía en lugar de null.

Por qué

El comportamiento anterior de materializar colecciones de propiedad vacías como null era un error.

Mitigaciones

Si su código comprueba explícitamente que las propiedades de las colecciones propias sean null para detectar que la colección está vacía, esas comprobaciones pueden eliminarse sin más, ya que ahora la colección siempre está inicializada:

// Before
if (entity.OwnedCollection is null or { Count: 0 })
{
    // treated as empty
}

// After
if (entity.OwnedCollection is { Count: 0 })
{
    // treated as empty
}

Cambios importantes en Microsoft.Data.Sqlite

Nota:

SQLitePCLRaw es una biblioteca externa y mantenida por la comunidad que no es propiedad o mantiene Microsoft. Microsoft. Data.Sqlite depende de él para su conectividad de SQLite.

Resumen

Cambio importante Impact
Se han quitado los paquetes sqLite habilitados para cifrado Media
Se han eliminado algunos conjuntos de SQLitePCLRaw Media

Cambios de impacto medio

Se han quitado los paquetes sqLite habilitados para cifrado

Problema de seguimiento n.º 5108

Comportamiento anterior

Anteriormente, el SQLitePCLRaw.bundle_e_sqlcipher paquete NuGet proporcionaba compilaciones de SQLite habilitadas para cifrado sin costo alguno.

Nuevo comportamiento

A partir de SQLitePCLRaw 3.0 (usado por Microsoft. Data.Sqlite 11.0), el paquete SQLitePCLRaw.bundle_e_sqlcipher ha quedado en desuso y se ha quitado de NuGet. Las compilaciones de SQLite habilitadas para cifrado sin costo ya no se distribuyen.

Por qué

El paquete sin costo SQLitePCLRaw.bundle_e_sqlcipher anterior apenas se mantuvo, lo que es una preocupación importante para el software de cifrado en el que las vulnerabilidades de seguridad pueden no estar actualizadas. El mantenedor SQLitePCLRaw quitó estas compilaciones en la versión 3.0 en favor de las alternativas de pago mantenidas profesionalmente que proporcionan actualizaciones de seguridad continuas.

Mitigaciones

Si necesita cifrado de SQLite, tiene las siguientes opciones:

Para obtener más información, consulte Opciones de cifrado de SQLite para usar con SQLitePCLRaw y Notas de lanzamiento de SQLitePCLRaw 3.0.

Algunos paquetes SQLitePCLRaw se han eliminado

Problema de seguimiento n.º 5108

Comportamiento anterior

Anteriormente, los SQLitePCLRaw.bundle_sqlite3paquetes , SQLitePCLRaw.bundle_winsqlite3, SQLitePCLRaw.bundle_greeny SQLitePCLRaw.bundle_e_sqlite3mc proporcionan una manera cómoda de configurar SQLitePCLRaw con el proveedor de SQLite correspondiente.

Nuevo comportamiento

A partir de SQLitePCLRaw 3.0 (usado por Microsoft. Data.Sqlite 11.0), estos paquetes de agrupación se han quitado. Si la aplicación dependía de uno de estos paquetes, ahora debe hacer referencia al paquete de proveedor correspondiente e inicializarlo explícitamente.

Por qué

Cada uno de estos paquetes de agrupación solo contenía una sola línea de código de configuración y agregó una sobrecarga de empaquetado innecesaria. Los paquetes de proveedor correspondientes siguen siendo compatibles.

Mitigaciones

Reemplace el paquete de agrupación quitado por el paquete de proveedor correspondiente y agregue código de inicialización explícito.

Si usa bundle_sqlite3 o bundle_winsqlite3, reemplace la referencia del paquete:

<!-- Old -->
<PackageReference Include="SQLitePCLRaw.bundle_sqlite3" Version="2.x.x" />
<!-- or -->
<PackageReference Include="SQLitePCLRaw.bundle_winsqlite3" Version="2.x.x" />

<!-- New -->
<PackageReference Include="SQLitePCLRaw.provider.sqlite3" Version="3.x.x" />
<!-- or -->
<PackageReference Include="SQLitePCLRaw.provider.winsqlite3" Version="3.x.x" />

A continuación, agregue la inicialización explícita antes de usar SQLite:

// For sqlite3
static void Init()
{
    SQLitePCL.raw.SetProvider(new SQLitePCL.SQLite3Provider_sqlite3());
}

// For winsqlite3
static void Init()
{
    SQLitePCL.raw.SetProvider(new SQLitePCL.SQLite3Provider_winsqlite3());
}

Si usa bundle_green, la ruta de migración recomendada es cambiar a SQLitePCLRaw.bundle_e_sqlite3. Como alternativa, use SQLitePCLRaw.config.e_sqlite3 emparejado con un paquete de biblioteca nativa independiente, como SourceGear.sqlite3, que permite actualizar la versión de SQLite de forma independiente:

<PackageReference Include="SQLitePCLRaw.bundle_e_sqlite3" Version="3.x.x" />

Si solo tiene como destino iOS y desea seguir usando la biblioteca SQLite del sistema, haga referencia al proveedor directamente:

<PackageReference Include="SQLitePCLRaw.core" Version="3.x.x" />
<PackageReference Include="SQLitePCLRaw.provider.sqlite3" Version="3.x.x" />

E inicialícelo explícitamente:

static void Init()
{
    SQLitePCL.raw.SetProvider(new SQLitePCL.SQLite3Provider_sqlite3());
}

Nota:

Si usa SQLitePCLRaw.bundle_e_sqlite3, no se requieren cambios, solo tiene que actualizar el número de versión. Consulte las notas de lanzamiento de SQLitePCLRaw 3.0 para obtener más información.