【Python】如何让SQL Server像MySQL一样拥有慢查询日志(Slow Query Log慢日志)

如何让SQL Server像MySQL一样拥有慢查询日志(Slow Query Log慢日志)

SQL Server一直以来被人诟病的一个问题是缺少了像MySQL的慢日志功能,程序员和运维无法知道数据库过去历史的慢查询语句。

因为SQLServer默认是不捕获过去历史的长时间阻塞的SQL语句,导致大家都认为SQL Server没有历史慢日志功能

其实SQLServer提供了扩展事件让用户自己去捕获过去历史的长时间阻塞的SQL语句,但是因为不是默认出厂配置并且设置扩展事件对初级用户有一定难度,这里可以说不得不是一个遗憾,希望后续版本的SQL Server可以默认设置好慢日志的相关扩展事件,用初级用户也可以快速上手。

话不多说,这个文章主要讲述设置慢日志的扩展事件的步骤,并且把慢日志提供第三方程序读取以提供报表功能。

扩展事件介绍

SQL Server 扩展事件(Extended Events,简称 XE)是从 SQL Server 2008 开始引入的一种轻量级、高度可定制的事件处理系统,
旨在帮助数据库管理员和开发人员更好地监控、调试和优化 SQL Server 的性能。
扩展事件可以用于捕获和分析 SQL Server 内部发生的各种事件,以便识别和解决性能瓶颈和问题。

扩展事件优点包括轻量级、统一事件处理框架和集成性。事件设计对系统性能影响最小,确保在高负载环境下也能稳定运行。
扩展事件可以与 SQL Server Profiler 和 SQL Server Audit 结合使用,为用户提供全面的诊断和监控工具。


实验步骤

创建环境所需的数据库和表

\--窗口1
--建表USE testdb
GOCREATE TABLE Account(id INT, name NVARCHAR(200))INSERT INTO \[dbo\].\[Account\]
SELECT 1,'Lucy'
UNION ALL
SELECT 2,'Tom'
UNION ALL
SELECT 3,'Marry'\--查询
SELECT \* FROM \[dbo\].\[Account\]

创建扩展事件

输入扩展事件名称

不要使用模版

事件库搜索block,选择blocked_process_report

确认事件

选择你需要的字段

这里选择client_app_name、client_hostname、database_id、database_name、plan_handle、query_hash、request_id、session_id、sql_text字段

当然你可以勾选自己想要的字段,这里只是抛砖引玉

直接下一步

这里需要注意的是,扩展事件日志不能全量保存,所以用户需要考虑好保留多长时间的扩展事件,假设一天可以产生的扩展事件大小为1GB,那么每个扩展事件文件大小1GB,最多5个扩展事件文件意味着你不能查询到5天之前的数据

比如你不能查询到前面第8天的扩展事件,扩展事件是滚动利用的。

扩展事件创建情况预览

小提示:你可以点击script生成这个扩展事件的create脚本,那么其他服务器就不用这样用界面去创建这么繁琐了。

生成出来的扩展事件

CREATE EVENT SESSION \[slowquerylog\]
ON SERVERADD EVENT sqlserver.blocked\_process\_report(ACTION(sqlserver.client\_app\_name,sqlserver.client\_hostname,sqlserver.database\_id,sqlserver.database\_name,sqlserver.plan\_handle,sqlserver.query\_hash,sqlserver.request\_id,sqlserver.session\_id,sqlserver.sql\_text))ADD TARGET package0.event\_file(SET filename \= N'E:\\DBExtentEvent\\slowquerylog.xel')
WITH
(STARTUP\_STATE \= ON
);
GO

完成

你可以勾选

a.扩展事件创建完成之后立刻启动

b.查看实时捕获的数据

立刻启动扩展事件

一定要设置locked process threshold,否则无办法捕获慢SQL语句,这个选项类似于MySQL的long_query_time参数

locked process threshold是SQL Server2005推出的一个选项,下面设置阻塞10秒就会记录

