51 votes

Imprimer les informations de trace de pile à partir de C#

Dans le cadre d'une gestion d'erreur dans notre produit, nous aimerions dump certaines informations de trace de pile. Cependant, nous faisons l'expérience que de nombreux utilisateurs vont tout simplement prendre une capture d'écran de la boîte de dialogue de message d'erreur au lieu de nous envoyer une copie du rapport complet disponible à partir du programme, et donc je voudrais faire un minimum de trace de la pile d'informations disponibles dans cette boîte de dialogue.

Un .NET trace de la pile sur ma machine ressemble à ceci:

at System.IO.__Error.WinIOError(Int32 errorCode, String maybeFullPath)
at System.IO.FileStream.Init(String path, FileMode mode, FileAccess access, Int32 rights, Boolean useRights, FileShare share, Int32 bufferSize, FileOptions options, SECURITY_ATTRIBUTES secAttrs, String msgPath, Boolean bFromProxy)
at System.IO.FileStream..ctor(String path, FileMode mode, FileAccess access, FileShare share, Int32 bufferSize, FileOptions options)
at System.IO.StreamReader..ctor(String path, Encoding encoding, Boolean detectEncodingFromByteOrderMarks, Int32 bufferSize)
at System.IO.StreamReader..ctor(String path)
at LVKWinFormsSandbox.MainForm.button1_Click(Object sender, EventArgs e) in C:\Dev\VS.NET\Gatsoft\LVKWinFormsSandbox\MainForm.cs:line 36

J'ai cette question:

Le format ressemble à ceci:

at <class/method> [in file:line ##]

Cependant, la au et en mots-clés, je suppose que ces vont être localisées, s'ils sont à court, disons, un norvégien .NET au lieu de l'anglais, je l'ai installé.

Est-il possible pour moi de prendre part à cette trace de la pile dans une langue neutre, de sorte que je peux afficher uniquement le fichier et le numéro de ligne pour les entrées qui ont ce?

En d'autres termes, je voudrais des informations à partir du texte ci-dessus:

C:\Dev\VS.NET\Gatsoft\LVKWinFormsSandbox\MainForm.cs:line 36

Tous les conseils que vous pouvez donner vous être utile.

71voto

Curt Hagenlocher Points 12432

Vous devriez être en mesure d'obtenir une StackTrace objet au lieu d'une chaîne en disant

var trace = new System.Diagnostics.StackTrace(exception);

Vous pouvez ensuite regarder les images vous-même sans s'appuyer sur le cadre de la mise en forme.

Voir aussi: StackTrace de référence

28voto

Lindholm Points 231

Voici le code que j'utilise pour ce faire sans une exception

public static void LogStack()
{
  var trace = new System.Diagnostics.StackTrace();
  foreach (var frame in trace.GetFrames())
  {
    var method = frame.GetMethod();
    if (method.Name.Equals("LogStack")) continue;
    Log.Debug(string.Format("{0}::{1}", 
        method.ReflectedType != null ? method.ReflectedType.Name : string.Empty,
        method.Name));
  }
}

18voto

Hertzel Guinness Points 2983

Juste pour que cela soit un 15 sec copier-coller la réponse:

static public string StackTraceToString()
{
    StringBuilder sb = new StringBuilder(256);
    var frames = new System.Diagnostics.StackTrace().GetFrames();
    for (int i = 1; i < frames.Length; i++) /* Ignore current StackTraceToString method...*/
    {
        var currFrame = frames[i];
        var method = currFrame.GetMethod();
        sb.AppendLine(string.Format("{0}:{1}",                    
            method.ReflectedType != null ? method.ReflectedType.Name : string.Empty,
            method.Name));
    }
    return sb.ToString();
}

(basé sur Lindholm réponse)

8voto

Aftershock Points 1602

Ou il existe même une version plus courte..

Console.Write(exception.StackTrace);

1voto

Greg Ogle Points 3964

Comme alternative, log4net, bien que potentiellement dangereux, m'a donné de meilleurs résultats que le Système.Diagnostics. En gros, dans log4net, vous avez une méthode pour les différents niveaux de journal, chacun avec un paramètre d'Exception. Donc, lorsque vous passez à la deuxième exception, il va imprimer la trace de la pile selon la appender vous avez configuré.

exemple: Logger.Error("Danger!!!", myException );

La sortie, en fonction de la configuration, ressemble à quelque chose comme

System.ApplicationException: Something went wrong.
   at Adapter.WriteToFile(OleDbCommand cmd) in C:\Adapter.vb:line 35
   at Adapter.GetDistributionDocument(Int32 id) in C:\Adapter.vb:line 181
   ...

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