55 votes

iOS crash log catch, debug info.. Attrapez et envoyez par e-mail à l'équipe de développement.

Récemment, nous avons rencontré une situation où nous voulions voir les informations de débogage de l'application qu'un utilisateur a sur son appareil. Donc, ce que je cherche est un moyen de trouver le journal sur l'appareil, le coller comme texte en ligne sur un mail et permettre à l'utilisateur de l'envoyer

Des idées ? Voici à nouveau les questions.. 1)Trouvez un journal de débogage sur l'appareil 2)Ouvrez le fichier et attachez le contenu du fichier en tant que texte en ligne dans le mail. 3)Permettre à l'utilisateur de l'envoyer par email au prochain lancement de l'application

Merci,

1 votes

ITunes le fait en fait automatiquement pour vous. Vérifiez votre compte iTunes-Connect.

67voto

AppvolutionTech Points 1496

Merci pour toutes vos contributions. J'ai regroupé vos solutions en une seule qui résoudrait mon problème Voici ce que j'ai fait pour être Bien sûr, je n'ai pas compilé le code, c'est un code à moitié cuit mais je vais le repasser bientôt une fois que je l'ai mis en œuvre dans mon code

NSLog dans un fichier Comment enregistrer NSLog dans un fichier LOG2FILE

#if TARGET_IPHONE_SIMULATOR == 0    
    NSArray *paths =  
    NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask, YES);        
    NSString *documentsDirectory = [paths objectAtIndex:0];    
    NSString *logPath = [documentsDirectory stringByAppendingPathComponent:@"console.log"];    
    freopen([logPath cStringUsingEncoding:NSASCIIStringEncoding],"a+",stderr);
#endif

Capturez le crash et enregistrez-les également dans un fichier.

Tout d'abord, créez une fonction qui traitera l'erreur et l'affichera dans la console (ainsi que tout ce que vous voulez en faire) :

void uncaughtExceptionHandler(NSException *exception) {    
    NSLog(@"CRASH: %@", exception);      
    NSLog(@"Stack Trace: %@", [exception callStackSymbols]);    
    // Internal error reporting
}

Ensuite, ajoutez le gestionnaire d'exception au délégué de votre application :

-(BOOL)application:(UIApplication*)application didFinishLaunchingWithOptions:  
(NSDictionary*)launchOptions
{   
    NSSetUncaughtExceptionHandler(&uncaughtExceptionHandler);    // Normal launch stuff
}

Définissez une variable dans info.plist appelée Crashed et lisez/écrivez-la de cette façon

- (void)readPlist
 {
      NSString *localizedPath = [[NSBundle mainBundle] pathForResource:fileName ofType:@"plist"];        
      NSMutableDictionary* plistDict = [[NSMutableDictionary alloc] initWithContentsOfFile:localizedPath];

    NSString *crashed;
    crashed = [plistDict objectForKey:@"Crashed"];
}

- (void)writeToPlist
{
    NSMutableDictionary* plistDict = [[NSMutableDictionary alloc] initWithContentsOfFile:filePath];

    [plistDict setValue:@"YES" forKey:@"Crashed"];
    [plistDict writeToFile:filePath atomically: YES];
}

Une fois l'application lancée, lisez le fichier info.plist et demandez à l'utilisateur de soumettre les journaux de bord

{
    MFMailComposeViewController *mailComposer = [[MFMailComposeViewController alloc] init];
    mailComposer.mailComposeDelegate = self;[mailComposer setSubject:@"Crash Log"];
    // Set up recipients
    NSArray *toRecipients = [NSArray arrayWithObject:@"first@example.com"]; 
    [mailComposer setToRecipients:toRecipients];
    // Attach the Crash Log..
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *documentsDirectory = [paths objectAtIndex:0];
    NSString *logPath = [documentsDirectory stringByAppendingPathComponent:@"console.log"];
    NSData *myData = [NSData dataWithContentsOfFile:logPath];
    [mailComposer addAttachmentData:myData mimeType:@"Text/XML" fileName:@"Console.log"];
    // Fill out the email body text
    NSString *emailBody = @"Crash Log";
    [mailComposer setMessageBody:emailBody isHTML:NO];
    [self presentModalViewController:mailComposer animated:YES];
}

0 votes

Ça marche bien, merci. J'ai ajouté le code de la fonction Mail dans une méthode distincte et je l'appelle depuis un bouton qui permet à l'utilisateur d'envoyer le journal de débogage par courriel. Vous devez ajouter la fonction didFinishWithResult dans le contrôleur de messagerie pour fermer la vue modale et revenir à l'application.

0 votes

NSString *localizedPath = [[NSBundle mainBundle] pathForResource:fileName ofType:@"plist"] ; - en fait, vous NE POUVEZ PAS sauvegarder les données dans plist dans mainBundle. utilisez donc le dossier documents

1 votes

Une solution intéressante. Pourquoi essayer d'écrire dans plist, alors que vous pourriez utiliser NSUserDefaults ?

52voto

