更新1:以下代码在我的DEV机器上正常工作,但在TEST / Production服务器上失败。
public TransImport()
{
ConnString = ConfigurationManager.ConnectionStrings["Connection"].ConnectionString;
SqlConnection conn_new;
SqlCommand command_serial_new;
SqlTransaction InsertUpdateSerialNumbers;
conn_new = new SqlConnection(ConnString);
command_serial_new = conn_new.CreateCommand();
command_serial_new.CommandText = "SELECT 1 FROM YSL00020 WITH (NOLOCK) WHERE SERLNMBR = @slnr";
var p = new SqlParameter("@slnr", SqlDbType.NVarChar, 50);
command_serial_new.Parameters.Add(p);
InsertUpdateSerialNumbers = conn.BeginTransaction();
boolean bErrors = false;
while (!headerFileReader.EndOfStream)
{
headerRow = headerFileReader.ReadLine();
if (!CheckSerialNumber(headerFields[0].Trim()))
{
bErrors = true;
break;
}
}
if (bErrors)
InsertUpdateSerialNumbers.Commit();
else
InsertUpdateSerialNumbers.Rollback();
if (conn_new != null)
{
conn_new.Close();
conn_new.Dispose();
}
}
private Boolean CheckSerialNumber(string SerialNumber)
{
command_serial_new.Parameters["@slnr"].Value = SerialNumber;
try
{
var itExists = Convert.ToInt32(command_serial_new.ExecuteScalar()) > 0;
if (!itExists)
{
command_serial.Transaction = InsertUpdateSerialNumbers;
command_serial.CommandText = "INSERT INTO YSL00([Manifest_Number],[PONUMBER],[ITEMNMBR],[SERLNMBR]"
+ "VALUES ('" + Manifest + "','" + PONr + "','" + itemNumber + "','" + serialNr + "')";
var insertStatus = command_serial.ExecuteNonQuery();
return true;
}
}
catch (Exception ex)
{
LogException(ex, "Error in CheckSerialNumber =>"+ command_serial_new.CommandText.ToString());
}
return false;
}
我在上面的代码中遇到的问题:
我正在使用SQLTransaction with commit&回滚。我遍历一个平面文件并更新一些表。文件通常包含大约500到1000行。我正在为每一行创建INSERT语句(使用sqltransaction),程序在COMMIT语句中停止很长时间,最终我得到错误,如下所示。但是如果我注释掉整个sqltransaction(以及commit plus rollback),一切都很好,但我们需要提交&回滚。有没有办法只创建一个事务(我现在正在为每个INSERT语句创建),这样我就不会得到如下所示的错误。
System.ServiceModel.CommunicationException
从管道读取错误:管道已经结束。 (109,0x6d)。 mscorlib程序
服务器堆栈跟踪: 在System.ServiceModel.Channels.StreamConnection.Read(Byte []缓冲区,Int32偏移量,Int32大小,TimeSpan超时) 在System.ServiceModel.Channels.SessionConnectionReader.Receive(TimeSpan超时) 在System.ServiceModel.Channels.SynchronizedMessageSource.Receive(TimeSpan超时) 在System.ServiceModel.Channels.FramingDuplexSessionChannel.Receive(TimeSpan超时) 在System.ServiceModel.Channels.FramingDuplexSessionChannel.TryReceive(TimeSpan超时,消息和消息) 在System.ServiceModel.Dispatcher.DuplexChannelBinder.Request(消息消息,TimeSpan超时) 在System.ServiceModel.Channels.ServiceChannel.Call(String action,Boolean oneway,ProxyOperationRuntime operation,Object [] ins,Object [] outs,TimeSpan timeout) 在System.ServiceModel.Channels.ServiceChannel.Call(String action,Boolean oneway,ProxyOperationRuntime operation,Object [] ins,Object [] outs) 在System.ServiceModel.Channels.ServiceChannelProxy.InvokeService(IMethodCallMessage methodCall,ProxyOperationRuntime操作) 在System.ServiceModel.Channels.ServiceChannelProxy.Invoke(IMessage message)
在[0]处重新抛出异常: 在System.Runtime.Remoting.Proxies.RealProxy.HandleReturnMessage(IMessage reqMsg,IMessage retMsg) 在System.Runtime.Remoting.Proxies.RealProxy.PrivateInvoke(MessageData& msgData,Int32 type)
答案 0 :(得分:1)
有助于改善这一点的一些事情。
SqlConnection
中的第一个using
命令。
第二个听起来像prod需要更长的时间来运行这个,这就是它超时的原因。您可以将超时设置为无限制。
如果您使用的是SQL Server 2008+,则应使用批量插入。
Insert into table (column1, column2) values (value1, value2), (value3, value4)
另一方面,在动态构建这些时,有一千个值的限制同时被引导。
答案 1 :(得分:0)
使用批量插入修改了我的代码,没有任何问题。