236 votes

Comment puis-je utiliser NSError dans mon iPhone?

Je suis en train de travailler sur la capture des erreurs dans mon application, et je suis à la recherche en utilisant NSError. Je suis un peu confus sur la façon de l'utiliser, et comment le remplir.

Quelqu'un pourrait-il donner un exemple sur la façon dont je remplir ensuite utiliser NSError?

486voto

Alex Points 21247

Eh bien, ce que j'ai l'habitude de faire mes méthodes qui pourraient erreur à l'exécution, prendre une référence à un NSError pointeur. Si quelque chose n'a en effet aller mal dans cette méthode, je peux remplir l' NSError de référence avec des données d'erreur et retourner nil à partir de la méthode.

Exemple:

- (id) endWorldHunger:(id)largeAmountsOfMonies error:(NSError**)error {
    // begin feeding the world's children...
    // it's all going well until....
    if (ohNoImOutOfMonies) {
        // sad, we can't solve world hunger, but we can let people know what went wrong!
        // init dictionary to be used to populate error object
        NSMutableDictionary* details = [NSMutableDictionary dictionary];
        [details setValue:@"ran out of money" forKey:NSLocalizedDescriptionKey];
        // populate the error object with the details
        *error = [NSError errorWithDomain:@"world" code:200 userInfo:details];
        // we couldn't feed the world's children...return nil..sniffle...sniffle
        return nil;
    }
    // wohoo! We fed the world's children. The world is now in lots of debt. But who cares? 
    return YES;
}

Nous pouvons alors utiliser la méthode comme ceci. Ne même pas la peine d'inspecter l'objet d'erreur, sauf si la méthode renvoie nil:

// initialize NSError object
NSError* error = nil;
// try to feed the world
id yayOrNay = [self endWorldHunger:smallAmountsOfMonies error:&error];
if (!yayOrNay) {
   // inspect error
   NSLog(@"%@", [error localizedDescription]);
}
// otherwise the world has been fed. Wow, your code must rock.

Nous avons été en mesure d'accéder à l'erreur de l' localizedDescription parce que nous accordons une valeur pour NSLocalizedDescriptionKey.

Le meilleur endroit pour plus d'informations est la documentation d'Apple. Il est vraiment bon.

Il ya aussi une belle, simple tutoriel sur le Cacao Est Ma petite Amie.

60voto

Wolfgang Schreurs Points 7910

Je voudrais ajouter quelques suggestions basées sur ma plus récente de la mise en œuvre. J'ai regardé un peu de code à partir d'Apple et je pense que mon code se comporte de la même manière.

Les postes ci-dessus déjà expliquer comment créer NSError objets et de les retourner, donc je ne vais pas l'embêter avec cette partie. Je vais essayer de proposer un bon moyen d'intégrer des erreurs (codes, messages) dans votre propre application.


Je vous recommande de créer 1 en-tête qui sera un aperçu de toutes les erreurs de votre nom de domaine (c'est à dire de l'app, bibliothèque, etc..). Ma tête ressemble à ceci:

FSError.h

FOUNDATION_EXPORT NSString *const FSMyAppErrorDomain;

enum {
    FSUserNotLoggedInError = 1000,
    FSUserLogoutFailedError,
    FSProfileParsingFailedError,
    FSProfileBadLoginError,
    FSFNIDParsingFailedError,
};

FSError.m

#import "FSError.h" 

NSString *const FSMyAppErrorDomain = @"com.felis.myapp";

Maintenant, avec les valeurs ci-dessus pour les erreurs, Apple va créer une certaine norme de base de message d'erreur pour votre application. Une erreur pourrait être créé comme suit:

+ (FSProfileInfo *)profileInfoWithData:(NSData *)data error:(NSError **)error
{
    FSProfileInfo *profileInfo = [[FSProfileInfo alloc] init];
    if (profileInfo)
    {
        /* ... lots of parsing code here ... */

        if (profileInfo.username == nil)
        {
            *error = [NSError errorWithDomain:FSMyAppErrorDomain code:FSProfileParsingFailedError userInfo:nil];            
            return nil;
        }
    }
    return profileInfo;
}

La norme Apple a généré le message d'erreur (error.localizedDescription) pour le code ci-dessus va ressembler à ceci:

Error Domain=com.felis.myapp Code=1002 "The operation couldn't be completed. (com.felis.myapp error 1002.)"

Le ci-dessus est déjà bien utile pour un développeur, puisque le message affiche le domaine où l'erreur s'est produite et le code d'erreur correspondant. Les utilisateurs finaux n'ont aucune idée de ce qu'est le code d'erreur 1002 signifie que, alors maintenant, nous devons mettre en œuvre certaines gentils messages pour chaque code.

Pour les messages d'erreur, nous devons garder la localisation dans l'esprit (même si nous n'avons pas de mettre en œuvre les messages de localisation). J'ai utilisé la méthode suivante dans mon projet actuel:


1) créer un strings fichier qui va contenir les erreurs. Les chaînes de fichiers sont facilement localisables. Le fichier peut ressembler à ceci:

FSError.les chaînes

"1000" = "User not logged in.";
"1001" = "Logout failed.";
"1002" = "Parser failed.";
"1003" = "Incorrect username or password.";
"1004" = "Failed to parse FNID."

2) Ajouter des macros pour convertir les codes entier les messages d'erreur. J'ai utilisé 2 macros dans mon Constantes+Macros.h fichier. J'ai toujours inclure ce fichier dans le préfixe en-tête (MyApp-Prefix.pch) pour des raisons de commodité.

Les Constantes+Macros.h

// error handling ...

#define FS_ERROR_KEY(code)                    [NSString stringWithFormat:@"%d", code]
#define FS_ERROR_LOCALIZED_DESCRIPTION(code)  NSLocalizedStringFromTable(FS_ERROR_KEY(code), @"FSError", nil)

3) Maintenant, il est facile de montrer à l'utilisateur message d'erreur convivial basé sur un code d'erreur. Un exemple:

UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Error" 
            message:FS_ERROR_LOCALIZED_DESCRIPTION(error.code) 
            delegate:nil 
            cancelButtonTitle:@"OK" 
            otherButtonTitles:nil];
[alert show];

38voto

jlmendezbonini Points 1287

Grande réponse à Alex. Un problème potentiel est le déréférencement de pointeur NUL. Apple de référence sur la Création et le Retour NSError objets

...
[details setValue:@"ran out of money" forKey:NSLocalizedDescriptionKey];

if (error != NULL) {
    // populate the error object with the details
    *error = [NSError errorWithDomain:@"world" code:200 userInfo:details];
}
// we couldn't feed the world's children...return nil..sniffle...sniffle
return nil;
...

32voto

AlBeebe Points 3273
NSError *err = [NSError errorWithDomain:@"some_domain"
                                   code:100
                               userInfo:@{
                                           NSLocalizedDescriptionKey:@"Something went wrong"
                               }];

9voto

Tirth Points 3978

Veuillez consulter en suivant le tutoriel

j'espère qu'il sera utile pour vous, mais avant vous devez lire la documentation de NSError

C'est très intéressant le lien que j'ai trouvé récemment ErrorHandling

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X