1. 程式人生 > >解決EF使用context.Database.SqlQuery時NotMapped屬性列為空null的問題(轉載)

解決EF使用context.Database.SqlQuery時NotMapped屬性列為空null的問題(轉載)

有時候我們要為EF中的Model加一個新屬性,這個屬性不是資料庫中的欄位,而是從其它表中關聯出來的。EF中要標示一個列不是對應表中欄位只需要加上NotMapped特性。要使用NotMapped,保證你的專案引用了System.ComponentModel.DataAnnotations.dll,NotMapped特性在名稱空間System.ComponentModel.DataAnnotations.Schema下。比如我們有一個Employee實體:

public class Employee
{
    public int EmployeeId { get; set; }
    
public string EmployeeName { get; set; } [NotMapped] public string CustomerName { get; set; } }

可能你會想到用context.Database.SqlQuery寫一句原生的sql為CustomerName賦值,就像下面的程式碼:

public List<Employee> GetEmployees()
{
    using (MyContext context = new MyContext())
    {
        return context.Database.SqlQuery<Employee>("
select E.EmployeeId, E.EmployeeName, C.CustomerName from Employee E left join Customer C on E.CustomerId = C.CustomerId").ToList(); } }

 

但是遺憾是上面程式碼欄位CustomerName始終都為空。因為使用context.Database.SqlQuery雖然是傳的sql語句,但是它和原生的ADO.NET還是不一樣,它還是會走一下EF框架,用NotMapped標示的欄位,EF會忽略掉這個欄位,當生成sql語句也不會包含這個欄位,無論你增,改,查都不會管這個字欄位,所以讀出來始終為空null值。下面介紹一種利用linq的變通的辦法。

public class EmployeeVM
{
    public int EmployeeId { get; set; }
    public string EmployeeName { get; set; }
    public string CustomerName { get; set; }
}

呼叫EF並使用linq的left join讀取屬性:

public List<Employee> GetEmployees()
{
    using (MyContext context = new MyContext())
    {
        return context.Database.SqlQuery<EmployeeVM>("select E.EmployeeId, E.EmployeeName,
 C.CustomerName from Employee E left join Customer C on E.CustomerId = C.CustomerId")
    .Select(x=> new Employee(){
        EmployeeId = x.EmployeeId,
        EmployeeName = x.EmployeeName,
        CustomerName = x.CustomerName
        }).ToList();
    }
}

 

 

原文連結