并发ASP.NET会话最佳实践

时间:2021-12-22 06:58:55

User A logs into a ticket management system to edit content on "SomePage.aspx"

用户A登录故障单管理系统以编辑“SomePage.aspx”上的内容

User B logs in 30 seconds later to edit the same ticket on "SomePage.aspx"

用户B在30秒后登录以编辑“SomePage.aspx”上的相同票证

What are some of the best known practices(in a 3-tier architecture) for notifying each of the users that someone else is modifying the same content?

用于通知每个用户其他人正在修改相同内容的一些最着名的实践(在3层体系结构中)是什么?

5 个解决方案

#1


2  

Roundup uses (for example) the optimistic concurrency approach: when you submit your change you may see a warning that someone has made changes before you, with a link to a page showing their changes. You can click Submit to just carry on with your change or edit the values in the form and then submit.

Roundup使用(例如)乐观并发方法:当您提交更改时,您可能会看到有人在您之前进行了更改的警告,其中包含指向显示其更改的页面的链接。您可以单击“提交”继续进行更改或编辑表单中的值,然后提交。

This works OK for a ticketing system because there is little shared state on a ticket -- mostly you append to the message log (or equivalent), so the 2 messages get added one after the other.

这适用于票务系统,因为票证上的共享状态很少 - 大多数情况下您附加到消息日志(或等效物),因此这两条消息将依次添加。

#2


7  

In a request/response system like HTTP, there isn't much of a concept of what a user is currently doing. You could notify them that someone else opened the ticket for edit "within the last two minutes" (or even prevent them from opening it in such a case) but user A could edit for half an hour - unless you prohibit that as well. You could keep a note of the fact that you believe user A has effectively "got" the item for edit, but with a web app there's nothing to stop the user from just walking away from the computer and never either saving/canceling.

在像HTTP这样的请求/响应系统中,没有太多关于用户当前正在做什么的概念。您可以通知他们其他人在最近两分钟内打开了机票进行编辑(或者甚至阻止他们在这种情况下打开它)但是用户A可以编辑半小时 - 除非您也禁止这样做。您可以记下这样一个事实,即您认为用户A已经有效地“获取”了该项目进行编辑,但是使用网络应用程序时,没有什么可以阻止用户离开计算机而从不保存/取消。

Before thinking about the technological solutions, I suggest thinking about the technological restrictions (the asynchronous and request/response nature of the web, basically) and work out the desired behaviour. Some common behaviours are:

