• sp_getAppLock使用


    sp_getAppLock  获取程序资源锁,简单的说就是调用此函数可以达到我们程序中.NET的lock锁的作用.

    作用域是当前数据库下
    四个参数:
    @resource(必填):资源名称,类型nvarchar(255),必填,不区分大小写,如果超出255,则取前255个字符,作用域是当前数据库下.
    @lockMode(必填):锁的模式,类型nvarchar(32),必填,五个值供选择:
      Shared: 共享, 相当于锁里面的S,
      Update: 更新, 相当于锁里面的U
      IntentShared: 意向共享, 相当于锁里面的IS
      IntentExclusive: 意向更新, 相当于锁里面的IX
      Exclusive: 独占, 相当于锁里面的X, 其中我们经常使用的是Exclusive,表示独占上面这个@resource资源
    @lockOwner:锁的拥有者,2个值供参考:
      1. Transaction:默认值,如果使用这个,则必须显示声明事务,事务结束以后释放锁
      2. Session:会话, 会话结束以后释放锁
    @lockTimeout:锁的超时时间
    @DBPrincipal:数据库角色

    我们一般都是使用@LockMode=Exclusive,@LoackMode=Transaction这种方式,所以下面是这种方式的测试.

    
    --不显示声明事务的前提下使用sp_getApplock
    DECLARE @v int; EXEC @v=sp_getapplock @Resource='test',@LockMode='Exclusive' SELECT 1,GETDATE(); WAITFOR DELAY '00:00:03'; SELECT 1,GETDATE(); /* 以下SQL显示的时间内容可以看出,会话1和会话2还是并行的 <<会话1>> 您试图在没有活动事务的情况下获取事务性应用程序锁。 ----------- ----------------------- 1 2017-08-30 10:22:17.883 ----------- ----------------------- 1 2017-08-30 10:22:20.887 <<会话2>> 您试图在没有活动事务的情况下获取事务性应用程序锁。 ----------- ----------------------- 1 2017-08-30 10:22:18.417 ----------- ----------------------- 1 2017-08-30 10:22:21.417 */
    --显示声明事务情况下,调用sp_getAppLock
    
    BEGIN TRAN
    DECLARE @v int;
    EXEC @v=sp_getapplock @Resource='test',@LockMode='Exclusive'
    SELECT 1,GETDATE();
    WAITFOR DELAY '00:00:03';
    SELECT 1,GETDATE();
    COMMIT
    /*
    以下SQL显示的时间内容可以看出,会话1和会话2是串行执行的
    
    <<会话1>>    
    ----------- -----------------------
    1           2017-08-30 10:29:14.197
     
    ----------- -----------------------
    1           2017-08-30 10:29:17.197
    
    
    <<会话2>>
    ----------- -----------------------
    1           2017-08-30 10:29:17.200
    
    ----------- -----------------------
    1           2017-08-30 10:29:20.200
    
    */

    当事务结束或者关闭会话或者服务器因为任何原因关闭的时候都会释放所有锁

    sp_releaseAppLock的作用是释放锁,当一个事务中只有部分代码需要加锁的时候, 就可以在执行完业务逻辑后再次调用sp_releaseApplock @Resource='XXX' , 这样就可以让堵塞的程序继续执行了. 

    例如:

    BEGIN TRAN
    DECLARE @v int;
    EXEC @v=sp_getapplock @Resource='test',@LockMode='Exclusive'
    WAITFOR DELAY '00:00:03';
    SELECT 1,GETDATE();
    EXEC sp_releaseapplock @Resource='test'
    SELECT 2,GETDATE();
    EXEC @v=sp_getapplock @Resource='test',@LockMode='Exclusive' WAITFOR DELAY '00:00:03'; SELECT 5,GETDATE(); EXEC sp_releaseapplock @Resource='test'
    SELECT 6,GETDATE(); COMMIT /* 会话1 ----------- ----------------------- 1 2017-08-30 11:15:23.200 ----------- ----------------------- 2 2017-08-30 11:15:23.200 ----------- ----------------------- 5 2017-08-30 11:15:29.200 ----------- ----------------------- 6 2017-08-30 11:15:29.200 */ BEGIN TRAN DECLARE @v int; EXEC @v=sp_getapplock @Resource='test',@LockMode='Exclusive' WAITFOR DELAY '00:00:03'; SELECT 3,GETDATE(); EXEC sp_releaseapplock @Resource='test'

    SELECT 4,GETDATE();
    EXEC @v=sp_getapplock @Resource='test',@LockMode='Exclusive' WAITFOR DELAY '00:00:03'; SELECT 7,GETDATE(); EXEC sp_releaseapplock @Resource='test'

    SELECT 8,GETDATE(); COMMIT /* 会话2 ----------- ----------------------- 3 2017-08-30 11:15:26.200 ----------- ----------------------- 4 2017-08-30 11:15:26.200 ----------- ----------------------- 7 2017-08-30 11:15:32.200 ----------- ----------------------- 8 2017-08-30 11:15:32.203
    */

    参考资料:

    https://msdn.microsoft.com/zh-cn/library/ms189823(v=sql.90).aspx

    https://msdn.microsoft.com/zh-cn/library/ms178602(v=sql.90).aspx

    测试比较简单,如有不对的地方还请大神指出,谢谢:)

  • 相关阅读:
    html-----018----HTML Web Server/HTML URL 字符编码
    html-----017
    SQL Server 2008 R2评估期已过的解决办法和sqlserver 服务器打不开问题
    Eclipse快捷键大全
    with递归
    PIVOT使用
    SSH框架搭建
    更换开发环境后设置Tomcat和jdk版本
    MyBatis 一对多和多对一关联查询
    MyBatis 使用接口增删改查和两表一对一级联查询
  • 原文地址:https://www.cnblogs.com/blog-east/p/7452317.html
Copyright © 2020-2023  润新知