2013-04-30 13 views
6

Desidero utilizzare async/attendere quando si esegue una query su un database con una chiamata HTTP nella mia applicazione WPF. È la mia prima volta che utilizzo async/await, quindi se vedi qualche errore evidente, sentiti libero di indicarlo.Async/Await Iterate over return Task <IEnumerable <SomeClass>>

Il problema è che non sono più in grado di iterare sulla raccolta restituita, perché ora è un'attività di <IEnumerable<SomeClass>> e, da quello che ho scoperto, l'attività non implementa IEnumerable/IEnumerator.

Il mio codice è simile al seguente: Il metodo che chiama il metodo async/await.

private void AddProjectDrawingAndComponentsFromServerToLocalDbAsync(CreateDbContext1 db, Project item) 
{ 
    var drawings = client.GetDrawingsAsync(item.ProjectId); 
    ..... (waiting for GetDrawingsAsync to return, so i can iterate over the drawings) 
    db.SaveChanges(); 
} 

Il metodo GetDrawingsAsync:

public async Task<IEnumerable<Drawing>> GetDrawingsAsync(int projectId) 
{ 
    var drawings = Task.Factory.StartNew(() => _client.Get(new GetDrawingsReq() { ProjectId = projectId })); 
    return await drawings; 
} 

Torna il metodo che attende il metodo asincrono per finire:

private void AddProjectDrawingAndComponentsFromServerToLocalDbAsync(CreateDbContext1 db, Project item) 
{ 
    var drawings = client.GetDrawingsAsync(item.ProjectId); <-- The returned Task<Task<IEnumerable<Drawing>> 
    Drawing prj_drawing = null; 
    foreach (var draw in drawings) 
    { 
     prj_drawing = new Drawing() { DrawingKey = draw.DrawingKey, Name = draw.Name, ProjectId = item.ProjectId }; 
     item.AddDrawing(prj_drawing); 
     db.Projects.Add(item); 
    } 
    db.SaveChanges(); 
} 

Come vorrei essere in grado di convertire il tipo restituito Task<IEnumerable<Drawing>> a qualcosa che posso scorrere nel ciclo di foreach.

risposta

6

Per ripetere il risultato dello Task, è necessario ottenere il risultato dello Task. E per farlo, dovresti usare await. Ciò significa che dovreste cambiare AddProjectDrawingAndComponentsFromServerToLocalDbAsync() in un metodo async:

private async Task AddProjectDrawingAndComponentsFromServerToLocalDbAsync(
    CreateDbContext1 db, Project item) 
{ 
    var drawings = await client.GetDrawingsAsync(item.ProjectId); 
    foreach (var draw in drawings) 
    { 
     // whatever 
    } 
    db.SaveChanges(); 
} 

Ciò significa che AddProjectDrawingAndComponentsFromServerToLocalDbAsync() (che è BTW abbastanza un brutto nome per un metodo, credo) ora restituisce una Task, quindi probabilmente si dovrebbe cambiare il metodo che lo chiama anche in un metodo async. Questo porta a “async all the way”, ma è inevitabile.

Problemi correlati