【问题标题】:T-SQL lock resouce in an event of concurrent access并发访问事件中的 T-SQL 锁定资源
【发布时间】:2013-11-05 10:22:25
【问题描述】:

我想在并发访问的情况下锁定某个表。

在存储过程中:

  • 我截断了一个表
  • 进行计算并填写上表
  • 从 PROCEDURE 返回后,从表中进行选择

为避免并发访问时出现问题,我计划添加“BEGIN TRANSACTION”,然后添加“BEGIN TRY -END TRY”和“BEGIN CATCH - END CATCH”。我在 'CATCH' 中的 'END-TRY' 和 'ROLLBACK' 之前'COMMIT'。

仅此一项就可以解决所有并发问题还是我需要做更多的事情。

非常感谢, 苏吉特

【问题讨论】:

    标签: sql-server tsql concurrency sqltransaction


    【解决方案1】:

    您可以在事务期间使用TABLOCKTABLOCKX (references) 锁定整个表:

    BEGIN TRANSACTION;
    
    -- For shared locking:    
    -- This will take a S(shared) lock at table level for duration of transaction
    -- SELECT TOP(0) * FROM dbo.MyTable WITH(TABLOCK,HOLDLOCK)
    -- HOLDLOCK hint is needed in this case because 
    -- default behavior at default transaction isolation level (READ COMMITTED) 
    -- is to maintain a S lock only during record reading.
    
    -- For exclusive locking:    
    -- This will take a (x)X(clusive) lock at table level for duration of transaction
    SELECT TOP(0) * FROM dbo.MyTable WITH(TABLOCKX)
    
    ROLLBACK;
    

    示例(SQL Profiler 输出):

    注意:SELECT OBJECT_ID(N'dbo.MyTable') = 1316199739

    【讨论】:

    • 亲爱的博格丹,感谢您的建议。我从经理那里收到的另一个解决方案是利用同一张表中的“LoggedInUser”字段,并针对当前的“LoggedInUser”执行 DML,以避免并发问题。
    • @sujimon:如果你给我更多关于你的问题的细节,我可以帮助你更多。目前,我在您的问题中看不到任何有关 LoggedInUser 列的信息。
    • 我想我没有正确地回答我的问题。我最好在表上没有任何数据库锁定。我只是想解决多用户环境中的并发问题。我后来发现可以通过 A> 识别记录的用户配置文件 B> 识别访问应用程序的计算机名 C> 在存储过程中使用表变量来完成。但我同意你关于表锁的看法,所以我会将此标记为答案!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-12-23
    • 1970-01-01
    • 2012-06-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多