2014-09-30 135 views
3

我想使用fastmember(Fastmember NuGet)扩展名和sqlbulkcopy将一定数量的自定义对象列表粘贴到我的数据库中。但是它给了我下面的错误:SqlBulkCopy无法将值NULL插入列

An unhandled exception of type 'System.Data.SqlClient.SqlException' occurred in System.Data.dll 

Additional information: Cannot insert the value NULL into column 'functionblockId', table '\path...\DBFHX.MDF.dbo.connections'; column does not allow nulls. INSERT fails. 

The statement has been terminated. 

代码:

private void insertConnection(functionblock functionblock) 
{ 
    using (var bcp = new SqlBulkCopy(db.Database.Connection.ConnectionString)) 
    { 
     foreach (connection item in functionblock.connections) 
       { 
        item.functionblockId = 1; 
       } 
     using (var creader = ObjectReader.Create(functionblock.connections, "step", "transition","steptotrans", "functionblockId")) 
       { 
        bcp.DestinationTableName = "connections"; 
        bcp.WriteToServer(creader); 
       } 
    } 
} 

使用型号首先,实体框架产生如下表:

CREATE TABLE [dbo].[connections] (
    [Id]    INT   IDENTITY (1, 1) NOT NULL, 
    [step]   NVARCHAR (MAX) NOT NULL, 
    [transition]  NVARCHAR (MAX) NOT NULL, 
    [steptotrans]  BIT   NOT NULL, 
    [functionblockId] INT   NOT NULL, 
    CONSTRAINT [PK_connections] PRIMARY KEY CLUSTERED ([Id] ASC), 
    CONSTRAINT [FK_functionblockconnection] FOREIGN KEY ([functionblockId]) REFERENCES [dbo].[functionblocks] ([Id]) 
); 

的代码工作正常,为不同表中还包含相同的“functionblockId”和相同类别的其他字段(尽管不包含位字段)。

我手动检查了所有我在functionblock.connections列表中的值,然后在具体的对象中它的'functionblockId',它都被一个数字填充。更好的是,就像你在代码中看到的那样,我实际上在我将它硬编码之前填充它进行硬编码。

我不知道为什么会出现此错误,有没有人有想法?

回答

6

在用测试数据手动生成DataTable后,它仍然给了我相同的错误。

我碰到过这篇文章(codeproject solution),并将SqlBulkCopyColumnMapping应用于我的案例。

代码示例:

using (var bcp = new SqlBulkCopy(fhxm.Database.Connection.ConnectionString)) 
            { 
            using (var creader = ObjectReader.Create(functionblock.connections, "step", "transition", "steptotrans", "functionblockId")) 
            { 
            SqlBulkCopyColumnMapping mapstep = new SqlBulkCopyColumnMapping("step", "step"); 
            SqlBulkCopyColumnMapping maptran = new SqlBulkCopyColumnMapping("transition", "transition"); 
            SqlBulkCopyColumnMapping mapstt = new SqlBulkCopyColumnMapping("steptotrans", "steptotrans"); 
            SqlBulkCopyColumnMapping mapfunc = new SqlBulkCopyColumnMapping("functionblockId", "functionblockId"); 
            bcp.ColumnMappings.Add(mapstep); 
            bcp.ColumnMappings.Add(maptran); 
            bcp.ColumnMappings.Add(mapstt); 
            bcp.ColumnMappings.Add(mapfunc); 

            bcp.DestinationTableName = "connections"; 
            bcp.WriteToServer(creader); 
            } } 
+0

你必须通过使用列映射跳过标识列。您的其他表格是否没有标识列? – 2014-10-01 15:47:23

+0

它确实有一个标识列,后来我发现如果我这样做:ObjectReader.Create(functionblock.connections,“Id”,“step”,“transition”,“steptotrans”,“functionblockId”))它也插入也没有列映射。 – usselite 2014-10-01 16:22:12

0

然而,对于这个语法不太熟悉: 我不知道'item'对象是否实际在事务中被使用。 它看起来像ObjectReader.Create步骤通过连接,'item'引用的独立 。

尝试减少交易计数以确认正确的行数到达 ,因为您可能正在加入迭代器。

此外,也许您可​​以尝试捕获item.functionblockId, 的意外值作为诊断工具。

相关问题