\--窗口2
--locked process threshold是SQL Server2005推出的一个选项\--设置阻塞进程阈值
sp\_configure 'show advanced options', 1 ;  
GO  
RECONFIGURE ;  
GO  
sp\_configure 'blocked process threshold', 10 ;   --10秒
GO  
RECONFIGURE ;  
GO  

执行一个update语句,不要commit

\--窗口3
USE testdb;
GOBEGIN tran
update Account
set name \='Test'
where ID \= 2\--commit

查询数据

\-- 窗口4
USE testdb;
GO\-- 这个查询会被窗口3中的事务阻塞
SELECT \* FROM Account
WHERE ID \= 2

执行完毕之后,你可以看到扩展事件已经记录下来了

双击查看详细的会话里面的语句

可以很清楚的看到谁是被blocked的语句,谁是主动blocking的语句也就是源头

同时可以看到扩展事件已经记录到xel文件


使用其他编程语言制作慢查询日志报表

微软提供了使用 SQL Server Management Studio (SSMS) 和 T-SQL 查询扩展事件 XEL 文件内容的 API。

我们可以使用 sys.fn_xe_file_target_read_file 函数来读取 XEL 文件中的内容。
然后,你可以将这些数据导出为其他编程语言可以处理的格式

SQL语句如下

\-- 查询扩展事件 XEL 文件内容
SELECT event\_data.value('(event/@name)\[1\]', 'VARCHAR(50)') AS event\_name,event\_data.value('(event/@timestamp)\[1\]', 'DATETIME2') AS event\_timestamp,event\_data.value('(event/data\[@name="duration"\]/value)\[1\]', 'INT') AS duration,event\_data.value('(event/action\[@name="client\_app\_name"\]/value)\[1\]', 'VARCHAR(255)') AS client\_app\_name,event\_data.value('(event/action\[@name="client\_hostname"\]/value)\[1\]', 'VARCHAR(255)') AS client\_hostname,event\_data.value('(event/action\[@name="database\_name"\]/value)\[1\]', 'VARCHAR(255)') AS database\_name,event\_data.value('(event/action\[@name="sql\_text"\]/value)\[1\]', 'VARCHAR(MAX)') AS sql\_text
FROM sys.fn\_xe\_file\_target\_read\_file('E:\\DBExtentEvent\\slowquerylog\*.xel', NULL, NULL, NULL) AS t
CROSS APPLY t.event\_data.nodes('event') AS XEvent(event\_data);

使用 Python 读取 XEL 文件内容
使用 pandas 库和pyodbc驱动程序从 SQL Server 导出数据并在 Python 中进行处理。
以下是一个示例脚本

import pyodbc
import pandas as pd# 设置数据库连接
conn = pyodbc.connect('DRIVER={SQL Server};''SERVER=your\_server\_name;''DATABASE=your\_database\_name;''UID=your\_username;''PWD=your\_password'
)# 查询 XEL 文件内容
query = """
SELECT event\_data.value('(event/@name)\[1\]', 'VARCHAR(50)') AS event\_name,event\_data.value('(event/@timestamp)\[1\]', 'DATETIME2') AS event\_timestamp,event\_data.value('(event/data\[@name="duration"\]/value)\[1\]', 'INT') AS duration,event\_data.value('(event/action\[@name="client\_app\_name"\]/value)\[1\]', 'VARCHAR(255)') AS client\_app\_name,event\_data.value('(event/action\[@name="client\_hostname"\]/value)\[1\]', 'VARCHAR(255)') AS client\_hostname,event\_data.value('(event/action\[@name="database\_name"\]/value)\[1\]', 'VARCHAR(255)') AS database\_name,event\_data.value('(event/action\[@name="sql\_text"\]/value)\[1\]', 'VARCHAR(MAX)') AS sql\_text
FROM sys.fn\_xe\_file\_target\_read\_file('E:\\DBExtentEvent\\slowquerylog\*.xel', NULL, NULL, NULL) AS t
CROSS APPLY t.event\_data.nodes('event') AS XEvent(event\_data);
"""# 使用 pandas 读取数据
df = pd.read\_sql(query, conn)# 关闭数据库连接
conn.close()# 显示数据
print(df)# 将数据保存为 CSV 文件
df.to\_csv('slowquerylog.csv', index=False)

