• 企业400电话
  • 微网小程序
  • AI电话机器人
  • 电商代运营
  • 全 部 栏 目

    企业400电话 网络优化推广 AI电话机器人 呼叫中心 网站建设 商标✡知产 微网小程序 电商运营 彩铃•短信 增值拓展业务
    Postgresql - 查看锁表信息的实现

    查看表锁信息,是DBA常用的脚本之一。

    实验环境:

    CentOS 7

    PG 10.4

    先通过A窗口执行

    mytest=# begin;
    BEGIN
    mytest=# update t1 set col1 = 'a' where id =1 ;
    UPDATE 1
    mytest=#

    打开B窗口执行

    mytest=# begin;
    BEGIN
    mytest=# update t1 set col1 = 'b' where id =2;
    UPDATE 1
    mytest=# update t1 set col1 = 'b' where id =1;

    等待了

    说明只锁住了行,对于更新其他行没有影响。

    再打开一个窗口查看信息

    SELECT
    a.datname,
    locktype,
    virtualtransaction,
    transactionid,
    nspname,
    relname,
    mode,
    granted,
    cast(date_trunc('second',query_start) AS timestamp) AS query_start
    FROM
    pg_locks
    LEFT OUTER JOIN pg_class ON (pg_locks.relation = pg_class.oid)
    LEFT OUTER JOIN pg_namespace ON (pg_namespace.oid = pg_class.relnamespace),
    pg_stat_activity a
    WHERE NOT pg_locks.pid = pg_backend_pid()
    AND pg_locks.pid=a.pid;
    datname | locktype | virtualtransaction | transactionid | nspname | relname | mode | granted | query_start
    ---------+---------------+--------------------+---------------+---------+---------+------------------+---------+---------------------
    mytest | relation | 7/332 | | public | t1 | RowExclusiveLock | t | 2018-06-28 06:29:58
    mytest | virtualxid | 7/332 | | | | ExclusiveLock | t | 2018-06-28 06:29:58
    mytest | relation | 6/42 | | public | t1 | RowExclusiveLock | t | 2018-06-28 06:29:35
    mytest | virtualxid | 6/42 | | | | ExclusiveLock | t | 2018-06-28 06:29:35
    mytest | transactionid | 7/332 | 712 | | | ExclusiveLock | t | 2018-06-28 06:29:58
    mytest | transactionid | 6/42 | 711 | | | ExclusiveLock | t | 2018-06-28 06:29:35
    mytest | transactionid | 7/332 | 711 | | | ShareLock | f | 2018-06-28 06:29:58
    mytest | tuple | 7/332 | | public | t1 | ExclusiveLock | t | 2018-06-28 06:29:58
    (8 rows)
    

    补充:如何查看PostgreSQL正在执行的SQL以及锁信息

    查看当前正在运行的SQL

    SELECT 
    procpid, 
    start, 
    now() - start AS lap, 
    current_query 
    FROM 
    (SELECT 
    backendid, 
    pg_stat_get_backend_pid(S.backendid) AS procpid, 
    pg_stat_get_backend_activity_start(S.backendid) AS start, 
    pg_stat_get_backend_activity(S.backendid) AS current_query 
    FROM 
    (SELECT pg_stat_get_backend_idset() AS backendid) AS S 
    ) AS S 
    WHERE 
    current_query > 'IDLE>' 
    ORDER BY 
    lap DESC; 
    procpid:进程id 
    start:进程开始时间 
    lap:经过时间 
    current_query:执行中的sql 
    怎样停止正在执行的sql 
    SELECT pg_cancel_backend(进程id); 
    或者用系统函数 
    kill -9 进程id;
    

    查看数据库目前是否有锁

    -- 查看当前事务锁等待、持锁信息的SQL
    with  
    t_wait as  
    (  
     select a.mode,a.locktype,a.database,a.relation,a.page,a.tuple,a.classid,a.granted,  
     a.objid,a.objsubid,a.pid,a.virtualtransaction,a.virtualxid,a.transactionid,a.fastpath,  
     b.state,b.query,b.xact_start,b.query_start,b.usename,b.datname,b.client_addr,b.client_port,b.application_name  
      from pg_locks a,pg_stat_activity b where a.pid=b.pid and not a.granted  
    ),  
    t_run as  
    (  
     select a.mode,a.locktype,a.database,a.relation,a.page,a.tuple,a.classid,a.granted,  
     a.objid,a.objsubid,a.pid,a.virtualtransaction,a.virtualxid,a.transactionid,a.fastpath,  
     b.state,b.query,b.xact_start,b.query_start,b.usename,b.datname,b.client_addr,b.client_port,b.application_name  
      from pg_locks a,pg_stat_activity b where a.pid=b.pid and a.granted  
    ),  
    t_overlap as  
    (  
     select r.* from t_wait w join t_run r on  
     (  
      r.locktype is not distinct from w.locktype and  
      r.database is not distinct from w.database and  
      r.relation is not distinct from w.relation and  
      r.page is not distinct from w.page and  
      r.tuple is not distinct from w.tuple and  
      r.virtualxid is not distinct from w.virtualxid and  
      r.transactionid is not distinct from w.transactionid and  
      r.classid is not distinct from w.classid and  
      r.objid is not distinct from w.objid and  
      r.objsubid is not distinct from w.objsubid and  
      r.pid > w.pid  
     )  
    ),  
    t_unionall as  
    (  
     select r.* from t_overlap r  
     union all  
     select w.* from t_wait w  
    )  
    select locktype,datname,relation::regclass,page,tuple,virtualxid,transactionid::text,classid::regclass,objid,objsubid,  
    string_agg(  
    'Pid: '||case when pid is null then 'NULL' else pid::text end||chr(10)||  
    'Lock_Granted: '||case when granted is null then 'NULL' else granted::text end||' , Mode: '||case when mode is null then 'NULL' else mode::text end||' , FastPath: '||case when fastpath is null then 'NULL' else fastpath::text end||' , VirtualTransaction: '||case when virtualtransaction is null then 'NULL' else virtualtransaction::text end||' , Session_State: '||case when state is null then 'NULL' else state::text end||chr(10)||  
    'Username: '||case when usename is null then 'NULL' else usename::text end||' , Database: '||case when datname is null then 'NULL' else datname::text end||' , Client_Addr: '||case when client_addr is null then 'NULL' else client_addr::text end||' , Client_Port: '||case when client_port is null then 'NULL' else client_port::text end||' , Application_Name: '||case when application_name is null then 'NULL' else application_name::text end||chr(10)||  
    'Xact_Start: '||case when xact_start is null then 'NULL' else xact_start::text end||' , Query_Start: '||case when query_start is null then 'NULL' else query_start::text end||' , Xact_Elapse: '||case when (now()-xact_start) is null then 'NULL' else (now()-xact_start)::text end||' , Query_Elapse: '||case when (now()-query_start) is null then 'NULL' else (now()-query_start)::text end||chr(10)||  
    'SQL (Current SQL in Transaction): '||chr(10)|| 
    case when query is null then 'NULL' else query::text end,  
    chr(10)||'--------'||chr(10)  
    order by  
     ( case mode  
      when 'INVALID' then 0  
      when 'AccessShareLock' then 1  
      when 'RowShareLock' then 2  
      when 'RowExclusiveLock' then 3  
      when 'ShareUpdateExclusiveLock' then 4  
      when 'ShareLock' then 5  
      when 'ShareRowExclusiveLock' then 6  
      when 'ExclusiveLock' then 7  
      when 'AccessExclusiveLock' then 8  
      else 0  
     end ) desc,  
     (case when granted then 0 else 1 end) 
    ) as lock_conflict 
    from t_unionall  
    group by  
    locktype,datname,relation,page,tuple,virtualxid,transactionid::text,classid,objid,objsubid ; 

    以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。如有错误或未考虑完全的地方,望不吝赐教。

    您可能感兴趣的文章:
    • PostgreSQL 实现登录及修改密码操作
    • postgresql表死锁问题的排查方式
    • 基于postgresql数据库锁表问题的解决
    • 基于postgresql行级锁for update测试
    • Postgresql锁机制详解(表锁和行锁)
    • postgresql查询锁表以及解除锁表操作
    • PostgreSQL中关闭死锁进程的方法
    • PostgreSQL用户登录失败自动锁定的处理方案
    上一篇:基于postgresql数据库锁表问题的解决
    下一篇:postgresql synchronous_commit参数的用法介绍
  • 相关文章
  • 

    © 2016-2020 巨人网络通讯 版权所有

    《增值电信业务经营许可证》 苏ICP备15040257号-8

    Postgresql - 查看锁表信息的实现 Postgresql,查看,锁表,信息,