我有一系列方法可以按照漂亮的顺序对数据库进行一些插入。但是,我遇到了一个问题,其中一个方法在调用另一个方法之前被触发,除非我放入一个断点。
我最初的想法是,由于我在IEnumerables周围传递,该方法在Controller返回对象之前没有启动,但在将所有内容转换为列表后,错误仍然存在。
我的代码如下所示:
// controller
public IActionResult CreateConversation([FromBody] CreateConvoRequest model)
{
var userId = ViewBag.UserData.UserID;
model.message.UserFrom = userId;
model.users.Add(userId);
var result = MessagingLogic.CreateConversation(model.conversation, model.message, model.users);
return Json(result);
}
// Logic
public static Conversation CreateConversation(Conversation conversation, ConversationMessage message,
List<int> users)
{
conversation.DateCreated = DateTime.Now;
conversation.LastUpdated = DateTime.Now;
var convo = SaveNewConversation(conversation, users);
message.ConversationId = convo.ConversationId;
SendMessage(message);
return convo;
}
public static Conversation SaveNewConversation(Conversation conversation, List<int> users)
{
conversation = SaveConversation(conversation);
conversation.Users = users.Select(n => CreateConversationUser(conversation.ConversationId, n)).ToList();
// the above linq executes some SQL insertions and returns the new object
return conversation;
}
public static ConversationMessage SendMessage(ConversationMessage message)
{
if (message.CloseConversation) CloseConversation(message.ConversationId);
return SaveMessage(message);
}
似乎正在发生的事情是在SendMessage
之前调用CreateConversationUser
。这将导致我的消息不能保存给用户,因为在调用SendMessage
方法之前,它们不会保存到数据库中。
但是,如果我在SaveNewConversation
方法上设置断点,一切都按预期工作。
编辑
因此,在进行了一些修补之后,将ToList添加到我的Linq Selected更正了它无序执行的问题。但是,我的SendMessage
SQL语句使用INSERT INTO SELECT。在SendMessage
sql执行时,用户通常还没有插入到数据库中。
例如,我的两个用户分别在2017-09-20 10:29:35.820
和2017-09-20 10:29:35.823
插入。但是,该消息已插入2017-09-20 10:29:35.810
。
SQL服务器上似乎发生了一些奇怪的事情。
编辑2
进一步的测试是将整个责任归咎于SQL Server。我运行了SQL Profiler工具,调用按正确的顺序进入。但是,在插入的最后一个用户和插入的消息之间只有大约3毫秒的延迟。
如果我在用户插入和几百毫秒的消息插入之间放置一个sleep语句,它就会按预期工作。我不太确定如何解决这个问题,但它似乎不再是乱序执行。