Demande GET utilisant AFNetworking et sauvegarde de la réponse

Je fais une simple requête GET avec AFNetworking

AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager]; [manager GET:@"http://someapi.com/hello.json" parameters:nil success:^(AFHTTPRequestOperation *operation, id responseObject) { NSLog(@"JSON: %@", responseObject); } failure:^(AFHTTPRequestOperation *operation, NSError *error) { NSLog(@"Error: %@", error); }]; 

Une fois que j'ai fait la request, je veux pouvoir accéder à responseObject partir de n'importe quelle autre méthode de la class.

Je veux être en mesure de sauvegarder le responseObject afin que je puisse faire quelque chose comme afficher la sortie dans un tableau.

Il est courant de créer des templates d'objects qui seront représentés par JSON. Lorsque vous obtenez la réponse, vous devez ensuite parsingr datatables dans les templates. L'approche que nous utilisons consiste à renvoyer la réponse au requestur via un bloc d'achèvement. Vous n'avez pas besoin d'parsingr le JSON en objects fortement typés, mais c'est vraiment utile à long terme. C'est probablement une bonne idée de gérer également les opérations de request réseau dans une class distincte (appelée service). De cette façon, vous pouvez instancier un nouveau service et être averti par un bloc d'achèvement qu'il est terminé. Par exemple, la signature de request de votre service pourrait ressembler à ceci:

 typedef void(^HelloWorldCompletionHandler)(NSSsortingng *helloWorld, NSError *error); - (void)requestHelloWorldData:(HelloWorldCompletionHandler)completionHandler; // implementation - (void)requestHelloWorldData:(HelloWorldCompletionHandler)completionHandler { AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager]; [manager GET:@"http://someapi.com/hello.json" parameters:nil success:^(AFHTTPRequestOperation *operation, id responseObject) { id JSONResponse = [operation responseObject]; if (operation.error) { completionHandler(nil, error); } else { // parse the response to something id parserResult = [self parseJSONResponse:JSONResponse]; completionHandler(parserResult, nil); } }]; 

De cette façon, vous saurez quand la requête réseau est terminée et vous pourrez définir datatables souhaitées sur une propriété de votre class. Ensuite, vous pouvez appeler tableView.reloadData afin d'utiliser datatables de votre table.

Tout ce code irait dans une class de type de service. J'aime organiser mes services par responsabilité. Je ne sais pas combien de différents appels de données vous faites, mais nous en avons plusieurs pour notre projet. Si, par exemple, vous créez une application météo, vous pouvez potentiellement organiser par conditions actuelles, prévisions quotidiennes et prévisions horaires. Je ferais un service pour chacune de ces requests. Dites que j'ai créé un CurrentConditionsService. L'en-tête ressemblerait à ceci:

 typedef void(^CurrentConditionsCompletionHandler)(CurrentConditions *currentConditions, NSError *error); @interface CurrentConditionsService : NSObject // locationKey is some unique identifier for a city + (instancetype)serviceWithLocationKey:(NSSsortingng *)locationKey; - (void)resortingeveCurrentConditionsWithCompletionHandler:(CurrentConditionsCompletionHandler)completionHandler; @end 

Ensuite, dans mon file d'implémentation, je ferais la request et j'appellerais le gestionnaire d'achèvement donné comme je l'ai démontré ci-dessus. Ce model peut être suivi par de nombreux services différents au point où tous vos services pourraient hériter d'une class de base qui gère les parties de requête / réponse. Ensuite, vos sous-classs pourraient replace des methods spécifiques et gérer / parsingr datatables de manière appropriée en fonction du type.

Si vous utilisez la méthode d'parsing des réponses JSON dans les objects de model, tous vos parsingurs devront se conformer à un protocole. De cette façon, dans votre super class, peu importe l'implémentation concrète de votre parsingur. Vous fournissez à la super class une implémentation concrète et tout ce qu'elle sait faire, c'est invoquer l'parsingur et renvoyer la réponse.

Un exemple de protocole d'parsingur JSON ressemblerait à ceci:

 @protocol AWDataParser <NSObject> @required - (id)parseFromDictionary:(NSDictionary *)dictionary; - (NSArray *)parseFromArray:(NSArray *)array; @end 

Et l'invoquant dans votre super class de services:

 - (id)parseJSONResponse:(id)JSONResponse error:(NSError **)error { NSAssert(self.expectedJSONResponseClass != nil, @"parseResponse: expectedJSONResponseClass cannot be nil"); NSAssert(self.parser != nil, @"parseResponse: parser cannot be nil"); id parserResult = nil; if (![JSONResponse isKindOfClass:self.expectedJSONResponseClass]) { //handle invalid JSON reponse object if (error) { *error = [NSError errorWithDomain:NetworkServiceErrorDomain code:kNetworkServiceErrorParsingFailure userInfo:@{@"Invalid JSON type": [NSSsortingng ssortingngWithFormat:@"expected: %@, is: %@",self.expectedJSONResponseClass, [JSONResponse class]]}]; } } else { if (self.expectedJSONResponseClass == [NSArray class]) { parserResult = [self.parser parseFromArray:JSONResponse]; }else { parserResult = [self.parser parseFromDictionary:JSONResponse]; } if (!parserResult) { if (error) { *error = [NSError errorWithDomain:NetworkServiceErrorDomain code:kNetworkServiceErrorParsingFailure userInfo:nil]; } } } return parserResult; } 

Utilisez cette approche:

 NSURL *COMBINAT = [[NSURL alloc] initWithSsortingng:@"http://someapi.com/hello.json"]; dispatch_async(kBgQueue, ^{ NSData* data = [NSData dataWithContentsOfURL: COMBINAT]; [self performSelectorOnMainThread:@selector(savedata:) withObject:data waitUntilDone:YES]; }); 

alors appelez simplement:

 - (void)savedata:(NSData *)responseData { NSError* error; NSLog(@"Answer from server %@", responseData); // ... your code to use responseData } 

Créez simplement une propriété:

 @property(nonatomic, strong) id savedResponseObject; 

et définissez-le dans le gestionnaire de succès de la requête:

 AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager]; [manager GET:@"http://someapi.com/hello.json" parameters:nil success:^(AFHTTPRequestOperation *operation, id responseObject) { self.savedResponseObject = responseObject; } failure:^(AFHTTPRequestOperation *operation, NSError *error) { NSLog(@"Error: %@", error); }]; 

Ensuite, vous pourrez y accéder à partir d'autres endroits de votre class en vous référant à:

 self.savedResponseObject