Finding 1 of 5Achado 1 de 5
· CriticalCrítica
ConfirmedConfirmado
Databases with missing or old backupsBancos com backup ausente ou antigo
| database | recovery_model | last_full | last_diff | last_log | problem |
| sales | FULL | 2026-10-12 23:10 | NULL | 2026-10-12 23:40 | full/diff too old |
| inventory | FULL | 2026-10-21 23:05 | 2026-10-21 23:30 | 2026-10-21 02:15 | log backup too old |
What it meansO que significa
A failure or mistake on these databases may lose more data than you expect, or be unrecoverable.Uma falha ou erro nesses bancos pode perder mais dados do que você espera, ou não ter recuperação.
Recommended actionAção recomendada
Check the backup jobs for these databases and run a manual backup now. In FULL recovery, schedule log backups too.Verifique os jobs de backup desses bancos e faça um backup manual agora. Em recovery FULL, agende também backups de log.
CaveatRessalva: Based on msdb history on this instance. Backups taken by external tools without msdb history are not visible.Baseado no histórico do msdb desta instância. Backups de ferramentas externas sem histórico no msdb não aparecem.
Source queryQuery de origem · Collected atColetado em 2026-10-22 09:30 UTC · 120ms
WITH b AS (
SELECT database_name,
MAX(CASE WHEN type = 'D' THEN backup_finish_date END) AS last_full,
MAX(CASE WHEN type = 'I' THEN backup_finish_date END) AS last_diff,
MAX(CASE WHEN type = 'L' THEN backup_finish_date END) AS last_log
FROM msdb.dbo.backupset
WHERE is_copy_only = 0
GROUP BY database_name
)
SELECT d.name AS [database],
d.recovery_model_desc AS recovery_model,
b.last_full,
b.last_diff,
b.last_log,
CASE
WHEN b.last_full IS NULL THEN 'no full backup'
WHEN ISNULL(b.last_diff, b.last_full) < DATEADD(hour, -{{full_max_hours}}, GETDATE())
AND b.last_full < DATEADD(hour, -{{full_max_hours}}, GETDATE()) THEN 'full/diff too old'
ELSE 'log backup too old'
END AS problem
FROM sys.databases d
LEFT JOIN b ON b.database_name = d.name
WHERE d.database_id <> 2 -- tempdb
AND d.state_desc = 'ONLINE'
AND d.source_database_id IS NULL -- snapshots
AND (
b.last_full IS NULL
OR (ISNULL(b.last_diff, b.last_full) < DATEADD(hour, -{{full_max_hours}}, GETDATE())
AND b.last_full < DATEADD(hour, -{{full_max_hours}}, GETDATE()))
OR (d.recovery_model_desc <> 'SIMPLE' AND d.name <> 'model'
AND ISNULL(b.last_log, '19000101') < DATEADD(hour, -{{log_max_hours}}, GETDATE()))
)
ORDER BY d.name;
Finding 2 of 5Achado 2 de 5
· HighAlta
ConfirmedConfirmado
Databases without a recent clean DBCC CHECKDBBancos sem DBCC CHECKDB recente e sem erros
| database | last_good_checkdb | days_ago | create_date |
| sales | 2026-08-30 01:00 | 53 | 2021-03-02 |
| reporting | NULL | NULL | 2025-11-18 |
What it meansO que significa
Corruption can sit unnoticed for weeks and end up in every backup, leaving nothing clean to restore.Uma corrupção pode passar semanas sem ser notada e entrar em todos os backups, sem deixar nada limpo para restaurar.
Recommended actionAção recomendada
Schedule DBCC CHECKDB (WITH NO_INFOMSGS, ALL_ERRORMSGS) at least weekly, or on a restored copy if the window is short.Agende DBCC CHECKDB (WITH NO_INFOMSGS, ALL_ERRORMSGS) pelo menos semanalmente, ou numa cópia restaurada se a janela for curta.
CaveatRessalva: Reads LastGoodCheckDbTime, which only records runs that finished without errors. Databases created in the last days are skipped.Lê o LastGoodCheckDbTime, que só registra execuções concluídas sem erros. Bancos criados nos últimos dias são ignorados.
Source queryQuery de origem · Collected atColetado em 2026-10-22 09:30 UTC · 120ms
SELECT d.name AS [database],
NULLIF(CAST(DATABASEPROPERTYEX(d.name, 'LastGoodCheckDbTime') AS datetime), '19000101') AS last_good_checkdb,
DATEDIFF(day, NULLIF(CAST(DATABASEPROPERTYEX(d.name, 'LastGoodCheckDbTime') AS datetime), '19000101'), GETDATE()) AS days_ago,
d.create_date
FROM sys.databases d
WHERE d.database_id <> 2 -- tempdb
AND d.state_desc = 'ONLINE'
AND d.source_database_id IS NULL -- snapshots
AND d.create_date < DATEADD(day, -{{max_days}}, GETDATE())
AND ISNULL(CAST(DATABASEPROPERTYEX(d.name, 'LastGoodCheckDbTime') AS datetime), '19000101') < DATEADD(day, -{{max_days}}, GETDATE())
ORDER BY d.name;
Finding 3 of 5Achado 3 de 5
· HighAlta
HintIndício
The instance spends a lot of time waiting on one resourceA instância passa muito tempo esperando por um recurso
| meaning | meaning | wait_type | share_pct | wait_s_per_hour | avg_wait_ms |
| Disk reads (data pages not in memory) | Leitura de disco (páginas fora da memória) | PAGEIOLATCH_SH | 41.7 | 812.4 | 18.3 |
| Parallel query coordination | Coordenação de consultas paralelas | CXPACKET | 22.9 | 446 | 3.1 |
What it meansO que significa
Waits are where query time goes when it isn't running. A dominant wait points straight at the bottleneck (disk, locks, CPU, memory).As esperas mostram para onde vai o tempo das consultas quando elas não estão executando. Uma espera dominante aponta direto para o gargalo (disco, bloqueios, CPU, memória).
Recommended actionAção recomendada
Start with the top row. The meaning column says which resource to look at; the rule's documentation page lists the usual causes for each wait.Comece pela primeira linha. A coluna de significado diz qual recurso investigar; a página da regra na documentação lista as causas comuns de cada espera.
CaveatRessalva: Totals accumulate since the last restart, so they show the long-term profile, not what is happening right now. Only deltas over time show the present.Os totais acumulam desde o último restart, então mostram o perfil de longo prazo, não o que acontece agora. Só diferenças ao longo do tempo mostram o presente.
Source queryQuery de origem · Collected atColetado em 2026-10-22 09:30 UTC · 120ms
-- Only waits with a clear meaning are counted; idle and background waits never reach the report.
WITH meaning (pattern, cat_en, cat_pt) AS (
SELECT * FROM (VALUES
('PAGEIOLATCH[_]%', 'Disk: reading data pages', 'Disco: leitura de páginas de dados'),
('WRITELOG', 'Disk: transaction log writes', 'Disco: escrita no log de transações'),
('IO[_]COMPLETION', 'Disk: other I/O', 'Disco: outros I/O'),
('LCK[_]M[_]%', 'Blocking: waiting for locks', 'Bloqueio: esperando locks'),
('PAGELATCH[_]%', 'Page contention in memory (often TempDB)', 'Disputa de páginas em memória (geralmente TempDB)'),
('SOS[_]SCHEDULER[_]YIELD', 'CPU pressure', 'Pressão de CPU'),
('CXPACKET', 'Parallelism', 'Paralelismo'),
('CXCONSUMER', 'Parallelism', 'Paralelismo'),
('RESOURCE[_]SEMAPHORE', 'Queries waiting for memory grants', 'Consultas esperando memória'),
('THREADPOOL', 'Out of worker threads', 'Falta de threads de trabalho'),
('ASYNC[_]NETWORK[_]IO', 'Application not reading results fast enough', 'Aplicação lendo resultados devagar'),
('HADR[_]SYNC[_]COMMIT', 'Synchronous Availability Group commit', 'Commit síncrono do Availability Group')
) v (pattern, cat_en, cat_pt)
),
c AS (
SELECT m.cat_en, MAX(m.cat_pt) AS cat_pt, SUM(ws.wait_time_ms) AS ms, SUM(ws.waiting_tasks_count) AS tasks,
MAX(ws.wait_type) AS example
FROM sys.dm_os_wait_stats ws
JOIN meaning m ON ws.wait_type LIKE m.pattern
WHERE ws.wait_time_ms > 0
GROUP BY m.cat_en
),
t AS (SELECT SUM(ms) AS total FROM c),
up AS (SELECT DATEDIFF(second, sqlserver_start_time, SYSDATETIME()) / 3600.0 AS hours FROM sys.dm_os_sys_info)
SELECT c.cat_en AS [meaning@en],
c.cat_pt AS [meaning@pt-BR],
c.example AS wait_type,
CAST(c.ms * 100.0 / t.total AS decimal(5, 1)) AS share_pct,
CAST(c.ms / 1000.0 / NULLIF(up.hours, 0) AS decimal(14, 1)) AS wait_s_per_hour,
CAST(c.ms * 1.0 / NULLIF(c.tasks, 0) AS decimal(14, 1)) AS avg_wait_ms,
CASE WHEN c.cat_en IN ('Out of worker threads', 'Queries waiting for memory grants') THEN 'confirmed' ELSE 'hint' END AS _confidence
FROM c CROSS JOIN t CROSS JOIN up
WHERE c.ms * 100.0 / t.total >= {{min_share_pct}}
AND c.ms / 1000.0 / NULLIF(up.hours, 0) >= {{min_wait_s_per_hour}}
ORDER BY c.ms DESC;
Finding 4 of 5Achado 4 de 5
· MediumMédia
HintIndício
Instance settings left at defaults that hurt performanceConfigurações da instância no padrão que prejudicam o desempenho
| setting | current_value | suggested | host |
| max server memory (MB) | 2147483647 | 26214 | 32768 MB RAM |
| cost threshold for parallelism | 5 | 50 | 16 CPUs |
What it meansO que significa
Default memory can starve the OS; default parallelism settings make small queries go parallel and fight for CPU.A memória padrão pode sufocar o sistema operacional; o paralelismo padrão faz consultas pequenas rodarem em paralelo e disputarem CPU.
Recommended actionAção recomendada
Review each setting with sp_configure, starting with max server memory. Change one at a time and observe.Revise cada configuração com sp_configure, começando pelo max server memory. Mude uma por vez e observe.
CaveatRessalva: Recommendations are common starting points, not universal rules. Hosts running other services may need different values.As recomendações são pontos de partida comuns, não regras universais. Hosts com outros serviços podem precisar de outros valores.
Source queryQuery de origem · Collected atColetado em 2026-10-22 09:30 UTC · 120ms
WITH c AS (SELECT name, CAST(value_in_use AS bigint) AS v FROM sys.configurations),
s AS (SELECT cpu_count, physical_memory_kb / 1024 AS ram_mb FROM sys.dm_os_sys_info)
SELECT 'max server memory (MB)' AS setting, CAST(c.v AS varchar(20)) AS current_value,
CAST(CAST(s.ram_mb * 0.8 AS bigint) AS varchar(20)) AS suggested, CAST(s.ram_mb AS varchar(20)) + ' MB RAM' AS host
FROM c CROSS JOIN s WHERE c.name = 'max server memory (MB)' AND c.v >= 2147483647
UNION ALL
SELECT 'max degree of parallelism', CAST(c.v AS varchar(20)), '8', CAST(s.cpu_count AS varchar(20)) + ' CPUs'
FROM c CROSS JOIN s WHERE c.name = 'max degree of parallelism' AND c.v = 0 AND s.cpu_count > {{maxdop_cpus}}
UNION ALL
SELECT 'cost threshold for parallelism', CAST(c.v AS varchar(20)), '50', CAST(s.cpu_count AS varchar(20)) + ' CPUs'
FROM c CROSS JOIN s WHERE c.name = 'cost threshold for parallelism' AND c.v = 5
UNION ALL
SELECT 'optimize for ad hoc workloads', CAST(c.v AS varchar(20)), '1', NULL
FROM c WHERE c.name = 'optimize for ad hoc workloads' AND c.v = 0;
Finding 5 of 5Achado 5 de 5
· MediumMédia
HintIndício
High-impact missing indexesÍndices ausentes de alto impacto
| database | table | equality_columns | inequality_columns | included_columns | uses | est_impact_pct | improvement | last_user_seek |
| sales | [sales].[dbo].[orders] | [customer_id] | [order_date] | [total] | 48210 | 93.4 | 1840221 | 2026-10-22 09:12 |
What it meansO que significa
The optimizer recorded queries that would run much cheaper with an index that doesn't exist. They read more pages and hold locks longer than needed.O otimizador registrou consultas que ficariam bem mais baratas com um índice que não existe. Elas leem mais páginas e seguram locks por mais tempo que o necessário.
Recommended actionAção recomendada
Treat each row as a lead, not a command. Compare it with the existing indexes on the table, merge similar suggestions and test the index before creating it in production.Trate cada linha como pista, não como ordem. Compare com os índices que já existem na tabela, junte sugestões parecidas e teste o índice antes de criar em produção.
CaveatRessalva: Always a hint. The DMV ignores existing similar indexes, suggests overlapping indexes, and is cleared on restart.Sempre um indício. A DMV ignora índices parecidos que já existem, sugere índices sobrepostos e é zerada no restart.
Source queryQuery de origem · Collected atColetado em 2026-10-22 09:30 UTC · 120ms
SELECT TOP (20)
DB_NAME(d.database_id) AS [database],
d.statement AS [table],
d.equality_columns,
d.inequality_columns,
d.included_columns,
s.user_seeks + s.user_scans AS uses,
CAST(s.avg_user_impact AS decimal(5, 1)) AS est_impact_pct,
CAST(s.avg_total_user_cost * s.avg_user_impact * (s.user_seeks + s.user_scans) AS decimal(18, 0)) AS improvement,
s.last_user_seek
FROM sys.dm_db_missing_index_details d
JOIN sys.dm_db_missing_index_groups g ON g.index_handle = d.index_handle
JOIN sys.dm_db_missing_index_group_stats s ON s.group_handle = g.index_group_handle
WHERE d.database_id > 4
AND s.avg_user_impact >= {{min_impact_pct}}
AND s.avg_total_user_cost * s.avg_user_impact * (s.user_seeks + s.user_scans) >= {{min_improvement}}
ORDER BY improvement DESC;