我创建了一个 SQLAgent 作业,其中一个作业步骤执行了一个不受我直接控制的过程。该过程中有打印语句,当它被执行时,所有这些打印语句的输出显示在作业历史记录->日志文件摘要->行详细信息窗格下作为消息。这本身不是问题,但这些消息掩盖了有时会发生的错误。如何配置 SQLAgent(或作业步骤)以使其忽略这些(信息性)消息并仅显示错误消息。重现步骤:创建一个包含以下语句的作业步骤:打印“hello world”并执行该作业步骤。历史记录显示作为用户执行的消息:NT SERVICE\SQLAgent$MSSQLSERVER2019。你好世界 [SQLSTATE 01000](消息 0)。步骤成功。现在,如果它们是 SQL 语句中的一系列打印语句,其执行结果导致被零除错误,它将显示为消息,但它会被所有这些打印语句输出所掩盖。但是如果可以抑制这些信息性消息,则错误消息将很容易看到。
QFirstLast's questions
越南语整理中的“tR”似乎有一些特别之处。了解它的人是否可以简单地解释一下。这个问题是在我们的产品安装在“越南语”整理的 SQL Server 上时发现的。架构中的一个表的名称中包含“tR”,但存储过程正在引用所有小写“tr”的表。这个参考失败了。
我猜这种情况类似于其他排序规则中的'阝'匹配'ss'。
这是一个复制品:
select case when 'tr' = 'tR' COLLATE SQL_Latin1_General_CP1_CI_AS then 'match' else 'no match' end
select case when 'tr' = 'tR' COLLATE Vietnamese_CI_AI then 'match' else 'no match' end
select case when 'tr' = 'TR' COLLATE Vietnamese_CI_AI then 'match' else 'no match' end
结果:
-----
match
--------
no match
-----
match
第二个 T-SQL 产生不匹配。't' 和 'R' 的其他组合没有。
我在 MS SQL Server 2014(以及 2014SP3)上运行以下查询
SET NOCOUNT ON
CREATE TABLE #GUIDs(
PartyNames_GUID UNIQUEIDENTIFIER NULL,
Party_GUID UNIQUEIDENTIFIER NULL,
FirstName NVARCHAR(255) NULL
)
insert #GUIDs(Party_GUID)
select top 1 Party_GUID
FROM Party a
join PartyNames b on a.Party_ID = b.Party_ID
--Give the optimizer all kinds of choices.
create index i1 on #GUIDs(PartyNames_GUID)
create index i2 on #GUIDs(Party_GUID)
create index i3 on #GUIDs(Party_GUID, PartyNames_GUID)
create index i4 on #GUIDs(PartyNames_GUID,Party_GUID)
update statistics #GUIDs
SELECT PartyNames.PartyNames_ID, PartyNames.LastName, PartyNames.FirstName
FROM Party INNER JOIN PartyNames ON PartyNames.Party_ID = Party.Party_ID
INNER JOIN #GUIDs ON Party.Party_GUID = #GUIDs.Party_GUID --Hard Match on Party_GUID
AND
(#GUIDs.PartyNames_GUID IS NULL OR PartyNames.PartyNames_GUID = #GUIDs.PartyNames_GUID ) --Optional Match
AND
(#GUIDs.FirstName IS NULL OR PartyNames.FirstName = #GUIDs.FirstName ) --Optional Match
drop table #GUIDs
Party 和 PartyNames 表在它们的主 _ID 上都有一个聚集索引,在它们各自的 GUID 上有一个非聚集唯一索引,而 PartyNames 在来自 Party 的外键上有一个索引。这些表的 DDL 包含在末尾,以免混淆问题的描述。Party 有大约 1.9M 行,PartyNames 有 1.3M。PartyNames 每个 Party 最多可以有 3 条记录。上面的查询需要几百毫秒才能运行。但相同的查询在 SQL Server 2012、2016 和 2019 上运行时间为 15 毫秒或更短。所有版本的架构都相同,完全相同的数据在 BCP 完成后和运行查询之前更新。这是 2014 年执行计划的外观 这是其他 SQL Server 版本的执行计划,2012、2016、2019
为什么 2014 年会产生如此糟糕的计划,它扫描 PartyNames 的主键而不是寻找
[PartyNames].[ix_PartyNames_Party_ID?或者更确切地说,高于和低于 2014 的版本如何设法提出一个好的计划,而 2014 没有?其他版本生成的计划显然更好,因为它消耗更少的 CPU 和更少的 IO。是 2014 年的某些服务器设置导致了这种情况吗?SQL Server 2014 优化器的成本计算与之前或之后的版本有很大不同吗?任何帮助或指针表示赞赏。我不愿意认为这是 SQL Server 2014 中的一个缺点。有趣的是,即使记录数减少到几千条,SQL Server 2014 仍会继续生成相同的错误计划。但是删除最后一个 AND 子句 (#GUIDs.FirstName IS NULL OR PartyNames.FirstName = #GUIDs.FirstName ) 会导致 SQL Server 2014 生成与其他版本相同的良好计划。这当然是人为的复制。在 MS SQL Server 2014 上运行我们产品的客户抱怨性能不佳,而在其他版本上则没有。对问题进行故障排除会导致这种简单的再现。
这是用于模式生成的 DDL
CREATE TABLE [dbo].[Party](
[Party_ID] [int] IDENTITY(1,1) NOT NULL,
[Party_GUID] [uniqueidentifier] ROWGUIDCOL NOT NULL,
CONSTRAINT [pk_Party_Party_ID] PRIMARY KEY CLUSTERED ( [Party_ID] ASC),
CONSTRAINT [uq_Party_Party_GUID] UNIQUE NONCLUSTERED ( [Party_GUID] ASC)
)
GO
ALTER TABLE [dbo].[Party] ADD CONSTRAINT [df_Party_Party_GUID] DEFAULT (newid()) FOR [Party_GUID]
GO
CREATE TABLE [dbo].[PartyNames](
[PartyNames_ID] [int] IDENTITY(1,1) NOT NULL,
[PartyNames_GUID] [uniqueidentifier] ROWGUIDCOL NOT NULL,
[Party_ID] [int] NOT NULL,
[FirstName] [nvarchar](255) NULL,
[MiddleName] [nvarchar](255) NULL,
[LastName] [nvarchar](255) NULL,
CONSTRAINT [pk_PartyNames_PartyNames_ID] PRIMARY KEY CLUSTERED ([PartyNames_ID] ASC),
CONSTRAINT [uq_PartyNames_PartyNames_GUID] UNIQUE NONCLUSTERED ([PartyNames_GUID] ASC)
) ON [PRIMARY]
GO
ALTER TABLE [dbo].[PartyNames] ADD CONSTRAINT [df_PartyNames_PartyNames_GUID] DEFAULT (newid()) FOR [PartyNames_GUID]
GO
ALTER TABLE [dbo].[PartyNames] WITH NOCHECK ADD CONSTRAINT [fk_PartyNames_Party_ID] FOREIGN KEY([Party_ID])
REFERENCES [dbo].[Party] ([Party_ID])
GO
ALTER TABLE [dbo].[PartyNames] CHECK CONSTRAINT [fk_PartyNames_Party_ID]
GO
CREATE NONCLUSTERED INDEX [ix_PartyNames_Party_ID] ON [dbo].[PartyNames]
(
[Party_ID] ASC
)
GO
我已经在 MS SQL2008R2 上的表 t1 上设置了 SQL Server 更改跟踪。在事务中,我向其中插入一行并更新它“n”次。当我检查更改跟踪表中的行数时,它显示“n”行,而 syscommitab 仅显示 1 行。由于更改跟踪机制是一种同步机制并且根据文档,预计仅跟踪事务中发生的“净更改”,为什么更改跟踪表显示“n”行而不是仅显示 1 行?下面是用于检查行数的 SQL。
SELECT sct1.name as CT_schema,
sot1.name as CT_table,
ps1.row_count as CT_rows,
ps1.reserved_page_count*8./1024. as CT_reserved_MB,
sct2.name as tracked_schema,
sot2.name as tracked_name,
ps2.row_count as tracked_rows,
ps2.reserved_page_count*8./1024. as tracked_base_table_MB,
change_tracking_min_valid_version(sot2.object_id) as min_valid_version
FROM sys.internal_tables it
JOIN sys.objects sot1 on it.object_id=sot1.object_id
JOIN sys.schemas AS sct1 on
sot1.schema_id=sct1.schema_id
JOIN sys.dm_db_partition_stats ps1 on
it.object_id = ps1. object_id
and ps1.index_id in (0,1)
LEFT JOIN sys.objects sot2 on it.parent_object_id=sot2.object_id
LEFT JOIN sys.schemas AS sct2 on
sot2.schema_id=sct2.schema_id
LEFT JOIN sys.dm_db_partition_stats ps2 on
sot2.object_id = ps2. object_id
and ps2.index_id in (0,1)
WHERE it.internal_type IN (209, 210)
and (sot2.name='t1' or sot1.name='syscommittab')
以上 SQL 由https://www.brentozar.com/archive/2014/06/performance-tuning-sql-server-change-tracking/提供