这里的一个问题是,你不能直接读取XEL文件,本身XEL文件是一个二进制文件,必须挂接到在线SQL Server实例(任何SQL Server实例都可以,不一定是生产库的那一台SQL Server实例,只要是XEL文件所在的机器)

另外一个方法是使用 PowerShell 中的 Microsoft.SqlServer.XEvent.Linq.QueryableXEventData 类直接解析 XEL 文件,不用挂接到SQL Server实例

直接读取 XEL 文件的内容,然后导出CSV文件,让其他编程语言处理

Step 1: 创建 PowerShell 脚本 ReadXELFile.ps1

# 加载所需的程序集
Add-Type -Path "C:\\Program Files\\Microsoft SQL Server\\140\\SDK\\Assemblies\\Microsoft.SqlServer.XEvent.Linq.dll"# 定义XEL文件路径
$xelFilePath = "E:\\DBExtentEvent\\slowquerylog\*.xel"# 创建XEventData对象
$events = New-Object Microsoft.SqlServer.XEvent.Linq.QueryableXEventData($xelFilePath)# 初始化一个空数组来存储事件数据
$eventDataList = @()# 遍历每个事件并提取所需的字段
foreach ($event in $events) {$eventData = New-Object PSObject -Property @{EventName      \= $event.NameTimestamp      \= $event.TimestampDuration       \= $event.Fields\["duration"\].ValueClientAppName  \= $event.Actions\["client\_app\_name"\].ValueClientHostname \= $event.Actions\["client\_hostname"\].ValueDatabaseName   \= $event.Actions\["database\_name"\].ValueSqlText        \= $event.Actions\["sql\_text"\].Value}$eventDataList += $eventData
}# 将事件数据导出为CSV文件
$eventDataList | Export-Csv -Path "E:\\DBExtentEvent\\slowquerylog.csv" -NoTypeInformation

Step 2: Python 脚本 ReadCSVFile.py读取导出的 CSV 文件

import pandas as pd# 定义CSV文件路径
csv\_file\_path = "E:\\\\DBExtentEvent\\\\slowquerylog.csv"# 使用pandas读取CSV文件
df = pd.read\_csv(csv\_file\_path)# 显示数据
print(df)

这个方法需要使用PowerShell ,对于PowerShell 不熟悉的朋友也是一个问题


实现简单审计

虽然SQL Server自带审计功能,但有时候捕捉某些SQL比较困难,我们借助扩展事件更加精准捕捉有问题的SQL语句

有一个场景是,系统用户反馈某个功能的数据每隔几天就会被“恢复”一次,这个恢复操作由一个更新语句所触发,由于不定时发生,所以很难捕捉实际情况。项目负责人遍历整个代码之后发现代码没有包含这个更新语句,怀疑某个版本升级过程完整更新导致在服务器的某个服务中残留代码。要完成这个工作,全面捕捉所有DML语句是不现实的,非常高的QPS加上不定期执行会带来困难。

这时候可以使用扩展事件来处理这个问题

在测试数据库下创建一个test表(只有一个ID字段,这里不演示了),然后创建一个扩展事件来监控SQL文本为update test的语句,把捕捉结果存储在文件里面,执行更新语句后,查询结果

