WAITFOR (Transact-SQL)

指定された時間または時間間隔に達するか、指定されたステートメントによって少なくとも 1 つの行が変更または返されるまで、バッチ、ストアド プロシージャ、またはトランザクションの実行をブロックします。

トピック リンク アイコンTransact-SQL 構文表記規則

構文

WAITFOR 
{
    DELAY 'time_to_pass' 
  | TIME 'time_to_execute' 
  | [ ( receive_statement ) | ( get_conversation_group_statement ) ] 
    [ , TIMEOUT timeout ]
}

引数

  • DELAY
    バッチ、ストアド プロシージャ、またはトランザクションを実行する前に経過する必要のある、最大 24 時間までの指定された時間です。

  • 'time_to_pass'
    待機する時間の長さです。time_to_pass は、datetime データに適合するいずれかの形式で指定することも、ローカル変数として指定することもできます。日付を指定することはできません。したがって、datetime 値の日付の部分は無視されます。

  • TIME
    バッチ、ストアド プロシージャ、またはトランザクションを実行するように指定された時間です。

  • 'time_to_execute'
    WAITFOR ステートメントが終了する時間です。time_to_execute は、datetime データに適合するいずれかの形式で指定することも、ローカル変数として指定することもできます。日付を指定することはできません。したがって、datetime 値の日付の部分は無視されます。

  • receive_statement
    有効な RECEIVE ステートメントです。

    重要な注意事項重要

    receive_statement が指定された WAITFOR は、Service Broker メッセージに対してのみ適用できます。詳細については、「RECEIVE (Transact-SQL)」を参照してください。

  • get_conversation_group_statement
    有効な GET CONVERSATION GROUP ステートメントです。

    重要な注意事項重要

    get_conversation_group_statement が指定された WAITFOR は、Service Broker メッセージに対してのみ適用できます。詳細については、「GET CONVERSATION GROUP (Transact-SQL)」を参照してください。

  • TIMEOUT timeout
    キューでメッセージの到着を待機する時間を、ミリ秒単位で指定します。

    重要な注意事項重要

    TIMEOUT が指定された WAITFOR は、Service Broker メッセージに対してのみ適用できます。詳細については、「RECEIVE (Transact-SQL)」および「GET CONVERSATION GROUP (Transact-SQL)」を参照してください。

説明

WAITFOR ステートメントを実行している間は、トランザクションが実行され、その他のリクエストは同じトランザクションの下で実行することはできません。

実際の遅延時間は time_to_pass、time_to_execute、または timeout で指定される時間によって異なり、サーバーの利用状況レベルにも依存します。時間のカウンターは、WAITFOR ステートメントに関連付けられたスレッドがスケジュールされた時点から開始します。サーバーがビジーの場合、スレッドはすぐにスケジュールされない場合があります。したがって遅延時間は指定した時間よりも長くなることがあります。

WAITFOR はクエリのセマンティクスを変更しません。クエリが行を返すことができない場合、WAITFOR は待機状態のままか、TIMEOUT が指定されている場合は TIMEOUT に達するまで待機します。

WAITFOR ステートメントでは、カーソルをオープンすることはできません。

WAITFOR ステートメントでは、ビューを定義することはできません。

クエリが query wait オプションの値を超えると、WAITFOR ステートメントの引数を実行せずに完了できます。この構成オプションの詳細については、「query wait オプション」を参照してください。アクティブな待機中の処理を表示するには、sp_who を使用します。

各 WAITFOR ステートメントには、それに関連付けられたスレッドがあります。同じサーバーに多くの WAITFOR ステートメントが指定されている場合、これらのステートメントの実行を待機することを中止できます。SQL Server では、WAITFOR ステートメントに関連付けられたスレッドの数を監視し、スレッドが不足し始めるとランダムにこれらのスレッドのいくつかを選択し、終了させます。

WAITFOR ステートメントがアクセスしようとしている行セットが変更されないようにロックも設定されているトランザクション内で、WAITFOR のあるクエリを実行することにより、デッドロックを作成することができます。SQL Server では、これらのシナリオを識別し、このようなデッドロックの機会が存在する場合は、空の結果セットを返します。

A. WAITFOR TIME を使用する

次の例では、午後 10 時 20 分 (22:20) にストアド プロシージャ sp_update_job を実行します。

USE msdb;
EXECUTE sp_add_job @job_name = 'TestJob';
BEGIN
    WAITFOR TIME '22:20';
    EXECUTE sp_update_job @job_name = 'TestJob',
        @new_name = 'UpdatedJob';
END;
GO

B. WAITFOR DELAY を使用する

次の例では、ストアド プロシージャを 2 時間遅延して実行します。

BEGIN
    WAITFOR DELAY '02:00';
    EXECUTE sp_helpdb;
END;
GO

C. ローカル変数と共に WAITFOR DELAY を使用する

次の例では、WAITFOR DELAY オプションでローカル変数を使用する方法を示します。ここでは、変更可能な時間が経過するまで待機し、経過した時間の時、分、秒の長さに関する情報をユーザーに返すストアド プロシージャを作成します。

USE AdventureWorks2008R2;
GO
IF OBJECT_ID('dbo.TimeDelay_hh_mm_ss','P') IS NOT NULL
    DROP PROCEDURE dbo.TimeDelay_hh_mm_ss;
GO
CREATE PROCEDURE dbo.TimeDelay_hh_mm_ss 
    (
    @DelayLength char(8)= '00:00:00'
    )
AS
DECLARE @ReturnInfo varchar(255)
IF ISDATE('2000-01-01 ' + @DelayLength + '.000') = 0
    BEGIN
        SELECT @ReturnInfo = 'Invalid time ' + @DelayLength 
        + ',hh:mm:ss, submitted.';
        -- This PRINT statement is for testing, not use in production.
        PRINT @ReturnInfo 
        RETURN(1)
    END
BEGIN
    WAITFOR DELAY @DelayLength
    SELECT @ReturnInfo = 'A total time of ' + @DelayLength + ', 
        hh:mm:ss, has elapsed! Your time is up.'
    -- This PRINT statement is for testing, not use in production.
    PRINT @ReturnInfo;
END;
GO
/* This statement executes the dbo.TimeDelay_hh_mm_ss procedure. */
EXEC TimeDelay_hh_mm_ss '00:00:10';
GO

以下に結果セットを示します。

A total time of 00:00:10, in hh:mm:ss, has elapsed! Your time is up.