Kerni Points 8104
  1. Pour enregistrer vos propres données, utilisez Cocoalumberjack . Il est beaucoup plus rapide que NSLog et peut être activé/désactivé dynamiquement. Il offre également la possibilité d'enregistrer les données dans un fichier. NSLog ralentira votre application et remplira le journal de la console. De plus, vous ne voulez pas trop loguer en général. Vous ne pouvez pas faire de journalisation en toute sécurité lorsque le crash se produit. Donc, une fois que vous avez déterminé où se situe le problème, ajoutez un peu plus de journalisation à cet endroit et essayez de le reproduire, par exemple en utilisant des cadres de tests automatisés comme KIF .

  2. Pour capturer le rapport de crash, vous ne devez rien d'autre qu'une solution basée sur le framework open source. PLCrashReporter qui peut en toute sécurité attrape les plantages, même lorsque l'application est déjà dans l'app store ! Il n'est pas recommandé d'attraper les exceptions comme le suggèrent d'autres personnes. cet article pour voir pourquoi !

    iTunes Connect vous offre également la possibilité de consulter certains rapports d'accident, mais il faut compter jusqu'à deux semaines pour en voir certains, mais pas tous, comme l'a fait remarquer par exemple la Les développeurs de Camera+ . Vous devez donc utiliser votre propre solution.

    PLCrashReporter vous enverra des rapports de crash au format standard apple, prêts à être symbolisés, afin que vous sachiez où le crash se produit dans votre code, y compris les numéros de ligne.

    Voici quelques solutions basées sur PLCrashReporter :

    • QuincyKit : Client Open Source + serveur php, regroupement basique des crashs, symbolisation peut être automatisé depuis votre mac (je suis le développeur de ceci).
    • HockeyApp : Service payant, utilise le client QuincyKit, regroupement avancé des crashs, symbolisation entièrement réalisée sur le serveur (je suis l'un des développeurs de ce service).
    • Bugsense : Service gratuit, pas de symbole
    • AppBlade : Service GRATUIT s'il est utilisé avec 25 appareils ou moins, sans symbolisation.
    • Crashlytics : Bêta privée, fonctionnalités inconnues, leur solution semble être basée sur PLCrashReporter
  3. Les solutions proposées permettent d'envoyer les données automatiquement au prochain démarrage ou en demandant à l'utilisateur s'il accepte de les envoyer.

0 votes

BugSense propose actuellement la symbolisation sur l'appareil.

0 votes

@Kerni comment faites-vous la symbolisation automatique sur votre machine (doit-elle être un Mac) avec QuincyKit ?

0 votes

@Roberto Oui, il faut que ce soit un mac. QuincyKit a un script de symbolisation modifié, un agent de lancement, etc. fourni. Consultez le fichier read me pour savoir comment le configurer : github.com/TheRealKerni/QuincyKit/blob/develop/README.markdown

5voto

Maudicus Points 4513

Il s'agit d'une solution qui capture les crashs au fur et à mesure qu'ils se produisent, elle donnera des informations sur le code plus lisibles par l'homme qu'un journal de crash. Il manquera une partie du journal de bord, mais comme le dit Till, vous devriez être capable d'y accéder de toute façon.

Une autre question de l'OS sur le fait que Xcode 4.2 revient toujours à main en cas de plantage. La réponse utilise cette méthode et vous pouvez l'étendre pour garder la trace des plantages.

implémenter votre propre gestionnaire d'exception dans l'AppDelegate

// on load
NSSetUncaughtExceptionHandler(&uncaughtExceptionHandler);

void uncaughtExceptionHandler(NSException *exception) {
    NSLog(@"CRASH: %@", exception);
    NSLog(@"Stack Trace: %@", [exception callStackSymbols]);
    // Internal error reporting
}

MISE À JOUR J'ai fait quelques recherches et cette solution a été proposée par Zane Claes à la question suivante Le débogage de Xcode 4.2 ne symbolise pas l'appel de pile

Il propose une solution générale dans son deuxième commentaire. "Je trouve qu'il est utile d'écrire le journal de crash dans un fichier et d'inviter l'utilisateur à le soumettre au prochain lancement (en mode release uniquement, pour ne pas gêner le débogage). Cela me permet d'obtenir d'excellents rapports de bogues... et les utilisateurs savent que leur problème est pris en compte". Je comprends que tout le monde ne souhaite pas demander cela à l'utilisateur, mais il y a des super utilisateurs qui seraient heureux de donner un coup de main.

Vous pouvez bien sûr inclure un bouton "Ne plus jamais me montrer cette invite" afin que les gens ne soient pas frustrés par le mécanisme de signalement.

Alternativement, Vous pouvez contacter un serveur avec les informations (je ne suis pas sûr que cela fonctionne car il se bloque, mais sauvegardez-le et essayez de temps en temps d'envoyer un message POST à un serveur avec les détails).

0 votes

+1 bon à savoir :-) mais Jacob n'obtiendra pas le contenu du fichier journal avant le crash.

3voto

Jeff Points 31

J'ai utilisé Crittercisme pour automatiser cela pour moi. Cela fonctionne aussi bien pour les tests que pour la production.

1voto

Nick Toumpelis Points 1755

BugSense fournit des services de signalement de pannes pour iOS. Outre la fourniture d'une trace de pile entièrement symbolisée, BugSense fournit des analyses pour vos pannes, dans toutes vos applications.

Je pense que c'est mieux que l'email, car lorsque votre application devient populaire, vous devrez gérer tous ces emails manuellement, alors que BugSense le fait automatiquement. Cependant, BugSense est également open-source, donc vous pouvez modifier ses internes comme vous le souhaitez et ajouter toute fonctionnalité supplémentaire.

En plus de ça, vous nous faites travailler pour vous gratuitement : Si vous avez une idée de nouvelle fonctionnalité intéressante à nous proposer, nous la réaliserons, à condition que nous la trouvions intéressante nous aussi.

Avis de non-responsabilité : J'écris le code pour BugSense-iOS.framework.

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