\--创建事件会话
IF EXISTS (SELECT \* FROM sys.server\_event\_sessions WHERE name \= 'CaptureSQL')
\-- 如果已有则删除事件会话
DROP EVENT SESSION \[CaptureSQL\] ON SERVER
GO
\-- 创建名为CaptureSQL的事件会话
CREATE EVENT SESSION \[CaptureSQL\] ON SERVER
\-- 添加sql\_statement\_starting和sql\_statement\_completed的跟踪,并且对sql\_text列进行筛选,同时为了减少开销,还指定了数据库名
-- 在Action中通常添加我们需要跟踪的内容
ADD EVENT sqlserver.sql\_statement\_starting(ACTION(sqlserver.client\_app\_name, sqlserver.client\_connection\_id,sqlserver.client\_hostname, sqlserver.client\_pid, sqlserver.database\_id,sqlserver.nt\_username, sqlserver.sql\_text, sqlserver.username)WHERE ((sql\_text like '%update&test%') AND (\[sqlserver\].\[database\_name\]\=(N'AdventureWorks2016')))  \--关键这一句,捕捉update test语句
),
ADD EVENT sqlserver.sql\_statement\_completed(ACTION(sqlserver.client\_app\_name, sqlserver.client\_connection\_id,sqlserver.client\_hostname, sqlserver.client\_pid, sqlserver.database\_id,sqlserver.nt\_username, sqlserver.sql\_text, sqlserver.username)WHERE ((sql\_text like '%update&test%')) AND (\[sqlserver\].\[database\_name\]\=(N'AdventureWorks2016'))
)
\-- 把会话数据保存到文件中以便日后查看
ADD TARGET package0.event\_file(SET filename\=N'E:\\SQLData\\CaptureSQL.xel',METADATAFILE \= N'E:\\SQLData\\CaptureSQL.xem'
)
WITH (STARTUP\_STATE\=ON) \-- 指定随着服务器启动而启用,服务器宕机后能自动继续运行
GO
\-- 创建完后启用会话,因为默认会话是不开启的
ALTER EVENT SESSION \[CaptureSQL\] ON SERVER STATE \= START;
GO查询结果
;WITH ee\_data AS
(SELECT data \= CONVERT(XML, event\_data)FROM sys.fn\_xe\_file\_target\_read\_file(N'E:\\SQLData\\CaptureSQL.xel', \-- 注意替换实际路径N'E:\\SQLData\\CaptureSQL.xem', \-- 注意替换实际路径NULL, NULL)
),
tab AS
(SELECT\[host\] \= data.value('(/event/action\[@name="client\_hostname"\]/value)\[1\]', 'nvarchar(400)'),app\_name \= data.value('(/event/action\[@name="client\_app\_name"\]/value)\[1\]', 'nvarchar(400)'),username \= data.value('(/event/action\[@name="username"\]/value)\[1\]', 'nvarchar(400)'),\[object\_name\] \= data.value('(/event/data\[@name="object\_name"\]/value)\[1\]', 'nvarchar(250)'),\[timestamp\] \= data.value('(/event/@timestamp)\[1\]', 'datetime2'),\[statement\] \= data.value('(/event/action\[@name="sql\_text"\]/value)\[1\]', 'nvarchar(400)'),\[DBName\] \= DB\_Name(data.value('(/event/action\[@name="database\_id"\]/value)\[1\]', 'nvarchar(400)')),\[ClientPid\] \= data.value('(/event/action\[@name="client\_pid"\]/value)\[1\]', 'nvarchar(400)')FROM ee\_data
)
SELECT DISTINCT \[host\], app\_name, username, MAX(\[timestamp\]) as last\_executed,\[object\_name\], \[statement\], \[DBName\], ClientPid
FROM tab
GROUP BY \[host\], app\_name, username, \[object\_name\], \[statement\], \[DBName\], ClientPid;

创建完毕之后,我们可以使用简单的UPDATE TEST SETID=1语句可触发事件。

通过这种简单的审计方法,让捕捉SQL语句更加简单


总结

本文介绍了利用【SQL Server的扩展事件】捕获慢查询语句的功能,也就是我们常说的开源数据库的慢日志

另外,一定要设置**“blocked process threshold**”参数,否则设置了扩展事件也没有效果

总体来说,SQL Server作为一个企业级数据库,确实不像MySQL这种开源数据库简单直接

