2015-03-21 9 views
84

Es funktioniert gut, wenn eine oder zwei Aufgaben wirft jedoch eine Fehlermeldung „Es wurde eine Aufgabe abgebrochen“, wenn wir mehr als eine Aufgabe aufgeführt haben.HttpClient - Eine Aufgabe wurde abgebrochen?

enter image description here

List<Task> allTasks = new List<Task>(); 
allTasks.Add(....); 
allTasks.Add(....); 
Task.WaitAll(allTasks.ToArray(), configuration.CancellationToken); 


private static Task<T> HttpClientSendAsync<T>(string url, object data, HttpMethod method, string contentType, CancellationToken token) 
{ 
    HttpRequestMessage httpRequestMessage = new HttpRequestMessage(method, url); 
    HttpClient httpClient = new HttpClient(); 
    httpClient.Timeout = new TimeSpan(Constants.TimeOut); 

    if (data != null) 
    { 
     byte[] byteArray = Encoding.ASCII.GetBytes(Helper.ToJSON(data)); 
     MemoryStream memoryStream = new MemoryStream(byteArray); 
     httpRequestMessage.Content = new StringContent(new StreamReader(memoryStream).ReadToEnd(), Encoding.UTF8, contentType); 
    } 

    return httpClient.SendAsync(httpRequestMessage).ContinueWith(task => 
    { 
     var response = task.Result; 
     return response.Content.ReadAsStringAsync().ContinueWith(stringTask => 
     { 
      var json = stringTask.Result; 
      return Helper.FromJSON<T>(json); 
     }); 
    }).Unwrap(); 
} 
+0

Was ist die innere Ausnahme sagen? – RagtimeWilly

+0

Warum nehmen Sie einen 'CancellationToken' als Parameter und verwenden ihn nicht? –

Antwort

128

ist es 2 mögliche Gründe, dass ein TaskCanceledException geworfen würde:

  1. Etwas abgeschlossen Cancel() auf den CancellationTokenSource im Zusammenhang mit der Kündigung Token vor der Aufgabe genannt.
  2. Die Zeitüberschreitung der Anforderung, das heißt nicht innerhalb der Zeitspanne von Ihnen angegebenen auf HttpClient.Timeout abgeschlossen haben.

Meine Vermutung ist es ein Timeout war. (Wenn es eine ausdrückliche Absage ist, würden Sie wahrscheinlich herausgefunden haben, dass aus.) Sie können mehr sicher sein, durch die Ausnahme Inspektion:

try 
{ 
    var response = task.Result; 
} 
catch (TaskCanceledException ex) 
{ 
    // Check ex.CancellationToken.IsCancellationRequested here. 
    // If false, it's pretty safe to assume it was a timeout. 
} 
+3

Was ist eine mögliche Lösung? Ich habe ein ähnliches Problem. http://stackoverflow.com/questions/36937328/get-asp-net-mvc5-webapi-token-fails-sometimes?noredirect=1#comment61434357_36937328 –

+20

@Dimi - das ist ziemlich alt, aber die Lösung, die ich verwendete, war zu setzen die Timeout-Eigenschaft auf einen größeren Wert: 'httpClient.Timeout = TimeSpan.FromMinutes (30)' – RQDQ

+1

@RQDQ, du der Mann, Mann! Die Verwendung des Konstruktors löste das Problem für mich. In meinem speziellen Fall wollte ich eine Auszeit in Millisekunden. Die Verwendung von 'TimeSpan.FromMilliseconds (Configuration.HttpTimeout)' im Gegensatz zu 'new TimeSpan (Configuration.HttpTimeout)' hat sich bewährt. Vielen Dank! –

5

ich in diese Ausgabe lief, weil meine Main() Methode nicht für die Aufgabe wartet abgeschlossen ist, bevor Rückkehr, so wurde die Task<HttpResponseMessage> myTask wenn meine Konsole Programm verlassen abgebrochen.

Die Lösung war myTask.GetAwaiter().GetResult() in Main() (von this answer) zu rufen.

+0

Vielen Dank Ben, Sie haben so viel Zeit gespart. – RaM

2

Eine andere Möglichkeit ist, dass das Ergebnis nicht auf der Clientseite erwartet wird. Dies kann vorkommen, wenn eine Methode auf dem Aufruf-Stack das Schlüsselwort await nicht verwendet, um auf den Abschluss des Aufrufs zu warten.

+0

Danke Manish, das hat geholfen, meine Ausnahme zu beheben. – Gunarathinam

Verwandte Themen