Azure SQL数据库迁移后现有表自动列统计信息未生成问题排查
这种情况我之前帮客户排查过好几次,核心原因大概率是表级的自动统计信息配置被迁移过程覆盖,导致数据库级的全局设置无法生效到这些旧表上——而新创建的表会继承数据库级的默认配置,所以表现正常。下面详细拆解可能的原因和对应的解决步骤:
一、最可能的原因:表级AUTO_CREATE_STATISTICS被禁用
虽然你已经确认数据库级的Auto Create Statistics是开启的,但SQL Server/Azure SQL允许表级设置覆盖全局配置。Data Migration Assistant在迁移时,有可能会把源数据库中某些表的特殊属性(比如曾手动关闭过自动统计的表)一并迁移过来,导致目标表的自动统计创建功能被关闭。
验证方法
执行以下查询检查目标表的配置:
SELECT t.name AS table_name, t.is_auto_create_stats_on FROM sys.tables t WHERE t.name = '你的问题表名'; -- 替换为出现性能问题的表名
如果返回的is_auto_create_stats_on值为0,就说明表级确实禁用了自动统计创建。
解决步骤
针对单个表开启自动统计创建:
ALTER TABLE 你的问题表名 SET (AUTO_CREATE_STATISTICS = ON);
如果需要批量修复所有表,可以用以下脚本:
DECLARE @sql NVARCHAR(MAX) = N''; SELECT @sql += N'ALTER TABLE ' + QUOTENAME(s.name) + N'.' + QUOTENAME(t.name) + N' SET (AUTO_CREATE_STATISTICS = ON);' + CHAR(13) FROM sys.tables t JOIN sys.schemas s ON t.schema_id = s.schema_id WHERE t.is_auto_create_stats_on = 0; EXEC sp_executesql @sql;
二、其他可能的次要原因
1. 统计信息自动创建的阈值未触发
SQL Server/Azure SQL的自动统计创建有内置阈值:
- 对于空表或小表(行数<500),首次执行查询时就会创建统计
- 对于大表(行数>=500),当数据变化量达到
500 + 20%的行数时才会触发自动创建/更新
不过你提到新表执行查询就会创建,旧表却不会,这个原因的概率较低,但可以手动更新一次统计信息来触发后续的自动逻辑:
EXEC sp_updatestats; -- 更新数据库所有表的统计信息
2. 弹性池资源限制导致自动操作延迟
如果你的弹性池处于高负载状态(比如DTU/CPU使用率长期接近100%),Azure SQL可能会延迟自动统计创建这类后台操作。可以在Azure门户查看弹性池的资源使用率,确认是否存在资源瓶颈。
三、验证修复效果
开启表级自动统计后,重新执行之前的慢查询或存储过程,观察是否会自动创建对应的列统计信息(可以通过sys.stats和sys.stats_columns视图查看),同时检查执行计划是否恢复正常,性能是否提升。
内容的提问来源于stack exchange,提问作者SzilardD