需要设置比较繁琐的扩展事件,对新手用户不太友好,门槛比较高,但是因为扩展事件功能非常强大

除了捕获慢查询语句还可以捕获死锁,索引缺失等性能问题,所以这个是在所难免的

👉 这份完整版的Python全套学习资料已经上传,朋友们如果需要可以扫描下方二维码免费领取【保证100%免费】
在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/442998.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

unity ps 2d animation 蛇的制作

一、PS的使用 1.打开PS 利用钢笔工具从下往上勾勒填充 2.复制图层,Ctrl T,w调为-100% 3.对齐图层并继续用钢笔工具进行三角勾勒 3.画眼睛,按U快捷键打开椭圆工具,按住Shift可以画圆,填充并复制图层对称。 4.画笔工具,打开小…

【Windows系统上NodeJS安装教程】

Windows系统上NodeJS安装教程 前言1 下载2 安装3 环境配置4 验证5 自带的npm环境配置 前言 Node.js 是一个基于 Chrome V8 引擎的 JavaScript 运行环境,允许在服务器端运行 JavaScript 代码。它采用事件驱动、非阻塞 I/O 模型,非常适合构建高性能的网络…

Koa2项目实战2(路由管理、项目结构优化)

添加路由(处理不同的URL请求) 路由:根据不同的URL,调用对应的处理函数。 每一个接口服务,最核心的功能是:根据不同的URL请求,返回不同的数据。也就是调用不同的接口返回不同的数据。 在 Node…

sqli-labs靶场第二关less-2

sqli-labs靶场第二关less-2 本次测试在虚拟机搭建靶场,从主机测试 1、输入?id1和?id2发现有不同的页面回显 2、判断注入类型 http://192.168.128.3/sq/Less-2/?id1’ 从回显判断多一个‘ ,预测可能是数字型注入 输入 http://192.168.128.3/sq/Less…

泡沫背后:人工智能的虚幻与现实

人工智能的盛世与泡沫 现今,人工智能热潮席卷科技行业,投资者、创业者和用户都被其光环吸引。然而,深入探讨这种现象,人工智能的泡沫正在形成,乃至具备崩溃的潜质。我们看到的,无非是一场由资本推动的狂欢…

SAP B1 Web Client MS Teams App集成连载五

支持的清单视图/Supported List Views: 以下是面向 Microsoft Teams 的 SAP Business One 应用中支持的清单视图的名称。 Here are the names of the list views that are supported in the SAP Business One app for Microsoft Teams. 支持的详细视图/Supported De…

希亦超声波清洗机值得购买吗?清洁技术之王多维度测评大揭秘!

随着人们生活质量的提升,高质量眼镜愈发受到欢迎,但它们的清洁与保养却常常被疏忽,导致镜片蒙尘受损,影响佩戴者的视觉清晰度。为此,超声波眼镜清洗机作为一种新兴潮流应时而生,以其高效清洁眼镜及珠宝、精…

体系结构论文(五十四):Reliability-Aware Runahead 【22‘ HPCA】

一、文章介绍 问题背景 随着半导体技术的进步,处理器的核心微架构(比如重新排序缓冲区、指令队列、寄存器文件等)变得越来越复杂,这些结构的规模越来越大,这也意味着在处理器等待内存返回数据的过程中,更…

【STM32开发之寄存器版】(三)-详解NVIC中断

一、前言 STM32F103ZET6具备强大的中断控制能力,其嵌套向量中断控制器(NVIC)和处理器核的接口紧密相连,可以实现低延迟的中断处理和高效地处理晚到的中断。NVIC主要具备以下特性: 68个可屏蔽中断通道(不包含16个Cortex™-M3的中断线)&#xf…

FFMpeg源码分析,关键结构体分析(一)

http://lazybing.github.io/blog/categories/ffmpegyuan-ma-fen-xi/ 一、下载FFmpeg的编译源码 进入网站:http://ffmpeg.org/download.html二、编译源码 执行下述命令: ./configure --prefix/usr/local/ffmpeg --enable-debug3 --enable-ffplay sudo …

