entity-framework entity-framework-4.3

entity framework - EF4.3.1 en.NET 4: la asignación del tipo CLR al tipo EDM es ambigua porque varios tipos CLR coinciden con el tipo EDM



entity-framework entity-framework-4.3 (2)

Creo que llegué al fondo de esto hoy.

Me parece que el tipo de enumeración vive en un ensamblaje separado y el modelo desencadena los tipos de carga de este ensamblaje. Este conjunto contiene el tipo ''DTO.A'' que coincide con el tipo ''Entities.A''. Esto causa la ambigüedad que a su vez hace que se lance una excepción. Tenga en cuenta que no sucedió en .NET Framework 4 ya que los tipos de enumeración en EF4 no eran compatibles y la operación de conversión no causó la carga de tipos desde el otro ensamblaje, por lo que para los proyectos que apuntan a .NET Framework 4 es una regresión en .NET Framework 4.5. En EF6, el comportamiento será el mismo independientemente de la versión de .NET Framework; siempre lo lanzaremos.

Actualización: Sujeto actualizado: ahora es reproducible en EF 4.3.1 bajo .NET 4 ejecutándose con VS2012 instalado bajo Windows 8. ¿Alguna idea de por qué esto empezaría a ocurrir ahora?

El tema lo dice todo de verdad. Acabamos de actualizar de EF 4.3 primero a EF 5 ejecutando bajo .NET 4.0. Tenemos una consulta similar a la siguiente:

ctx.Set<Entities.A>().Select(a => new DTO.A { Id = a.Id, Name = a.Name }).ToArray();

Entities.A se define en un conjunto denominado Entities y DTO.A se define en un conjunto denominado DTO . En EF 4.3 esto funcionó bien, pero bajo EF 5.0 arroja la siguiente excepción:

Schema specified is not valid. Errors: The mapping of CLR type to EDM type is ambiguous because multiple CLR types match the EDM type ''A''. Previously found CLR type ''Entities.A'', newly found CLR type ''DTO.A''.

Rastro de pila es

