2009-03-30 10 views
22

Piszę aplikację na iPhone'a, która musi pobrać dane z serwera WWW. Używam NSURLConnection do wykonania żądania HTTP, które działa dobrze, ale mam problem z testowaniem mojego kodu w przypadku, gdy odpowiedź ma kod błędu HTTP (jak 404 lub 500).Testowanie użycia NSURLConnection ze stanami błędów odpowiedzi HTTP

Używam GTM do testowania jednostkowego i OCMock do kpiny.

Gdy serwer zwraca błąd, połączenie nie wymaga connection:didFailWithError: na delegata, ale wzywa connection:didReceiveResponse:, connection:didReceiveData: i connectionDidFinishLoading: zamiast. Obecnie sprawdzam kod stanu w odpowiedzi pod numerem connection:didReceiveResponse: i dzwonię pod numer cancel, gdy kod stanu wygląda jak błąd uniemożliwiający wywołanie connectionDidFinishLoading:, w którym zgłaszana jest pomyślna odpowiedź.

Zapewnienie statycznego upięcia NSURLConnection jest proste, ale chcę, aby mój test zmienił zachowanie, gdy wywoływana jest jedna z metod fałszywego połączenia. W szczególności chcę, aby test był w stanie stwierdzić, kiedy kod wywołuje cancel na fałszywym połączeniu, więc test może przestać wywoływać connection:didReceiveData: i connectionDidFinishLoading: na delegata.

Czy istnieje sposób na sprawdzenie, czy cancel został wywołany na fałszywym obiekcie? Czy istnieje lepszy sposób testowania kodu, który używa NSURLConnection? Czy istnieje lepszy sposób na obsługę błędów HTTP?

+0

Czy mógłby Pan/Pani pokazać przykładowy kod na temat tego, jak jednostka testuje połączenia z NSURLConnection? –

Odpowiedz

43

Is there a better way to handle HTTP error statuses?

Myślę, że jesteś na dobrej drodze. Używam coś podobnego do następującego kodu, który znalazłem here:

if ([response respondsToSelector:@selector(statusCode)]) 
{ 
    int statusCode = [((NSHTTPURLResponse *)response) statusCode]; 
    if (statusCode >= 400) 
    { 
     [connection cancel]; // stop connecting; no more delegate messages 
     NSDictionary *errorInfo 
      = [NSDictionary dictionaryWithObject:[NSString stringWithFormat: 
      NSLocalizedString(@"Server returned status code %d",@""), 
      statusCode] 
             forKey:NSLocalizedDescriptionKey]; 
     NSError *statusError 
      = [NSError errorWithDomain:NSHTTPPropertyStatusCodeKey 
           code:statusCode 
          userInfo:errorInfo]; 
     [self connection:connection didFailWithError:statusError]; 
    } 
} 

ten anuluje połączenie i wywołuje connection:didFailWithError: w celu kody błędów http zachowują się dokładnie tak samo, jak każdy inny błąd połączenia.

+1

Działa świetnie. Lekki problem: 'NSHTTPPropertyStatusCodeKey' jest nieaktualny. –

+3

Możesz użyć dowolnego ciągu, na przykład @ "Błąd", zamiast NSHTTPPropertyStatusCodeKey –

+0

Tak, to nie wygląda na poprawne użycie 'NSHTTPPropertyStatusCodeKey'. Cf. odwołanie do klasy NSURL: http://developer.apple.com/library/mac/#documentation/Cocoa/Reference/Foundation/Classes/NSURL_Class/Reference/Reference.html%23//apple_ref/occ/instm/NSURL/relativePath . Ponadto, jeśli jesteś Xcode 4.4 lub nowszy, prawdopodobnie możesz skrócić kod słownika do '@ {NSLocalizedDescriptionKey: [NSHTTPURLResponse localizedStringForStatusCode: statusCode]}'. –

Powiązane problemy