2016-05-14 34 views
2

HostingEnvironment.QueueBackgroundWorkItemで行われたバックグラウンドタスクをキャンセルする方法はありますか?HostingEnvironment.QueueBackgroundWorkItemをキャンセルする方法

タスクがキャンセルされたかどうかを通知するCancellationTokenがありますが、どうすればいいですか? https://msdn.microsoft.com/en-us/library/dd997396(v=vs.110).aspx

成功キャンセルに 参照のうえは、要求コード

OK CancellationTokenSource.Cancelメソッドを呼び出すことを必要とします。 CancellationTokenSourceへのアクセス権はどこから得ることができますか?

答えて

2

私はsoulution思い付いたいくつかの試行後:

HostingEnvironment.QueueBackgroundWorkItem(ct => 
{ 
    var linkedTokenSource = CancellationTokenSource.CreateLinkedTokenSource(ct); 
    var cancellationToken = linkedTokenSource.Token; 
    return Task.Factory.StartNew(() => 
    { 
     // do stuff on background 
    }, cancellationToken); 
}); 

を更新:確かに

、タスクは必要ありません。それをもたらすための感謝svick。 ここには、タスクなしのもう少し詳細なコードサンプルがあります。

HostingEnvironment.QueueBackgroundWorkItem(ct => 
{ 
    var linkedTokenSource = CancellationTokenSource.CreateLinkedTokenSource(ct); 
    // following is a dummy method, but you get the idea. 
    // StoreCancellationTokenSourceSoItCanBeUsedSomewhereElse(linkedTokenSource); 

    var cancellationToken = linkedTokenSource.Token; 

    try 
    { 
     while(true) 
     { 
      cancellationToken.ThrowIfCancellationRequested(); 
      // do bg stuff 
     } 
    } 
    catch (OperationCanceledException ex) 
    { 
     // either token is in cancelled state 
    } 
}); 
+0

キャンセルするには、別の「タスク」でコードを実行する必要はありません。 – svick

+0

他のオーバーロードを使用すると、シーンの後ろにタスクが作成されます。リンクされたトークンソースを作成することで、私は1つのcancallationトークンだけを管理する必要があります。 Ref:https://msdn.microsoft.com/en-us/library/system.threading.cancellationtokensource.createlinkedtokensource(v=vs.110).aspx "CancellationTokenSourceを作成します。キャンセルされた状態になるのは、ソーストークンはキャンセルされた状態になります。 – maxlego

+0

[そこに作成された「タスク」はありません](http://referencesource.microsoft.com/#System.Web/Hosting/HostingEnvironment.cs,32c143ca4ed232c1)コードが実際に実行されます)。そして、キャンセルする2つの方法を組み合わせたいのであれば、 'CreateLinkedTokenSource()'は正しい解決策です。私はそれに対して何も言いませんでした。 – svick

1

HostingEnvironment.QueueBackgroundWorkItemのシグネチャは次のとおりです。

public static void QueueBackgroundWorkItem(Action<CancellationToken> workItem) 

これは、作業項目がCancellationTokenへのアクセスを得ることを意味します。しかし、私はそれがあなたの場合に有用だとは思わない。 the documentation

提供されているCancellationTokenは、アプリケーションのシャットダウン時に通知されます。

あなたには、いくつかの他の条件に基づいてworkItemをキャンセルしたい場合は、あなたがCancellationTokenSourceから作成した別のCancellationTokenを、使用することができます。それは10秒以内に起動しない場合たとえば、作業項目をキャンセルします

var cts = new CancellationTokenSource(TimeSpan.FromSeconds(10)); 

HostingEnvironment.QueueBackgroundWorkItem(_ => 
{ 
    cts.Token.ThrowIfCancellationRequested(); 

    // the code of the work item goes here 
}); 

これは技術的にはまだCancellationTokenがキャンセルされた場合でも、作業項目を開始しますが、それは何もしません。

キャンセルは常に協力的であることに注意してください。つまり、実行中の作業項目があり、その実行中にキャンセルする場合は、定期的にCancellationTokenをチェックする必要があります。

関連する問題