在考虑技术解决方案之前,我建议考虑技术限制(基本上是Web的异步和请求/响应性质)并找出所需的行为。一些常见的行为是:

  • First edit wins (tell second editor that their changes have been rejected, basically)
  • 首先编辑胜利(告诉第二编辑他们的更改已被拒绝,基本上)

  • Second edit wins (overwrite first edit - it's too late to tell the first editor)
  • 第二次编辑获胜(覆盖第一次编辑 - 告诉第一个编辑器为时已晚)

  • Merge (can be insanely difficult and/or impossible, depending on the content). This may be automatic or manual (on the part of the second editor).
  • 合并(可能非常困难和/或不可能,取决于内容)。这可以是自动的或手动的(在第二编辑器方面)。

  • Prevent a second person from editing while you think a first person may be editing (rarely appropriate for web apps due to the issue mentioned in the first paragraph)
  • 在您认为第一个人可能正在编辑时阻止第二个人编辑(由于第一段中提到的问题,很少适合网络应用)

#3


1  

I'm not very experienced on this but if I need to do something like that, I would create a new field on the database on the Ticket Table called EditingBy and add a default value of '0'.

我对此并不是很有经验,但如果我需要做类似的事情,我会在Ticket Table上的数据库上创建一个名为EditingBy的新字段,并添加一个默认值'0'。

when a user calls the TicketID = 897 the query should be like:

当用户调用TicketID = 897时,查询应如下所示:

SELECT * FROM Tickets WHERE TicketID = 897; 
UPDATE Tickets SET EditingBy = @UserID WHERE TicketID = 897;

then in the code, you see if the EditingBy is greater than 0 you can warn UserB that UserA (you know the UserID) is editing the ticket, like SO does when someone post an answer and you are writing yours, or when you get a new badge for example.

然后在代码中,您会看到EditingBy是否大于0,您可以警告UserB UserA(您知道UserID)正在编辑故障单,就像有人发布答案并且您正在编写您的,或者当您获得例如新徽章。

when commit the ticket for update you can then update the field back to 0.

提交更新票证时,您可以将该字段更新回0。

and be advise that the user can enter the SomePage.aspx and leave without doing anything, for that a javascript onUnload in the body tag that would trigger an Asynchronous call to update the EdittingBy back to 0 would be an idea.

并建议用户可以输入SomePage.aspx并不做任何事情,因为body标签中的javascript onUnload将触发异步调用以将EdittingBy更新回0,这将是一个想法。

hop that this gives you an idea about doing it.

跳,这让你知道这样做。

Edited: you can always record the EditingBy in a XML file if you can't edit the Database itself, just keep TicketID and UserID, and instead of finding if it is greater than 0, just check if the TicketID is in the XML.

编辑:如果你不能编辑数据库本身,你可以随时将EditingBy记录在XML文件中,只需保留TicketID和UserID,而不是查找它是否大于0,只需检查TicketID是否在XML中。

#4


1  

The best way I found for preventing Optimistic concurrency is by adding a field called timestamp in the database Eg:SQLTimeStamp. This field maintains a unique value for each record in the table. when user A queries the table for editing, store the sqltimestamp value in a session. If user B queries and updates the same record before user A then the sql timestamp value changes. If user A now tries to store the edited value, first check if session stamp is same as current timestamp on database and if the timestamp is different, promp the user that someone modified the record.

我发现阻止乐观并发的最好方法是在数据库中添加一个名为timestamp的字段,例如:SQLTimeStamp。该字段为表中的每条记录维护一个唯一值。当用户A查询表进行编辑时,将sqltimestamp值存储在会话中。如果用户B在用户A之前查询并更新相同的记录,则sql时间戳值会发生变化。如果用户A现在尝试存储编辑的值,首先检查会话标记是否与数据库上的当前时间戳相同,如果时间戳不同,则提示用户有人修改了记录。

This is the solution I use for a web application.

这是我用于Web应用程序的解决方案。

#5


0  

i'm assuming that you're talking about a help-desk ticket or something analgous, where only one user should be working on it at a time. In this case the status of the ticket should change when the first user checks it out

我假设你正在谈论一张帮助台票或一些非常有用的东西,一次只有一个用户应该使用它。在这种情况下,当第一个用户签出时,票证的状态应该会改变

#1


2  

Roundup uses (for example) the optimistic concurrency approach: when you submit your change you may see a warning that someone has made changes before you, with a link to a page showing their changes. You can click Submit to just carry on with your change or edit the values in the form and then submit.

Roundup使用(例如)乐观并发方法:当您提交更改时,您可能会看到有人在您之前进行了更改的警告,其中包含指向显示其更改的页面的链接。您可以单击“提交”继续进行更改或编辑表单中的值,然后提交。

This works OK for a ticketing system because there is little shared state on a ticket -- mostly you append to the message log (or equivalent), so the 2 messages get added one after the other.

这适用于票务系统,因为票证上的共享状态很少 - 大多数情况下您附加到消息日志(或等效物),因此这两条消息将依次添加。

#2


7  

In a request/response system like HTTP, there isn't much of a concept of what a user is currently doing. You could notify them that someone else opened the ticket for edit "within the last two minutes" (or even prevent them from opening it in such a case) but user A could edit for half an hour - unless you prohibit that as well. You could keep a note of the fact that you believe user A has effectively "got" the item for edit, but with a web app there's nothing to stop the user from just walking away from the computer and never either saving/canceling.

在像HTTP这样的请求/响应系统中,没有太多关于用户当前正在做什么的概念。您可以通知他们其他人在最近两分钟内打开了机票进行编辑(或者甚至阻止他们在这种情况下打开它)但是用户A可以编辑半小时 - 除非您也禁止这样做。您可以记下这样一个事实,即您认为用户A已经有效地“获取”了该项目进行编辑,但是使用网络应用程序时,没有什么可以阻止用户离开计算机而从不保存/取消。

Before thinking about the technological solutions, I suggest thinking about the technological restrictions (the asynchronous and request/response nature of the web, basically) and work out the desired behaviour. Some common behaviours are:

在考虑技术解决方案之前,我建议考虑技术限制(基本上是Web的异步和请求/响应性质)并找出所需的行为。一些常见的行为是:

  • First edit wins (tell second editor that their changes have been rejected, basically)
  • 首先编辑胜利(告诉第二编辑他们的更改已被拒绝,基本上)

  • Second edit wins (overwrite first edit - it's too late to tell the first editor)
  • 第二次编辑获胜(覆盖第一次编辑 - 告诉第一个编辑器为时已晚)

  • Merge (can be insanely difficult and/or impossible, depending on the content). This may be automatic or manual (on the part of the second editor).
  • 合并(可能非常困难和/或不可能,取决于内容)。这可以是自动的或手动的(在第二编辑器方面)。

  • Prevent a second person from editing while you think a first person may be editing (rarely appropriate for web apps due to the issue mentioned in the first paragraph)
  • 在您认为第一个人可能正在编辑时阻止第二个人编辑(由于第一段中提到的问题,很少适合网络应用)

#3


1  

I'm not very experienced on this but if I need to do something like that, I would create a new field on the database on the Ticket Table called EditingBy and add a default value of '0'.

我对此并不是很有经验,但如果我需要做类似的事情,我会在Ticket Table上的数据库上创建一个名为EditingBy的新字段,并添加一个默认值'0'。

when a user calls the TicketID = 897 the query should be like:

当用户调用TicketID = 897时,查询应如下所示:

SELECT * FROM Tickets WHERE TicketID = 897; 
UPDATE Tickets SET EditingBy = @UserID WHERE TicketID = 897;

then in the code, you see if the EditingBy is greater than 0 you can warn UserB that UserA (you know the UserID) is editing the ticket, like SO does when someone post an answer and you are writing yours, or when you get a new badge for example.

然后在代码中,您会看到EditingBy是否大于0,您可以警告UserB UserA(您知道UserID)正在编辑故障单,就像有人发布答案并且您正在编写您的,或者当您获得例如新徽章。

when commit the ticket for update you can then update the field back to 0.

提交更新票证时,您可以将该字段更新回0。

and be advise that the user can enter the SomePage.aspx and leave without doing anything, for that a javascript onUnload in the body tag that would trigger an Asynchronous call to update the EdittingBy back to 0 would be an idea.

并建议用户可以输入SomePage.aspx并不做任何事情,因为body标签中的javascript onUnload将触发异步调用以将EdittingBy更新回0,这将是一个想法。

hop that this gives you an idea about doing it.

跳,这让你知道这样做。

Edited: you can always record the EditingBy in a XML file if you can't edit the Database itself, just keep TicketID and UserID, and instead of finding if it is greater than 0, just check if the TicketID is in the XML.

编辑:如果你不能编辑数据库本身,你可以随时将EditingBy记录在XML文件中,只需保留TicketID和UserID,而不是查找它是否大于0,只需检查TicketID是否在XML中。

#4


1  

The best way I found for preventing Optimistic concurrency is by adding a field called timestamp in the database Eg:SQLTimeStamp. This field maintains a unique value for each record in the table. when user A queries the table for editing, store the sqltimestamp value in a session. If user B queries and updates the same record before user A then the sql timestamp value changes. If user A now tries to store the edited value, first check if session stamp is same as current timestamp on database and if the timestamp is different, promp the user that someone modified the record.

我发现阻止乐观并发的最好方法是在数据库中添加一个名为timestamp的字段,例如:SQLTimeStamp。该字段为表中的每条记录维护一个唯一值。当用户A查询表进行编辑时,将sqltimestamp值存储在会话中。如果用户B在用户A之前查询并更新相同的记录,则sql时间戳值会发生变化。如果用户A现在尝试存储编辑的值,首先检查会话标记是否与数据库上的当前时间戳相同,如果时间戳不同,则提示用户有人修改了记录。

This is the solution I use for a web application.

这是我用于Web应用程序的解决方案。

#5


0  

i'm assuming that you're talking about a help-desk ticket or something analgous, where only one user should be working on it at a time. In this case the status of the ticket should change when the first user checks it out

我假设你正在谈论一张帮助台票或一些非常有用的东西,一次只有一个用户应该使用它。在这种情况下,当第一个用户签出时,票证的状态应该会改变