Sql-Server

我可以將 tempdb 大小更改為特定值嗎?我可以在我們的生產數據庫的日常工作時間內將其縮小嗎

  • November 21, 2019

我可以將 tempdb 大小更改為特定值,並且可以在我們的生產數據庫的日常工作時間內將其縮小嗎?請告訴我它是否對生產數據庫有不良影響。

我的數據庫伺服器有 4 個核心,我使用的是 SQL Server 2008 R2 SP3。我問這個問題是因為我注意到它的大小突然變大了。我擔心它可能會使硬碟驅動器充滿。

我經常在查詢下方執行以查看是否存在頁面爭用。我總是看到一個空結果,這表明沒有頁面爭用,因此我沒有向 tempdb 添加額外的數據文件。

(SELECT session_id AS [Session],
wait_duration_ms AS [WaitTime(ms)],
resource_description AS [Type]
FROM sys.dm_os_waiting_tasks
WHERE wait_type LIKE 'PAGELATCH_%'
AND (resource_description LIKE '2:%:1'
OR resource_description LIKE '2:%:2'
OR resource_description LIKE '2:%:3')

我的 tempdb 位於本地 C 驅動器上。我只有一個數據文件。

這裡要注意多點。tempdb 應該具有與伺服器上可用的核心數相同數量的數據文件(最多 8 個)。因此,在您的情況下,它應該是 4 個數據文件,並且它們的大小應該相同,這樣您就不會發生分配爭用。KB 2154845解決了這個問題。

下面由 Brent Ozar 先生為配置 tempdb 進行解釋:

為 TempDB 配置一個卷/驅動器。將總空間除以 9,這就是您的尺寸。創建 8 個大小相同的數據文件和一個日誌文件,每個文件大小相同。Presto,驅動器已滿,您的 TempDB 已配置為易於執行。

我會堅持下面的腳本來找到等待統計的瓶頸:

WITH [Waits] AS
(SELECT
[wait_type],
[wait_time_ms] / 1000.0 AS [WaitS],
([wait_time_ms] - [signal_wait_time_ms]) / 1000.0 AS [ResourceS],
[signal_wait_time_ms] / 1000.0 AS [SignalS],
[waiting_tasks_count] AS [WaitCount],
100.0 * [wait_time_ms] / SUM ([wait_time_ms]) OVER() AS [Percentage],
ROW_NUMBER() OVER(ORDER BY [wait_time_ms] DESC) AS [RowNum]
FROM sys.dm_os_wait_stats
WHERE [wait_type] NOT IN (
N'BROKER_EVENTHANDLER', N'BROKER_RECEIVE_WAITFOR',
N'BROKER_TASK_STOP', N'BROKER_TO_FLUSH',
N'BROKER_TRANSMITTER', N'CHECKPOINT_QUEUE',
N'CHKPT', N'CLR_AUTO_EVENT',
N'CLR_MANUAL_EVENT', N'CLR_SEMAPHORE',
N'DBMIRROR_DBM_EVENT', N'DBMIRROR_EVENTS_QUEUE',
N'DBMIRROR_WORKER_QUEUE', N'DBMIRRORING_CMD',
N'DIRTY_PAGE_POLL', N'DISPATCHER_QUEUE_SEMAPHORE',
N'EXECSYNC', N'FSAGENT',
N'FT_IFTS_SCHEDULER_IDLE_WAIT', N'FT_IFTSHC_MUTEX',
N'HADR_CLUSAPI_CALL', N'HADR_FILESTREAM_IOMGR_IOCOMPLETION',
N'HADR_LOGCAPTURE_WAIT', N'HADR_NOTIFICATION_DEQUEUE',
N'HADR_TIMER_TASK', N'HADR_WORK_QUEUE',
N'KSOURCE_WAKEUP', N'LAZYWRITER_SLEEP',
N'LOGMGR_QUEUE', N'ONDEMAND_TASK_QUEUE',
N'PWAIT_ALL_COMPONENTS_INITIALIZED',
N'QDS_PERSIST_TASK_MAIN_LOOP_SLEEP',
N'QDS_CLEANUP_STALE_QUERIES_TASK_MAIN_LOOP_SLEEP',
N'REQUEST_FOR_DEADLOCK_SEARCH', N'RESOURCE_QUEUE',
N'SERVER_IDLE_CHECK', N'SLEEP_BPOOL_FLUSH',
N'SLEEP_DBSTARTUP', N'SLEEP_DCOMSTARTUP',
N'SLEEP_MASTERDBREADY', N'SLEEP_MASTERMDREADY',
N'SLEEP_MASTERUPGRADED', N'SLEEP_MSDBSTARTUP',
N'SLEEP_SYSTEMTASK', N'SLEEP_TASK',
N'SLEEP_TEMPDBSTARTUP', N'SNI_HTTP_ACCEPT',
N'SP_SERVER_DIAGNOSTICS_SLEEP', N'SQLTRACE_BUFFER_FLUSH',
N'SQLTRACE_INCREMENTAL_FLUSH_SLEEP',
N'SQLTRACE_WAIT_ENTRIES', N'WAIT_FOR_RESULTS',
N'WAITFOR', N'WAITFOR_TASKSHUTDOWN',
N'WAIT_XTP_HOST_WAIT', N'WAIT_XTP_OFFLINE_CKPT_NEW_LOG',
N'WAIT_XTP_CKPT_CLOSE', N'XE_DISPATCHER_JOIN',
N'XE_DISPATCHER_WAIT', N'XE_TIMER_EVENT')
AND [waiting_tasks_count] > 0
)
SELECT
MAX ([W1].[wait_type]) AS [WaitType],
CAST (MAX ([W1].[WaitS]) AS DECIMAL (16,2)) AS [Wait_S],
CAST (MAX ([W1].[ResourceS]) AS DECIMAL (16,2)) AS [Resource_S],
CAST (MAX ([W1].[SignalS]) AS DECIMAL (16,2)) AS [Signal_S],
MAX ([W1].[WaitCount]) AS [WaitCount],
CAST (MAX ([W1].[Percentage]) AS DECIMAL (5,2)) AS [Percentage],
CAST ((MAX ([W1].[WaitS]) / MAX ([W1].[WaitCount])) AS DECIMAL (16,4)) AS [AvgWait_S],
CAST ((MAX ([W1].[ResourceS]) / MAX ([W1].[WaitCount])) AS DECIMAL (16,4)) AS [AvgRes_S],
CAST ((MAX ([W1].[SignalS]) / MAX ([W1].[WaitCount])) AS DECIMAL (16,4)) AS [AvgSig_S]
FROM [Waits] AS [W1]
INNER JOIN [Waits] AS [W2]
ON [W2].[RowNum] <= [W1].[RowNum]
GROUP BY [W1].[RowNum]
HAVING SUM ([W2].[Percentage]) - MAX ([W1].[Percentage]) < 95; -- percentage threshold
GO

我不太確定這是否適用於 SQL Server 2008R2,因為我沒有使用此版本的任何環境。

關於您的主要問題,即填充 C 驅動器上的空間以及儲存在同一驅動器中的唯一 tempdb 設備可能會使您的數據庫損壞,並且如果使用了所有空間,您的作業系統將停止工作。因此,我建議您再添加三個相同大小的數據文件並將它們保存在不同的驅動器上,同時禁用現有設備的自動增長選項,如下所示:

Tempdb 禁用自動增長

檢查 tempdb 中實際使用了多少數據並嘗試將其縮小到一定程度(在正常情況下這不是一個好的選擇,但是您沒有太多選擇,因為我們現在不想重新啟動服務)。

完成上述步驟並且您設法在高峰時段生存後,您可能計劃讓系統停機幾分鐘,並且需要重新啟動 SQL 服務才能將第一個數據文件從 C 驅動器移動到其他驅動器。

您可以使用以下連結中給出的命令並按照步驟移動 tempdb 的數據/日誌文件:

https://blog.sqlauthority.com/2016/06/26/moving-tempdb-new-drive-interview-question-week-077/

https://www.brentozar.com/archive/2017/11/move-tempdb-another-drive-folder/

如何將 TempDB 文件移動到不同的驅動器或文件夾?

以上希望有所幫助。

每次重新啟動 MSSQL 服務時,您的 tempDB 文件都會被清空,因此您可以更改大小,但這可能不是一個好習慣。您確實需要告訴您的運營或管理團隊您需要一個單獨的驅動器,並且它不能存在於 C 驅動器上,因為它是等待發生的中斷。

理想情況下,您應該將 tempdb 文件放在單獨的驅動器上,而不是放在與作業系統相同的驅動器上。您需要作業系統驅動器,理想情況下,日誌文件、mdf 文件和臨時文件需要不同的驅動器。

至少,您應該將所有數據庫、日誌和 tempdb 文件從作業系統驅動器中取出,因為如果日誌填滿或數據庫增長,並且它填滿了驅動器,它就會崩潰。

引用自:https://dba.stackexchange.com/questions/253717