2017-10-05 1 views
2

Ich habe eine Web-API und ich möchte einige Daten in einem Controller und zeigen auf einer Ansicht.So verwenden Sie eine asynchrone Aufgabe, um Daten zu erhalten und in einer Ansicht anzuzeigen?

das ist meine Hauptklasse:

public class APISrv 
{ 
    public string result = string.Empty; 
    public async Task<string> GetIT() 
    { 
     try 
     { 
      using (var client = new HttpClient()) 
      { 
       client.BaseAddress = new Uri("http://localhost:2474/"); 
       client.DefaultRequestHeaders.Clear(); 
       client.DefaultRequestHeaders.Accept.Add(new 
       MediaTypeWithQualityHeaderValue("application/json")); 

       HttpResponseMessage Res = await 
       client.GetAsync("api/Test/Get"); 

       if (Res.IsSuccessStatusCode) 
       { 
        result = Res.Content.ReadAsStringAsync().Result; 
       } 
      } 

     } 
     catch (Exception err) 
     { 
      result=err.Message; 
     } 
     return result; 
    } 
} 

ich meine Klasse mit zwei Controllern getestet:

ein:

public ActionResult Index() 
    { 
     APISrv aPISrv = new APISrv(); 
     aPISrv.GetIT(); 
     ViewData["mydata"] = aPISrv.result; 
     return View(); 
    } 

in dieser Sache "Ergebnis" ist ein öffentlicher Bereich und immer ist leer, es scheint Haupt Thread wartet nicht auf Async-Methode getan seine Arbeit.Ich kann meine Ansicht sehen, aber "ViewData [" Mydata "]" ist leer.

auf den zweiten:

public ActionResult Index() 
    { 
     APISrv aPISrv = new APISrv(); 
     ViewData["mydata"] = aPISrv.GetIT().Result; 
     return View(); 
    } 

in dieser meiner Seite Aufenthalt verursachen im Modus „für die lokale ... warten“ und nichts arbeiten.

Wie kann ich und was ist der beste Weg, um Daten aus meiner Klasse zu bekommen?

Antwort

3

Sie mischen Blockierungsaufrufe (.Result) mit async/await, was zu Deadlocks führen kann. Das ist, was Sie nicht zurück Ergebnisse erhalten, wenn Sie die Controller-Aktion aufrufen.

Referenz Async/Await - Best Practices in Asynchronous Programming

Entweder gehen async den ganzen Weg oder synchron den ganzen Weg. Versuche sie nicht zu mischen.

result = await Res.Content.ReadAsStringAsync(); 

Auch die Aktion aktualisieren async auch

public async Task<ActionResult> Index() { 
    var aPISrv = new APISrv(); 
    ViewData["mydata"] = await aPISrv.GetIT(); 
    return View(); 
} 

Zusätzlich, dass der Service sein sollte über Konstruktor Injektion werden abstrahiert und injiziert, aber das ist außerhalb des Umfangs dieser Frage.

+0

Vielen Dank für Ihre Hilfe, Ihre Codes funktionieren gut, aber können Sie mir kurz schreiben plz, wie kann ich damit umgehen, wenn ich nicht aus einem normalen Modus meinen Controller ändern möchte, ich meine mein Controller nur "ActionResult" nicht zurück "Aufgabe "? – motevalizadeh

Verwandte Themen