(12)MATLAB莱斯(Rician)衰落信道仿真2补充:莱斯衰落信道与莱斯随机变量

文章目录 前言1.关于莱斯衰落信道仿真的两个公式2.由式(1)推出式(2) 前言 本文给出关于莱斯衰落信道仿真的两个公式之间的推导。 1.关于莱斯衰落信道仿真的两个公式 在上一篇《(11)MATLAB莱斯&#xff08…

Linux入门3——vim的简单使用

1.vim 1.1 vim的模式 vim有三种主要模式: ①命令模式:使用vim刚打开进入的模式就是命令模式; ②插入模式:只有在插入模式下才可以做文字输入,按[Esc]键可退回命令模式; ③末行模式:文件保存或退…

智能医疗:Spring Boot医院管理系统开发

2相关技术 2.1 MYSQL数据库 MySQL是一个真正的多用户、多线程SQL数据库服务器。 是基于SQL的客户/服务器模式的关系数据库管理系统,它的有点有有功能强大、使用简单、管理方便、安全可靠性高、运行速度快、多线程、跨平台性、完全网络化、稳定性等,非常适…

行为设计模式 -观察者模式- JAVA

观察者模式 一.简介二. 案例2.1 抽象主题(Subject)2.2 具体主题(Concrete Subject)2.3 抽象观察者(Observer)2.4 具体观察者(Concrete Observer)2.5 测试 三. 结论3.1 优缺点3.2 使用…

Vortex GPGPU的github流程跑通与功能模块波形探索(二)

文章目录 前言一、环境配置和debugging.md文档1.1 调试 Vortex GPU1.1.1测试 RTL 或模拟器 GPU 驱动的更改1.1.2 SimX 调试1.1.3 RTL 调试1.1.4 FPGA 调试1.1.5 分析 Vortex 跟踪日志 二、跑出波形文件和日志文件总结 前言 昨天另辟蹊径地去探索了子模块的波形仿真&#xff0c…

【简介Sentinel-1】

Sentinel-1是欧洲航天局哥白尼计划(GMES)中的地球观测卫星,由Sentinel-1A和Sentinel-1B两颗卫星组成。以下是对Sentinel-1的详细介绍: 一、基本信息 卫星名称:Sentinel-1 所属计划:欧洲航天局哥白尼计划…

【含开题报告+文档+PPT+源码】基于SSM框架的民宿酒店预定系统的设计与实现

开题报告 随着人们旅游需求的增加,民宿行业呈现出快速发展的趋势。传统的住宿方式逐渐无法满足人们对个性化、舒适、便捷的需求,而民宿作为一种新型的住宿选择,逐渐受到人们的青睐。民宿的特点是具有独特的风格、便捷的地理位置、相对亲近的…

简单使用DrissionPage网页自动化工具

DrissionPage 是一个基于 python 的网页自动化工具,类似Selenium,可以操控浏览器进行一些自动测试,也可以直接发请求; 官网:DrissionPage官网 (那个浏览器黑白图标一眼看去还以为是只哭泣的小猪&#xff0…

云计算Openstack Neutron

OpenStack Neutron是OpenStack云计算平台中的网络服务组件,它为OpenStack提供了强大的网络连接功能。 一、基本概念 Neutron是一个网络服务项目,旨在为OpenStack提供网络连接。它允许用户创建和管理虚拟网络,包括子网、路由、安全组等&…

VMWare安装和基本使用NixOS Linux 24.05版本

文章目录 简介Nix 语言基础知识NixOS 虚拟机创建 VMWare 的 NixOS 虚拟机安装说明Nix 包管理器安装Windows(WSL)上安装Linux 上安装Docker 上安装MacOS 上安装NixOS 的安装下载 ISO 镜像安装 NixOS修改语言网络配置设置位置设置键盘设置账号和密码桌面环境分区完成安装登录系…