5

tengo un problema que no estoy seguro de cómo hacer frente. Puedo, sin ningún problema, realizar solicitudes al servicio REST cuando paso una sola solicitud.múltiple servicio web asíncrono pide NSURLConnection iOS

Mi problema ahora es por lo que en base a respons consigo algunos valores incluidos ID's. Todos los ID recuperados necesitarán hacer otra solicitud para recopilar nueva información.

Mi conjetura es cargar toda la solicitud específica en una matriz o diccionario y crear solicitud de eso. Alguien tiene algunos consejos útiles con respecto a esto? La información recuperada completará una UITableView.

+0

Es su requisito es algo como esto. req ---> respuesta (úsela para otra solicitud y también almacene alguna información) -> respuesta (nuevamente haga una nueva solicitud y almacene/use información) ---> respuesta ... y así sucesivamente? – Ravin

+0

Sí, pero el problema es que la primera solicitud recupera todo lo que necesito en una solicitud. Por ejemplo, recibo 20 personas, cada una con una identificación. Quiero tomar cada identificación y hacer 20 solicitudes para recuperar un horario para cada una. Lo difícil es que la primera respuesta llene una UITableView con nombres. después de cada nombre quiero poner su horario individual. No sé, esto hizo que mi problema fuera más claro. – Silversnail

Respuesta

4

le sugiero que utilice un patrón de sincronización asíncrona en este problema.

es necesario implementar dos métodos síncronos:

// Fetch the array of ID's 
-(NSArray*)fetchItemIDsWithError:(NSError**)error; 

// Fetch the item for a ID 
-(Item*)fetchItemForID:(NSString*)itemID error:(NSError**)error; 

la implementación de estas utilizando el código síncrono es fácil y comprobable. Puede utilizar métodos simples como dataWithURL…, stringWithContentsOfURL…, sendSynchronousRequest… o ASIHTTPrequest con facilidad, y escribir sencillo pruebas unitarias para esto. El código también será extremadamente fácil de mantener y ampliar, comparado con la forma en que el código concurrente generalmente termina.

Ahora con el paso dos, crear una envoltura asíncrono, me gustaría utilizar un delegado y una firma método como este:

@protocol FetchItemsDelegate <NSObject> 
-(void)didFetchItems:(NSArray*)array; 
-(void)failedFetchItemsWithError:(NSError*)error; 
@end 

-(void)fetchItemsWithAsyncDelegate:(id<FetchItemsDelegate>)delegate; 

usted ya tiene todo el código que hace lo que necesita, por lo que todo lo que tiene que hacer es impelente las partes asincrónicas. Este código se verá bien y será sencillo. Probaly no más que esto:

-(void)fetchItemsWithAsyncDelegate:(id<FetchItemsDelegate>)delegate; 
{ 
    [self performSelectorInBackground:@selector(backgroundFetchItemsWithDelegate:) 
          withObject:delegate];  
} 

-(void)backgroundFetchItemsWithDelegate:(id<FetchItemsDelegate>)delegate; 
{ 
    NSAutoreleasePool* pool = [[NSAutoreleasePool alloc] init]; 
    BOOL success = YES; 
    NSMutableArray* items = [NSMutableArray array]; 
    NSError* error = nil; 
    NSArray* itemIDs = [self fetchItemIDsWithError:&error]; 
    if (itemIDs) { 
     for (NSString* itemID in itemIDs) { 
      Item* item = [self fetchItemForID:itemID 
             error:&error]; 
      if (item) { 
       [items addObject:item]; 
      } else { 
       success = NO; 
       break; 
      } 
     } 
    } else { 
     success = NO; 
    } 
    if (success) { 
     [delegate performSelectorOnMainThread:@selector(didFetchItems:) 
            withObject:[NSArray arraiWithArray:items] 
           waitUntilDone:NO]; 
    } else { 
     [delegate performSelectorOnMainThread:@selector(failedFetchItemsWithError) 
            withObject:error 
           waitUntilDone:NO]; 
    } 
    [pool release]; 
} 

