2016-01-07 93 views
1

對於更改日誌記錄功能,我需要檢索任何實體的主鍵值。這將與表名以及已更改的屬性名稱以及舊值和新值一起寫入審計表。檢索實體的鍵值

我能反映出特定實體的類型和尋找一個[Key]屬性。這在我的情況下會起作用,因爲我使用了代碼優先,屬性和只有單列鍵。但我不確定(未緩存)反射使用的運行時性能。

有一個更強大和「官方」的方式來獲得從已知到EF實體的主鍵的值?

請留在最新的EF版本(6.1.3)。我無法使用EF 4/5的解決方案來訪問已棄用或已刪除的功能。

代碼示例:

class MyEntity1 
{ 
    [Key] 
    public Guid KeyColumn { get; set; } 
    // ... 
} 

class MyEntity2 
{ 
    [Key] 
    public string EntityId { get; set; } 
    // ... 
} 

class MyContext : DbContext 
{ 
    public DbSet<MyEntity1> Entities1 { get; set; } 
    public DbSet<MyEntity2> Entities2 { get; set; } 

    public object GetEntityKey(object entity) 
    { 
     return ???(entity); 
     // Expected: The value of the property with [Key] 
    } 
} 

PS:我使用下面的全手動解決方法,如果有人正在尋找相同的解決方案。但添加新實體時維護並不容易。

public object GetEntityKey<T>(T entity) 
{ 
    if (typeof(T) == typeof(MyEntity1)) 
    { 
     return ((MyEntity1)(object)entity).KeyColumn; 
    } 
    if (typeof(T) == typeof(MyEntity2)) 
    { 
     return ((MyEntity2)(object)entity).EntityId; 
    } 
    // Important: Makes you aware of new entities 
    throw new NotSupportedException("The specified entity type is not supported."); 
} 

回答

2

我不能使用反射此的表現發表評論,但你當然可以通過使用反射和尋找[關鍵]屬性(我假設他們都找到一個給定的實體的PK這個屬性):

public object GetEntityKey<T>(T entity) 
{ 
    return typeof(T).GetProperties().Where(x => Attribute.IsDefined(x, typeof(KeyAttribute))).Single().GetValue(entity); 
} 
+1

它不應該是'typeof(KeyAttribute)'嗎? –

+0

好地方,更新了答案。 – James