簡體   English   中英

使用實體框架和 C# 查詢以檢查列是否可為空

[英]Query to check whether a column is nullable with Entity Framework and C#

要在 SQL 中確定列是否可以具有空值,我執行以下操作:

 SELECT IS_NULLABLE FROM INFORMATION_SCHEMA.COLUMNS WHERE TABLE_SCHEMA = 'dbo' AND TABLE_NAME = 'table_name' AND COLUMN_NAME = 'column_name'

在 C# 和實體框架中,我正在執行以下操作:

 var varx = context.Database.ExecuteSqlCommand("select IS_NULLABLE from INFORMATION_SCHEMA.COLUMNS where TABLE_SCHEMA = 'dbo' AND TABLE_NAME = 'table_name'AND COLUMN_NAME = 'column_name'");

但是無論列是否接受空值, varx始終為 -1。

歡迎任何意見或建議

您可以嘗試解決一些問題 -

使用 EF SqlQuery而不是ExecuteSqlCommand作為 -

string studentName = ctx.Database.SqlQuery<string>("Select studentname from Student where studentid=@id", new SqlParameter("@id", 1))
                            .FirstOrDefault();

注意數據庫。 ExecuteSqlCommnad()方法在執行數據庫命令時很有用,例如插入、更新和刪除命令。

我建議您編輯您的 SQL以使用SYS.COLUMNS表,如下所示。
dbo.Worker是我的數據庫表, Worker_Id為 Not Null 列, First_Name為 Nullable 列

SELECT IS_NULLABLE FROM SYS.COLUMNS 
WHERE OBJECT_ID = OBJECT_ID('dbo.Worker') AND NAME = 'Worker_id' --Returns 0  

SELECT IS_NULLABLE FROM SYS.COLUMNS 
WHERE OBJECT_ID = OBJECT_ID('dbo.Worker') AND NAME = 'First_Name' --Returns 1  

SYS.COLUMNS 是一個系統表,用於維護數據庫中列的信息。 對於在數據庫中添加的每一列,都會在 SYS.COLUMNS 表中創建一條記錄。

如前所述,如果您使用 EF6 SqlQuery可以執行查詢並返回結果。

但是,如果您准備好親自動手並詢問 EF 本身,則可以在不執行查詢的情況下從 EF6 中獲取此信息。 讓我們面對現實吧,EF 需要知道這種事情才能完成它的工作,對吧?

首先,這要歸功於 romiller的勇氣。

以下是我用來獲取實體審計類似信息的方法的修改。 它為指定的模型屬性計算出相應的存儲屬性,在這種情況下,返回列是否可為空。

public static class DbContextExtensions
{
    public static bool IsPropertyNullableFor(this DbContext context, Type type, string propertyName)
    {
        var metadataWorkspace = ((IObjectContextAdapter) context).ObjectContext.MetadataWorkspace;

        var objectItemCollection = (ObjectItemCollection) metadataWorkspace.GetItemCollection(DataSpace.OSpace);

        var entityType = metadataWorkspace
            .GetItems<EntityType>(DataSpace.OSpace)
            .Single(e => objectItemCollection.GetClrType(e) == type);

        var entitySet = metadataWorkspace.GetItems<EntityContainer>(DataSpace.CSpace)
            .Single()
            .EntitySets
            .Single(s => s.ElementType.Name == entityType.Name);

        var entitySetMapping = metadataWorkspace
            .GetItems<EntityContainerMapping>(DataSpace.CSSpace)
            .Single()
            .EntitySetMappings
            .Single(s => s.EntitySet.Equals(entitySet));

        var column = entitySetMapping
            .EntityTypeMappings.Single()
            .Fragments.Single()
            .PropertyMappings
            .OfType<ScalarPropertyMapping>()
            .Single(m => m.Property.Name == propertyName)
            .Column;

        return column.Nullable;
    }
}

像這樣調用:

Console.WriteLine("Is id nullable?: " + dbContext.IsPropertyNullableFor(typeof(MyClass), nameof(MyClass.Id)));

您可以使用泛型/表達式收緊接口,這只是演示如何執行此操作。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM