這一段時間,因為系統升級,新系統產生的數據長度,比原來的數據長度要長,所以說要擴充一下字段長度。
alter table TableName alter column ColumnName varchar(50) --修改字段長度sql
在執行的時候,有這樣一個情況。
例如Student表的Name字段長度是nvarchar(50),
假如想變成nvarchar(100),這種情況,立刻能執行成功。
假如想變成nvarchar(20),這種情況,會執行很久。
有一些表沒啥問題,但是有一個表數據量較大,差不多有1億多,執行時間太長,還把所有數據表給鎖住了(如下圖)。不過這種情況數據還能用語句查詢。
①我就查詢出這個語句的spid。之后kill掉。
SELECT session_id, r.status, r.start_time, r.command, s.text, r.wait_time, r.cpu_time, r.total_elapsed_time, r.reads, r.writes, r.logical_reads, r.transaction_isolation_level FROM sys.dm_exec_requests r CROSS APPLY sys.dm_exec_sql_text(r.sql_handle) s WHERE R.STATUS='running'
kill 75
②但是連續kill了好幾遍,依然沒啥效果,還是提示鎖住。所有就繼續看下spid為75的狀態。
方法1:
select spid, blocked,waittime,lastwaittype,dbid,last_batch,open_tran,hostprocess,cmd from sysprocesses where spid = 75
方法2:
USE master; GO EXEC sp_who '75' --指定process_id;
兩種方法查詢出來的都是KILLED/ROLLBACK,表示,現在數據在回滾。
③查詢一下,數據的回滾狀態。
KILL 75 WITH STATUSONLY;
查了一下,這個情況要等好久,有的等兩三天的都有,最好的解決辦法無非是重啟。
----------------------------------------------------解決辦法------------------------------------------------
網上找了好久,找了找到了一篇結決辦法。
1.查詢出處於阻塞的sql線程。

SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED SELECT db_id(DB_NAME(er.[database_id])) [DBID] ,er.[session_id] AS [SessionID] ,er.[command] AS [CommandType] ,est.[text] [StatementText] ,er.[status] AS [Status] ,CONVERT(DECIMAL(5, 2), er.[percent_complete]) AS [Complete_Percent] ,CONVERT(DECIMAL(38, 2), er.[total_elapsed_time] / 60000.00) AS [ElapsedTime_m] ,CONVERT(DECIMAL(38, 2), er.[estimated_completion_time] / 60000.00) AS [EstimatedCompletionTime_m] ,er.[last_wait_type] [LastWait] ,er.[wait_resource] [CurrentWait] FROM sys.dm_exec_requests AS er INNER JOIN sys.dm_exec_sessions AS es ON er.[session_id] = es.[session_id] CROSS APPLY sys.dm_exec_sql_text(er.[sql_handle]) est WHERE er.[command] like 'Killed%'
附:查詢出正在執行的語句

SELECT spid, blocked, DB_NAME(sp.dbid) AS DBName, program_name, waitresource, lastwaittype, sp.loginame, sp.hostname, a.[Text] AS [TextData], SUBSTRING(A.text, sp.stmt_start / 2, (CASE WHEN sp.stmt_end = -1 THEN DATALENGTH(A.text) ELSE sp.stmt_end END - sp.stmt_start) / 2) AS [current_cmd] FROM sys.sysprocesses AS sp OUTER APPLY sys.dm_exec_sql_text (sp.sql_handle) AS A WHERE spid > 50 ORDER BY blocked DESC, DB_NAME(sp.dbid) ASC, a.[text];
2.查到spid是75,根據spid查詢出來系統進程hostprocess為20540。

select spid, blocked,waittime,lastwaittype,dbid,last_batch,open_tran,hostprocess,cmd from sysprocesses where spid = 69
3.在執行這條語句的機器上,用cmd命令查詢出來。
tasklist|findstr 進程號
如:tasklist|findstr 75
4.cmd中根據進程名稱殺死進程
taskkill /f /t /im 進程名稱
如:taskkill /f /t /im /svchost.exe
如果不行,只有等,或者重啟了。
參考文章:1.SQL Server會話KILL不掉,一直處於KILLED /ROLLBACK狀態情形淺析
3.百度 谷歌 新浪 執行 SQL 出現 Lock request time out period exceeded.
---------------------------------------------------------------------
歷史消耗
SELECT TOP 20 total_worker_time/1000 AS [總消耗CPU 時間(ms)],execution_count [運行次數], qs.total_worker_time/qs.execution_count/1000 AS [平均消耗CPU 時間(ms)], last_execution_time AS [最后一次執行時間],max_worker_time /1000 AS [最大執行時間(ms)], SUBSTRING(qt.text,qs.statement_start_offset/2+1, (CASE WHEN qs.statement_end_offset = -1 THEN DATALENGTH(qt.text) ELSE qs.statement_end_offset END -qs.statement_start_offset)/2 + 1) AS [使用CPU的語法], qt.text [完整語法], qt.dbid, dbname=db_name(qt.dbid), qt.objectid,object_name(qt.objectid,qt.dbid) ObjectName FROM sys.dm_exec_query_stats qs WITH(nolock) CROSS apply sys.dm_exec_sql_text(qs.sql_handle) AS qt WHERE execution_count>1 ORDER BY total_worker_time DESC