He escrito una entrada en el blog ya sobre este tema aquí:. http://blog.jayway.com/2011/04/28/sync-asyn-pair-pattern-easy-concurrency-on-ios/

+0

@PeyloW ¡Gracias por tu respuesta! Voy a darle una oportunidad. Soy bastante nuevo en Objective-C, así que si ahora tengo una clase separada que recupera la primera respuesta para llenar el conjunto de ID, ¿creo una nueva clase para estos métodos? La otra clase hace una devolución de llamada a mi viewController y luego llena el TableView. – Silversnail

+0

@Silversnail - Soy un defensor de los objetos modelo inteligentes. Entonces, si dependiera de mí, agregaría los métodos como métodos de clase en la clase 'Item'. Tal vez en una categoría para separación, en el mismo archivo de encabezado, pero opcionalmente en archivos de implementación separados si el archivo crece a 500 líneas de código o más. – PeyloW

+0

@PeyloW, creo que quizás soy un poco inexperto para saber cómo conseguiré todo esto junto, echaré un vistazo a tu blog para obtener más información. Así es como tengo mi conexión asíncrona ahora ... stackoverflow.com/questions/5975825/debugger-message – Silversnail

0

su pregunta es un poco vago, pero creo que yo pueda entender su problema. Por lo general implementar un patrón de delegado con un protocolo al hacer peticiones http:

@protocol HttpDelegate 
    -(void) httpDidFinish; 
    -(void) httpError:(NSError *) error; 
@end 

y en una clase de HttpClient:

-(void) connectionDidFinishLoading:(NSURLConnection *)connection { 
    [self.delegate httpDidFinish]; 
} 

controlador Usted (u otra clase) implementa HttpDelegate y en httpDidFinish o bien hacer la segunda solicita o completa tu tabla. En este caso, dado que este es un proceso de dos pasos, en lugar de implementar HttpDelegate en un controlador, probablemente agregaría otra clase, TwoStepProcessor y TwoStepProcessorDelegate. TwoStepProcessorDelegate es como HttpDelegate excepto que tiene:

-(void) secondStepFinished: 

que sus implementos controlador.

0

Su solución depende de su aplicación existente (estoy considerando aquí sólo dos casos.)

Caso I: If you are having a different class for managing connection related task, a separate class that has NSURLConnection Delegate methods.(Asynchronous..)

  • que se necesitan para ejecutar un bucle for para solicitar todos º e 20 Solicitud de ID con notificación de registro para ellos con ID como nombre de notificación.Cuando la conexión termine de cargarse, se publicará una notificación a su clase de observación y aquí, utilizando el nombre de la notificación, puede actualizar la programación relacionada de la ID respectiva. [aquí necesitarás crear diferentes objetos de esa clase de controlador de conexión] ... aquí deberás esperar el calendario cargando lo que puedes hacer puedes poner un indicador de actividad en la vista de acceso de la celda hasta que se cargue el calendario. (puede mostrar nombres en este caso)

caso II: If its singleton or in the same class which you are using.(we can not create it's multiple objects)..(it will have the performance cost.) one by one request.

  • Usted tendrá que enviar solicitud de uno en uno y actualizar el contenido de la celda hasta que se hace. Significa que envía la solicitud de ID 1 y, cuando llegue su respuesta, puede actualizar la celda y enviar la próxima solicitud. y así.

Será útil si nos publica cómo está manejando la actividad de conexión.

Gracias,

+0

esta es la estructura de cómo hago las conexiones. http://stackoverflow.com/questions/5975825/debugger-message – Silversnail

+0

por lo que en su celda tiene alguna vista para su pantalla de programación, UILabel o algo así? – Ravin

+0

¡Sí exactamente! UIlabel – Silversnail