Risoluzione dei problemi relativi al ripristino accelerato del database
Si applica a: SQL Server 2019 (15.x) Database SQL di Azure Istanza gestita di SQL di Azure
Questo articolo consente agli amministratori di diagnosticare i problemi relativi al ripristino accelerato del database in SQL Server 2019 (15.x) e versioni successive, Istanza gestita di SQL di Azure e database SQL di Azure.
Esaminare l'archivio versioni permanenti (PVS)
Sfrutta la DMV sys.dm_tran_persistent_version_store_stats per identificare se le dimensioni del PSV di ripristino accelerato del database (ADR) stanno crescendo più del previsto e quindi per determinare quale fattore impedisce la pulizia dell'archivio versioni permanenti (PVS).
Nello script di esempio seguente è inclusa la colonna sys.dm_tran_persistent_version_store_stats.pvs_off_row_page_skipped_oldest_aborted_xdesid
, che è stata aggiunta in SQL Server 2022 (16.x) e contiene il numero di pagine ignorate per il recupero a causa delle transazioni interrotte meno recenti. Se la pulizia della versione è lenta o invalidata, questo rifletterà il numero di pagine da conservare per le transazioni interrotte.
La query di esempio mostra tutte le informazioni sui processi di pulizia e mostra la dimensione attuale del PVS, la transazione meno recente interrotta e altri dettagli:
SELECT
db_name(pvss.database_id) AS DBName,
pvss.persistent_version_store_size_kb / 1024. / 1024 AS persistent_version_store_size_gb,
100 * pvss.persistent_version_store_size_kb / df.total_db_size_kb AS pvs_pct_of_database_size,
df.total_db_size_kb/1024./1024 AS total_db_size_gb,
pvss.online_index_version_store_size_kb / 1024. / 1024 AS online_index_version_store_size_gb,
pvss.current_aborted_transaction_count,
pvss.aborted_version_cleaner_start_time,
pvss.aborted_version_cleaner_end_time,
dt.database_transaction_begin_time AS oldest_transaction_begin_time,
asdt.session_id AS active_transaction_session_id,
asdt.elapsed_time_seconds AS active_transaction_elapsed_time_seconds,
pvss.pvs_off_row_page_skipped_low_water_mark,
pvss.pvs_off_row_page_skipped_min_useful_xts,
pvss.pvs_off_row_page_skipped_oldest_aborted_xdesid -- SQL Server 2022 only
FROM sys.dm_tran_persistent_version_store_stats AS pvss
CROSS APPLY (SELECT SUM(size*8.) AS total_db_size_kb FROM sys.database_files WHERE [state] = 0 and [type] = 0 ) AS df
LEFT JOIN sys.dm_tran_database_transactions AS dt
ON pvss.oldest_active_transaction_id = dt.transaction_id
AND
pvss.database_id = dt.database_id
LEFT JOIN sys.dm_tran_active_snapshot_database_transactions AS asdt
ON pvss.min_transaction_timestamp = asdt.transaction_sequence_num
OR
pvss.online_index_min_transaction_timestamp = asdt.transaction_sequence_num
WHERE pvss.database_id = DB_ID();
Controlla le dimensioni di
pvs_pct_of_database_size
, nota eventuali differenze rispetto alle previsioni e confrontale con i valori di riferimento durante altri periodi di attività dell'applicazione. L'archivio versioni permanente è considerato grande se le sue dimensioni sono significativamente maggiori rispetto a quelle di base o se è prossimo al 50% delle dimensioni del database. Utilizza i seguenti passaggi come aiuto per la risoluzione dei problemi di un PVS di grandi dimensioni.Le transazioni attive e a esecuzione prolungata in qualsiasi database in cui è abilitata la replica automatica del database possono impedire la pulizia del PVS. Recuperare
oldest_active_transaction_id
e verificare se la transazione è stata attiva per un tempo lungo eseguendo una query susys.dm_tran_database_transactions
in base all'ID della transazione. Verificare la presenza di transazioni attive e a esecuzione prolungata con una query simile all'esempio seguente, che dichiara le variabili per impostare le soglie per la durata o l'importo del log:DECLARE @longTxThreshold int = 1800; --number of seconds to use as a duration threshold for long-running transactions DECLARE @longTransactionLogBytes bigint = 2147483648; --number of bytes to use as a log amount threshold for long-running transactions SELECT dbtr.database_id, transess.session_id, transess.transaction_id, atr.name, sess.login_time, dbtr.database_transaction_log_bytes_used, CASE WHEN getdate() >= dateadd(second, @longTxThreshold, tr.transaction_begin_time) then 'DurationThresholdExceeded' WHEN dbtr.database_transaction_log_bytes_used >= @longTransactionLogBytes then 'LogThresholdExceeded' ELSE 'unknown' END AS Reason FROM sys.dm_tran_active_transactions AS tr INNER JOIN sys.dm_tran_session_transactions AS transess on tr.transaction_id = transess.transaction_id INNER JOIN sys.dm_exec_sessions AS sess on transess.session_id = sess.session_id INNER JOIN sys.dm_tran_database_transactions AS dbtr on tr.transaction_id = dbtr.transaction_id INNER JOIN sys.dm_tran_active_transactions AS atr on atr.transaction_id = transess.transaction_id WHERE transess.session_id <> @@spid AND ( getdate() >= dateadd(second, @longTxThreshold, tr.transaction_begin_time) OR dbtr.database_transaction_log_bytes_used >= @longTransactionLogBytes );
Dopo aver identificato le sessioni, prendere in considerazione l'eliminazione della sessione, se consentito. Esaminare anche l'applicazione per determinare la natura delle transazioni attive problematiche.
Per altre informazioni sulla risoluzione dei problemi relativi alle query a esecuzione prolungata, vedere:
La pulizia della versione persistente potrebbe essere bloccata a causa di una lunga scansione attiva snapshot. Le istruzioni che usano l'isolamento dello snapshot read committed (RCSI) o i livelli di isolamento SNAPSHOT ricevono timestamp a livello di istanza. Un'analisi snapshot usa il timestamp per decidere la visibilità delle righe per la transazione RCSI o SNAPSHOT nel PVS in cui è abilitato il ripristino accelerato del database. Ogni istruzione che utilizza RCSI ha un proprio timestamp, mentre l'isolamento SNAPSHOT ha un timestamp a livello di transazione. Questi timestamp delle transazioni a livello di istanza vengono utilizzati anche nelle transazioni su un solo database, perché la transazione può essere promossa a transazione su più database. Le scansioni istantanee possono quindi impedire la pulizia dei record nel PVS del ripristino accelerato del database o, quando questo non è presente, nell'archivio delle versioni
tempdb
. Pertanto, a causa di questo rilevamento della versione, le transazioni in esecuzione prolungata che utilizzano SNAPSHOT o RCSI possono far ritardare la pulizia del database dell'istanza da parte del PVS del ripristino accelerato del database, causando la crescita delle dimensioni di quest'ultimo.Nella query originale di risoluzione dei problemi nella parte superiore di questo articolo, il valore
pvs_off_row_page_skipped_min_useful_xts
mostra il numero di pagine ignorate per il recupero a causa di un'analisi snapshot lunga. Sepvs_off_row_page_skipped_min_useful_xts
mostra un valore più grande del normale, significa che è presente un'analisi snapshot lunga che impedisce la pulizia di PVS.Questa query di esempio può essere usata per decidere quale è la sessione problematica:
SELECT snap.transaction_id, snap.transaction_sequence_num, session.session_id, session.login_time, GETUTCDATE() as [now], session.host_name, session.program_name, session.login_name, session.last_request_start_time FROM sys.dm_tran_active_snapshot_database_transactions AS snap INNER JOIN sys.dm_exec_sessions AS session ON snap.session_id = session.session_id ORDER BY snap.transaction_sequence_num asc;
Per evitare ritardi nella pulizia di PVS:
- Prendere in considerazione l'eliminazione della sessione di transazioni attiva prolungata che ritarda la pulizia di PVS, ove possibile. Le transazioni con esecuzione prolungata in qualsiasi database in cui è abilitato il ripristino accelerato del database possono ritardare la pulizia di PVS del ripristino accelerato del database.
- Ottimizzare le query a esecuzione prolungata per ridurre la durata delle query e i blocchi necessari. Per altre informazioni e indicazioni, vedere Comprendere e risolvere i blocchi in SQL Server o Comprendere e risolvere i problemi di blocco del database SQL di Azure.
- Esaminare l'applicazione per determinare la natura dell'analisi snapshot attiva problematica. Prendere in considerazione un livello di isolamento diverso, come READ COMMITTED, invece di SNAPSHOT o READ COMMITTED SNAPSHOT per le query a esecuzione prolungata che ritardano la pulizia dell'ADR PVS. Questo problema si verifica più frequentemente con il livello di isolamento SNAPSHOT.
- Questo problema può verificarsi in SQL Server, Istanza gestita di SQL di Azure e nei pool elastici dei database SQL di Azure, ma non nei database SQL di Azure singleton. Nei pool elastici dei database SQL di Azure, prendi in considerazione l'idea di spostare dal pool elastico i database che hanno query a esecuzione prolungata che utilizzano i livelli di isolamento READ COMMIT SNAPSHOT o SNAPSHOT.
Quando le dimensioni del PVS crescono a causa di transazioni in esecuzione prolungata sulle repliche primarie o secondarie, analizza le query a esecuzione prolungata e individua il collo di bottiglia. La DMV
sys.dm_tran_aborted_transactions
mostra tutte le transazioni interrotte. Per altre informazioni, consultare sys.dm_tran_aborted_transactions (Transact-SQL). La colonnanest_aborted
indica che è stato eseguito il commit della transazione, ma sono presenti parti interrotte (punti di salvataggio o transazioni annidate) che possono bloccare il processo di pulizia PVS.Se il database fa parte di un gruppo di disponibilità, controllare
secondary_low_water_mark
. Questo valore corrisponde a quello dilow_water_mark_for_ghosts
restituito dasys.dm_hadr_database_replica_states
. Eseguire una query susys.dm_hadr_database_replica_states
per verificare se una delle repliche conserva questo valore perché anche in questo caso viene impedita la pulizia dell'archivio versioni permanente. La pulizia della versione viene bloccata a causa di query di lettura su repliche secondarie leggibili. Sia SQL Server locale che il database SQL di Azure supportano repliche secondarie leggibili. Nella DMVsys.dm_tran_persistent_version_store_stats
,pvs_off_row_page_skipped_low_water_mark
può anche fornire indicazioni di un ritardo di replica secondaria. Per altre informazioni, vedere sys.dm_tran_persistent_version_store_stats.La soluzione è uguale a quella dell'analisi snapshot. Passare ai database secondari, individuare la sessione che esegue la query prolungata e prendere in considerazione l'eliminazione della sessione, se consentita. Da notare che il blocco secondario non influisce solo sulla pulizia della versione del ripristino accelerato del database, ma può anche impedire la pulizia dei record fantasma.
Controllare
min_transaction_timestamp
(oonline_index_min_transaction_timestamp
se l'archivio versioni permanente online impedisce l'operazione) e quindi controllare insys.dm_tran_active_snapshot_database_transactions
la colonnatransaction_sequence_num
per individuare la sessione con la transazione snapshot precedente che impedisce la pulizia dell'archivio versioni permanente.Se non si applica alcuna delle opzioni precedenti, significa che la pulizia viene impedita da transazioni interrotte. Controllare gli orari di
aborted_version_cleaner_last_start_time
eaborted_version_cleaner_last_end_time
più recenti per verificare se la pulizia della transazione interrotta è stata completata. Il valore dioldest_aborted_transaction_id
aumenta dopo il completamento della pulizia della transazione interrotta. Se èoldest_aborted_transaction_id
molto inferiore aoldest_active_transaction_id
ecurrent_abort_transaction_count
ha un valore maggiore, esiste una transazione interrotta precedente che impedisce la pulizia PVS. Per risolvere il problema:- Ove possibile, interrompere il carico di lavoro per consentire alla versione di pulizia di progredire.
- Ottimizzare il carico di lavoro per ridurre l'utilizzo dei blocchi a livello di oggetto.
- Esaminare l'applicazione per visualizzare eventuali problemi di interruzione delle transazioni elevati. Deadlock, chiavi duplicate e altre violazioni dei vincoli possono innescare un'alta percentuale di interruzioni.
- Se si tratta di SQL Server, disabilitare il ripristino accelerato del database come operazione di sola emergenza per controllare le dimensioni del PVS e il numero di transazioni interrotte. Vedere Disabilitare la funzionalità di ripristino accelerato del database.
Se la transazione interrotta non è stata completata di recente, controllare se nel log degli errori sono presenti messaggi che segnalano problemi di tipo
VersionCleaner
.Monitorare il log degli errori di SQL Server per trovare le voci 'PreallocatePVS'. Se sono presenti voci "PreallocatePVS", significa che potrebbe essere necessario aumentare la capacità dell'ADR di preallocare le pagine per le attività in background, in quanto le prestazioni possono migliorare quando il thread in background dell'ADR prealloca un numero sufficiente di pagine e la percentuale di allocazioni PVS in primo piano è prossima a 0. È possibile utilizzare
sp_configure 'ADR Preallocation Factor'
per aumentare questo importo. Per altre informazioni, vedere Opzione di configurazione del server del fattore di preallocazione ADR.
Avviare manualmente il processo di pulizia PVS
L'ADR non è consigliato per gli ambienti di database con un elevato numero di transazioni di aggiornamento/eliminazione, come ad esempio gli OLTP ad alto volume, senza un periodo di riposo/recupero per il processo di pulizia del PVS per recuperare spazio.
Per attivare manualmente il processo di pulizia PVS tra carichi di lavoro o durante le finestre di manutenzione, usare la stored procedure di sistema sys.sp_persistent_version_cleanup.
EXEC sys.sp_persistent_version_cleanup [database_name];
ad esempio:
EXEC sys.sp_persistent_version_cleanup [WideWorldImporters];
Acquisire gli errori di pulizia
A partire da SQL Server 2022 (16.x), SQL Server registra il comportamento di pulizia dell'ADR PVS nel log degli errori di SQL Server. In genere questo comporta la registrazione di un nuovo evento di log ogni 10 minuti.
Vedi anche
- sys.sp_persistent_version_cleanup
- sys.dm_tran_persistent_version_store_stats
- sys.dm_tran_aborted_transactions