Estoy trabajando en un proyecto de muestra pequeño utilizando Entity Framework 4.1 (código primero). Mis clases se ven así:Código Entity Framework Primero: ¿Por qué no puedo actualizar propiedades complejas de esta manera?
public class Context : DbContext
{
public IDbSet<Person> People { get; set; }
public IDbSet<EmployeeType> EmployeeTypes { get; set; }
}
public class Person
{
[Key]
public int Key { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
virtual public EmployeeType EmployeeType { get; set; }
}
public class EmployeeType
{
[Key]
public int Key { get; set; }
public string Text { get; set; }
virtual public ICollection<Person> People { get; set; }
}
he ahorrado un par de EmployeeTypes ("primero", "segundo") a la base de datos, y me han ahorrado una persona que tiene el primer tipo. Ahora quiero modificar la Persona. Sé que puedo hacer esto cargando la Persona, cambiando las propiedades y luego guardando. Pero lo que quiero hacer en su lugar, lo que me parece que se debe trabajar, es la siguiente:
var c = new Context();
var e = c.EmployeeTypes.Single(x => x.Text.Equals("second"));
var p = new Person {
Key = originalKey, // same key
FirstName = "NewFirst", // new first name
LastName = "NewLast", // new last name
EmployeeType = e }; // new employee type
c.Entry(p).State = EntityState.Modified;
c.SaveChanges();
Curiosamente, esto cambia nombre y apellido, pero no EmployeeType. Si obtengo un nuevo contexto y solicito esta persona, EmployeeType permanece configurado en "primero" como estaba antes de que se ejecutara este código.
¿Qué debo hacer para actualizar las propiedades de navegación, y no solo las propiedades escalares? (Esto es especialmente desconcertante porque para EmployeeType, lo único que realmente necesita cambiar es la clave externa en la tabla Person, y esa clave es una propiedad escalar.)
(Por cierto, sé que puedo hacer esto recuperando primero a la persona, luego cambiando las propiedades una a una, pero como estoy usando el enlace de modelo en ASP.NET MVC, parece que de esta manera sería más fácil porque tendré el objeto de persona actualizado ya en mi método POST)
Ugh, ¿puede ser esa la única manera? Prefiero marcar EmployeeType como Modified y la Person.Aunque cuando lo intenté, tampoco funcionó. –
No funcionará debido a la asociación independiente, como dije, es un objeto separado. Probablemente haya otra forma. Voy a modificar mi respuesta. –
Lo probé de "otra manera": "DbUpdateException: Ocurrió un error al guardar entidades que no exponen propiedades de claves foráneas para sus relaciones. La propiedad EntityEntries devolverá null porque no se puede identificar una sola entidad como el origen de la excepción. El manejo de excepciones al guardar puede hacerse más fácil al exponer propiedades de clave externa en los tipos de entidad. Consulte la InnerException para obtener más información. –