at System.Data.Metadata.Edm.ObjectItemCollection.LoadAssemblyFromCache(ObjectItemCollection objectItemCollection, Assembly assembly, Boolean loadReferencedAssemblies, EdmItemCollection edmItemCollection, Action''1 logLoadMessage) at System.Data.Metadata.Edm.ObjectItemCollection.ImplicitLoadAssemblyForType(Type type, EdmItemCollection edmItemCollection) at System.Data.Metadata.Edm.MetadataWorkspace.ImplicitLoadAssemblyForType(Type type, Assembly callingAssembly) at System.Data.Objects.ELinq.ExpressionConverter.TryGetValueLayerType(Type linqType, TypeUsage& type) at System.Data.Objects.ELinq.ExpressionConverter.GetCastTargetType(TypeUsage fromType, Type toClrType, Type fromClrType, Boolean preserveCastForDateTime) at System.Data.Objects.ELinq.ExpressionConverter.CreateCastExpression(DbExpression source, Type toClrType, Type fromClrType) at System.Data.Objects.ELinq.ExpressionConverter.ConvertTranslator.TranslateUnary(ExpressionConverter parent, UnaryExpression unary, DbExpression operand) at System.Data.Objects.ELinq.ExpressionConverter.UnaryTranslator.TypedTranslate(ExpressionConverter parent, UnaryExpression linq) at System.Data.Objects.ELinq.ExpressionConverter.TypedTranslator`1.Translate(ExpressionConverter parent, Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.TranslateExpression(Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.UnaryTranslator.TypedTranslate(ExpressionConverter parent, UnaryExpression linq) at System.Data.Objects.ELinq.ExpressionConverter.TypedTranslator`1.Translate(ExpressionConverter parent, Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.TranslateExpression(Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.MemberInitTranslator.TypedTranslate(ExpressionConverter parent, MemberInitExpression linq) at System.Data.Objects.ELinq.ExpressionConverter.TypedTranslator`1.Translate(ExpressionConverter parent, Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.TranslateExpression(Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.TranslateLambda(LambdaExpression lambda, DbExpression input) at System.Data.Objects.ELinq.ExpressionConverter.TranslateLambda(LambdaExpression lambda, DbExpression input, DbExpressionBinding& binding) at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.OneLambdaTranslator.Translate(ExpressionConverter parent, MethodCallExpression call, DbExpression& source, DbExpressionBinding& sourceBinding, DbExpression& lambda) at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.SelectTranslator.Translate(ExpressionConverter parent, MethodCallExpression call) at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.SequenceMethodTranslator.Translate(ExpressionConverter parent, MethodCallExpression call, SequenceMethod sequenceMethod) at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.TypedTranslate(ExpressionConverter parent, MethodCallExpression linq) at System.Data.Objects.ELinq.ExpressionConverter.TypedTranslator`1.Translate(ExpressionConverter parent, Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.TranslateExpression(Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.MemberInitTranslator.TypedTranslate(ExpressionConverter parent, MemberInitExpression linq) at System.Data.Objects.ELinq.ExpressionConverter.TypedTranslator`1.Translate(ExpressionConverter parent, Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.TranslateExpression(Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.TranslateLambda(LambdaExpression lambda, DbExpression input) at System.Data.Objects.ELinq.ExpressionConverter.TranslateLambda(LambdaExpression lambda, DbExpression input, DbExpressionBinding& binding) at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.OneLambdaTranslator.Translate(ExpressionConverter parent, MethodCallExpression call, DbExpression& source, DbExpressionBinding& sourceBinding, DbExpression& lambda) at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.SelectTranslator.Translate(ExpressionConverter parent, MethodCallExpression call) at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.SequenceMethodTranslator.Translate(ExpressionConverter parent, MethodCallExpression call, SequenceMethod sequenceMethod) at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.TypedTranslate(ExpressionConverter parent, MethodCallExpression linq) at System.Data.Objects.ELinq.ExpressionConverter.TypedTranslator`1.Translate(ExpressionConverter parent, Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.TranslateExpression(Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.TranslateSet(Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.UnarySequenceMethodTranslator.Translate(ExpressionConverter parent, MethodCallExpression call) at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.SequenceMethodTranslator.Translate(ExpressionConverter parent, MethodCallExpression call, SequenceMethod sequenceMethod) at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.TypedTranslate(ExpressionConverter parent, MethodCallExpression linq) at System.Data.Objects.ELinq.ExpressionConverter.TypedTranslator`1.Translate(ExpressionConverter parent, Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.TranslateExpression(Expression linq) at System.Data.Objects.ELinq.ExpressionConverter.Convert() at System.Data.Objects.ELinq.ELinqQueryState.GetExecutionPlan(Nullable`1 forMergeOption) at System.Data.Objects.ObjectQuery`1.GetResults(Nullable`1 forMergeOption)

Comprendería el problema si los tipos estuvieran en el mismo ensamblaje (un problema documentado durante mucho tiempo con EF, por el cual no se puede desambiguar usando solo el nombre de la entidad), sino de un ensamblaje diferente.

¿Alguna idea de a dónde ir desde aquí? No veo ninguna manera de decirle a EF que ignore efectivamente el conjunto de DTO y supongo que la generación de expresiones de consulta requiere conocimiento del DTO para proyectar los resultados en la cosa correcta después de la materialización.

Gracias decano


Decano,

Este es un problema conocido como se informa en los siguientes enlaces:

http://entityframework.codeplex.com/workitem/483

http://entityframework.codeplex.com/workitem/589

Entity Framework ignora el espacio de nombres, por lo que las mismas tablas en varias bases de datos causan el problema porque Entity Framework solo mira el nombre de la tabla.

Aparentemente, el equipo de Entity Framework no entiende la importancia de respaldar cualquier esquema de base de datos que tengan los clientes. También han perdido de vista el hecho de que también debería ejecutarse un código de compilación limpio.

Si observa los enlaces que mencioné anteriormente, verá que corregir sus errores tiene una prioridad baja. No sé sobre ti, pero me despedirían por esa actitud.