文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

如何监控SQL Server服务器CPU的各项指标

2024-12-03 09:22

关注

本文转载自微信公众号「DBA闲思杂想录」,作者潇湘隐者。转载本文请联系DBA闲思杂想录公众号。

如何采集SQL Server数据库服务器上的CPU的一些指标呢?我们知道一些监控工具(例如Zabbix)可以很简单、轻松的获取CPU利用率等指标,但是Zabbix需要在服务器上安装客户端,那么能否通过SQL账号,直接获取例如CPU利用率,SQL Server数据库实例CPU利用率(Instance CPU Utilization)、CPU Signal Waits这些指标呢?如下图所示:

 

在SQL Server中,其实有个没有文档的DMV视图sys.dm_os_ring_buffers,我们可以从这个DMV中获取服务器CPU利用率,数据库实例的CPU利用率,脚本如下

  1.   
  2. DECLARE @ts_now BIGINT
  3. SET  @ts_now= ( SELECT  cpu_ticks / ( cpu_ticks / ms_ticks ) 
  4.                 FROM    sys.dm_os_sys_info WITH ( NOLOCK ) 
  5.               );  
  6.  
  7.  
  8.  SELECT  
  9.         @@SERVERNAME AS [Server Name]  
  10.        ,DATEADD(ms, -1 * (@ts_now  - [timestamp] ), GETDATE()) AS [Event Time
  11.        ,SQLProcessUtilization                                  AS [SQL Server Process CPU Utilization(%)]  
  12.        ,100 - SystemIdle - SQLProcessUtilization               AS [Other Process CPU Utilization(%)]  
  13.        ,100 - SystemIdle                                       AS [OS CPU Utilization(%)] 
  14.        ,SystemIdle                                             AS [System Idle Process(%)]  
  15.  
  16.  FROM   ( SELECT    record.value('(./Record/@id)[1]''int'AS record_id , 
  17.                     record.value('(./Record/SchedulerMonitorEvent/SystemHealth/SystemIdle)[1]'
  18.                                  'int'AS [SystemIdle] , 
  19.                     record.value('(./Record/SchedulerMonitorEvent/SystemHealth/ProcessUtilization)[1]'
  20.                                  'int'AS [SQLProcessUtilization] , 
  21.                     [timestamp
  22.           FROM      ( SELECT    [timestamp] , 
  23.                                 CONVERT(XML, record) AS [record] 
  24.                       FROM      sys.dm_os_ring_buffers WITH ( NOLOCK ) 
  25.                       WHERE     ring_buffer_type = N'RING_BUFFER_SCHEDULER_MONITOR' 
  26.                                 AND record LIKE N'%%' 
  27.                     ) AS x 
  28.         ) AS y 
  29.  ORDER BY record_id DESC 
  30.  OPTION ( RECOMPILE ); 

sys.dm_os_ring_buffers是一个没有文档函数,里面仅仅保存了256分钟的CPU利用率数据,一分钟一条数据。但是也没有其它地方可以设置,延长保存更长时间的数据,所以如果要获取历史的CPU利用率等指标数据,只能通过Python或作业定期采集。下面是Python中要用到的表和脚本。

  1. USE YourSQLDba; 
  2. GO 
  3. IF NOT EXISTS(SELECT 1 FROM sys.objects WHERE type='u' AND name='SERVER_CPU_INFO'
  4. BEGIN 
  5.       CREATE TABLE dbo.SERVER_CPU_INFO 
  6.       ( 
  7.          [server_name]    NVARCHAR(64), 
  8.          [event_time]    DATETIME, 
  9.          [sqlserver_cpu_utilization] FLOAT NOT NULL
  10.          [other_cpu_utilization]     FLOAT NOT NULL
  11.          [os_cpu_utilization]  FLOAT NOT NULL
  12.          [idle_cpu_utilization]     FLOAT NOT NULL
  13.          CONSTRAINT PK_SERVER_CPU_INFO PRIMARY KEY([server_name], [event_time]) 
  14.       ); 
  15. END 
  16. GO 
  17.  
  18. EXEC sys.sp_addextendedproperty @name = N'MS_Description'
  19.     @value = N'服务器CPU利用率信息表', @level0type = N'SCHEMA', @level0name = N'dbo'
  20.     @level1type = N'TABLE', @level1name = N'SERVER_CPU_INFO'
  21. GO 
  22. EXEC sys.sp_addextendedproperty @name = N'MS_Description', @value = N'服务器名称'
  23.     @level0type = N'SCHEMA', @level0name = N'dbo', @level1type = N'TABLE'
  24.     @level1name = N'SERVER_CPU_INFO', @level2type = N'COLUMN'
  25.     @level2name = N'server_name'
  26. GO 
  27. EXEC sys.sp_addextendedproperty @name = N'MS_Description'
  28.     @value = N'事件发生日期时间', @level0type = N'SCHEMA', @level0name = N'dbo'
  29.     @level1type = N'TABLE', @level1name = N'SERVER_CPU_INFO'
  30.     @level2type = N'COLUMN', @level2name = N'event_time'
  31. GO 
  32. EXEC sys.sp_addextendedproperty @name = N'MS_Description'
  33.     @value = N'SQL Server实例占用CPU百分比', @level0type = N'SCHEMA'
  34.     @level0name = N'dbo', @level1type = N'TABLE'
  35.     @level1name = N'SERVER_CPU_INFO', @level2type = N'COLUMN'
  36.     @level2name = N'sqlserver_cpu_utilization'
  37. GO 
  38. EXEC sys.sp_addextendedproperty @name = N'MS_Description'
  39.     @value = N'服务器CPU利用率', @level0type = N'SCHEMA', @level0name = N'dbo'
  40.     @level1type = N'TABLE', @level1name = N'SERVER_CPU_INFO'
  41.     @level2type = N'COLUMN', @level2name = N'os_cpu_utilization'
  42. GO 
  43. EXEC sys.sp_addextendedproperty @name = N'MS_Description'
  44.     @value = N'空闲CPU利用率', @level0type = N'SCHEMA', @level0name = N'dbo'
  45.     @level1type = N'TABLE', @level1name = N'SERVER_CPU_INFO'
  46.     @level2type = N'COLUMN', @level2name = N'idle_cpu_utilization'
  47. GO 
  48. EXEC sys.sp_addextendedproperty @name = N'MS_Description', @value = N'其它进程利用率'
  49.     @level0type = N'SCHEMA', @level0name = N'dbo', @level1type = N'TABLE'
  50.     @level1name = N'SERVER_CPU_INFO', @level2type = N'COLUMN'
  51.     @level2name = N'other_cpu_utilization'
  52. GO 
  53.  
  54.  MERGE INTO dbo.SERVER_CPU_INFO S 
  55.  USING 
  56.  ( 
  57.  SELECT  
  58.    @@SERVERNAME AS [Server Name]  
  59.      ,DATEADD(ms, -1 * ( (SELECT  cpu_ticks / ( cpu_ticks / ms_ticks ) FROM    sys.dm_os_sys_info WITH ( NOLOCK ))  
  60.         - [timestamp] ), GETDATE()) AS [Event Time
  61.      ,SQLProcessUtilization                                  AS [SQL Server Process CPU Utilization(%)]  
  62.      ,100 - SystemIdle                                       AS [OS CPU Utilization(%)] 
  63.      ,SystemIdle                                             AS [System Idle Process(%)]  
  64.      ,100 - SystemIdle - SQLProcessUtilization               AS [Other Process CPU Utilization(%)]  
  65.   FROM   ( SELECT    record.value('(./Record/@id)[1]''int'AS record_id , 
  66.       record.value('(./Record/SchedulerMonitorEvent/SystemHealth/SystemIdle)[1]'
  67.           'int'AS [SystemIdle] , 
  68.       record.value('(./Record/SchedulerMonitorEvent/SystemHealth/ProcessUtilization)[1]'
  69.           'int'AS [SQLProcessUtilization] , 
  70.       [timestamp
  71.      FROM      ( SELECT    [timestamp] , 
  72.                            CONVERT(XML, record) AS [record] 
  73.                  FROM      sys.dm_os_ring_buffers WITH ( NOLOCK )  
  74.                  WHERE     ring_buffer_type = N'RING_BUFFER_SCHEDULER_MONITOR' 
  75.          AND record LIKE N'%%' 
  76.       ) AS x 
  77.    ) AS y  
  78.  ) T 
  79.  --ON (T.[Server Name] = S.server_name AND T.[Event Time] = s.event_time)   
  80.  --注意:由于计算[Event Time]存在偏差,可能导致出现重复记录,只能将其转化精确到分. 
  81.  ON (T.[Server Name] = S.server_name AND CONVERT(VARCHAR(16),T.[Event Time],120) = CONVERT(VARCHAR(16),s.event_time,120)) 
  82.  WHEN NOT MATCHED THEN 
  83.  INSERT  (  
  84.           [server_name]              
  85.          ,[event_time]   
  86.          ,[sqlserver_cpu_utilization] 
  87.          ,[os_cpu_utilization]  
  88.          ,[idle_cpu_utilization]  
  89.          ,[other_cpu_utilization] 
  90.      
  91.     ) 
  92.   VALUES (   T.[Server Name]  
  93.             ,CONVERT(VARCHAR(19),T.[Event Time],120) 
  94.             ,T.[SQL Server Process CPU Utilization(%)]  
  95.             ,T.[OS CPU Utilization(%)] 
  96.             ,T.[System Idle Process(%)]  
  97.             ,T.[Other Process CPU Utilization(%)]  
  98.     ); 

有时候项目经理会跟你说,我们数据库服务器CPU压力大不大,存不存在CPU资源瓶颈?你怎么判断呢?我们不能仅仅根据服务器CPU的利用率来判断,毕竟业务高峰期间,服务器CPU利用率本来可能就比较高,一般而言,我们还需要通过指标“Signal Wait Percent”来判定CPU是否存在瓶颈,通过这个指标判断CPU的瓶颈是否影响了数据库性能。在了解这个指标前,我们先要了解“CPU signal wait time”这个指标。这个指标是啥呢?它指进程或线程从发出信号到开始运行的时间差,在等待运行队列中时间开销,是单纯的CPU等待。

而指标“Signal Wait Percent”它描述了指令等待CPU资源的时间占总时间的百分比。如果“Signal Wait Percent”较高的话,这可能表明CPU已被过度使用,从而迫使SQL Server进程进入任务等待。如果超过20%,说明CPU资源紧张,存在瓶颈。

Signal Wait Percent

The signal wait percentage shows the percentage of overall time that sessions are waiting for a CPU to become available. Anything over 20% would indicate that there is a possible CPU resource bottleneck.

获取“Signal Wait Percent”的脚本如下

  1. SELECT  CAST(100.0 * SUM(signal_wait_time_ms) / SUM(wait_time_ms) AS NUMERIC(20, 
  2.                                                               2)) AS [signal wait percent(%)] , 
  3.         CAST(100.0 * SUM(wait_time_ms - signal_wait_time_ms) 
  4.         / SUM(wait_time_ms) AS NUMERIC(20, 2)) AS [resource waits(%)] 
  5. FROM    sys.dm_os_wait_stats 
  6. OPTION  ( RECOMPILE ); 

注意,signal_wait_time_ms这些值是从服务器的最后一次重新启动后开始计算或累加的,由于是一个累加值,所以,上面计算的[signal wait percent(%)]的值是一个平均值,一段时间内可能不会有变化,它不适合计算某个时间点或时间段之间的“Signal Wait Percent”,可以有下面两种方法解决:

另外,如果一个SQL Server实例下,有多个用户数据库,那么有没有方法统计那个用户数据库消耗了服务器CPU资源的比例呢?统计那个用户数据库消耗的CPU资源最多。当然这个只是大概统计,不是非常精准。

  1. WITH    DB_CPU_Stats 
  2.           AS ( SELECT   pa.DatabaseID , 
  3.                         DB_NAME(pa.DatabaseID) AS [Database Name] , 
  4.                         SUM(qs.total_worker_time / 1000) AS [CPU_Time_Ms] 
  5.                FROM     sys.dm_exec_query_stats AS qs WITH ( NOLOCK ) 
  6.                         CROSS APPLY ( SELECT    CONVERT(INT, value) AS [DatabaseID] 
  7.                                       FROM      sys.dm_exec_plan_attributes(qs.plan_handle) 
  8.                                       WHERE     attribute = N'dbid' 
  9.                                     ) AS pa 
  10.                GROUP BY DatabaseID 
  11.              ) 
  12.     SELECT  ROW_NUMBER() OVER ( ORDER BY [CPU_Time_Ms] DESC ) AS [CPU Rank] , 
  13.             [Database Name] , 
  14.             [CPU_Time_Ms] AS [CPU Time (ms)] , 
  15.             CAST([CPU_Time_Ms] * 1.0 / SUM([CPU_Time_Ms]) OVER ( ) * 100.0 AS DECIMAL(5, 
  16.                                                               2)) AS [CPU Percent(%)] 
  17.     FROM    DB_CPU_Stats 
  18.     WHERE   DatabaseID <> 1  
  19.     ORDER BY [CPU Rank] 
  20. OPTION  ( RECOMPILE ); 

总结:

 

这里我们介绍了如何通过SQL Server的一些DMV视图获取服务器CPU的各项指标数据的一些方法,它的优点是不用在服务器上安装客户端(Agent)工具,一个SQL账号即可采集收集CPU各项指标数据。不足也比较明显,例如,采集频率无法定制。其实像Solarwinds的Database Performance Analyzer等工具就是用这种方式采集CPU各项指标。各有利弊。了解了这些知识点,你也可以在自己的监控工具中加入这些功能,完善、增加一些监控功能。

 

来源:DBA闲思杂想录内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     813人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     354人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     318人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     435人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     224人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