ربط .الصافي المصحح في حين لا يزال توفير مفيدة تسجيل الدخول الموت

StackOverflow https://stackoverflow.com/questions/211622

  •  03-07-2019
  •  | 
  •  

سؤال

أود أن يكون نوعا من التقاط كل الاستثناءات آلية في جذر قانون بلدي ، حتى عندما يكون التطبيق إنهاء بشكل غير متوقع لا يمكن أن لا تزال توفر بعض المعلومات المفيدة في قطع الأشجار.

شيء على غرار

static void Main () {
    if (Debugger.IsAttached)
        RunApp();
    else {
        try {
            RunApp();
        }
        catch (Exception e) {
            LogException(e);
            throw;
        }
    }
 }

في حين أن هذا كل شيء يعمل بشكل جيد, مشكلتي هي عندما أريد إرفاق مصحح الأخطاء بعد استثناء وقد أثيرت.

منذ استثناء يهرب إلى وقت التشغيل ويندوز موجه إلى إرفاق visual studio, إلا, منذ rethrown جميع السكان المحليين والمعلمات من فوق كومة قد فقدت.

هناك على أية حال أن سجل هذه الاستثناءات ، في حين لا يزال توفير طريقة إرفاق مصحح الأخطاء والإبقاء على جميع المعلومات المفيدة ؟

هل كانت مفيدة؟

المحلول

وأما بول بيتس التي سبق ذكرها، قد يكون من الافضل استخدام في AppDomain.UnhandledException الحدث بدلا من كتلة حاول / catch.

في الخاص بك معالج الحدث UnhandledException يمكنك تسجيل / عرض استثناء ومن ثم تقديم خيار لتصحيح مثل إظهار نموذج مع تفاصيل الاستثناء وأزرار تجاهل والتصحيح أو الإقلاع عن التدخين.

إذا قام المستخدم بتحديد خيار التصحيح، استدعاء System.Diagnostics.Debugger.Break () الذي يسمح للمستخدم إرفاق أيا كان المصحح يريدون مع مكدس الاستدعاءات الكامل لا تزال متاحة.

من الواضح، هل يمكن تعطيل هذا الخيار لأي يبني كنت تعرف أنك لا من أي وقت مضى ستكون إرفاق مصحح الأخطاء.

class Program
{
    static void Main()
    {
        AppDomain.CurrentDomain.UnhandledException += ExceptionHandler;

        RunApp();
    }

    static void ExceptionHandler(object sender, UnhandledExceptionEventArgs e)
    {
        Console.WriteLine(e.ExceptionObject);
        Console.WriteLine("Do you want to Debug?");
        if (Console.ReadLine().StartsWith("y"))
            Debugger.Break();
    }

    static void RunApp()
    {
        throw new Exception();
    }
}

نصائح أخرى

فظيعة المباراة ولكن دون السنانير وقت (أنا أعرف من لا شيء) الطريقة الوحيدة للوصول إلى إطار مكدس حيث كنت رمي من....

جميع الاستثناءات التي هي معروفة لتكون محطة القيت أن يكون لديك التالية في منشئ:

#if DEBUG
System.Diagnostics.Debugger.Launch()
#endif

هذا من شأنه أن يقدم الحوار مما يتيح للمستخدم إما التوريد ذات الصلة المصحح أو اختيار أي و التصحيح سوف تحدث (في كلتا الحالتين استثناء سوف تنتهي يجري بناؤها ثم يتم طرح.ومن الواضح أن هذا يعمل فقط على الاستثناءات التي يمكنك التحكم.

أنا لا أوصي هذا في التصحيح بناء مع إرفاق مصحح الأخطاء فقط يمكنك أن تختار للحصول على أول فرصة' كسر على استثناء رمي والتي عادة تكون كافية لتلبية الاحتياجات الخاصة بك.

خيار آخر هو أن تبدأ في توليد صغيرة مقالب برمجيا في الاستثناء رمي مواقع هذه البيانات ومن ثم يمكن تفتيشها في وقت لاحق مع أداة مثل windbg ولكن لا تتداخل كثيرا مع السلوك المطلوب من الاستثناء الفك المكدس بعد.

قانون الاستثناء إلى التقاط كل فخ هو بالضبط كومة الاسترخاء كنت لا تريد, آسف.إذا كنت مرتاحا مع C++ و يتوهم أنه يمكنك بناء الصغرى (ولكن معقدة للحصول على حق) شوكة أحادية الذي تسبب في كل الاستثناءات الزناد المصحح.بدلا من ذلك فقط بناء أحادية هو BCL استثناء فئة أن تفعل الشيء نفسه كما هو مفصل أعلاه..

لماذا لا مجرد السماح لها تحطم ثم قم بالتسجيل لتلقي تقارير خطأ ويندوز من مايكروسوفت؟ تحقق من http://msdn.microsoft.com/en-us/isv/ bb190483.aspx للحصول على التفاصيل.

إذا كنت لا تريد أن تفعل ذلك، يمكنك استخدام وظيفة IsDebuggerPresent (<لأ href = "http://msdn.microsoft.com/en-us/library/ms680345.aspx" يختلط = "نوفولو noreferrer "> http://msdn.microsoft.com/en-us/library/ms680345.aspx )، وإذا كانت النتيجة هي كاذبة، بدلا من التفاف التعليمات البرمجية في محاولة اللحاق، إضافة إلى معالج الحدث الحدث AppDomain.UnhandledException ( http://msdn.microsoft. كوم / EN-US / مكتبة / system.appdomain.unhandledexception.aspx )

ولا ينبغي ببساطة القيام

Exception e1 = e;
LogException(e);
throw(e1);

وداخل الصيد تفعل خدعة (على الأقل يمكنك فحص استثناء الخارجي)؟

إذا كنت تستخدم بدقة وضع التصحيح لتطوير وإطلاق سراح وضع للنشر، قد تتمكن من محاولة استخدام فئة System.Diagnostics.Debugger.

catch (Exception e) {
#if DEBUG
            System.Diagnostics.Debugger.Launch()
#endif
            LogException(e);
            throw;
        }

ويمكنك الحصول على معلومات الاستثناء عن طريق الكتابة في سجل التتبع:

        private static void Main(string[] args)
    {
        try
        {
            // ...
        }
        catch (Exception exception)
        {
            System.Diagnostics.Trace.Write(exception);
            #if DEBUG
            System.Diagnostics.Trace.Write("Waiting 20 seconds for debuggers to attach to process.");
            System.Threading.Thread.Sleep(20000);
            System.Diagnostics.Trace.Write("Continue with process...");
            #endif
            throw;
        }
    }

استخدم DebugView لعرض سجل التتبع. ووقف الموضوع لبضع ثوان تعطيك بعض الوقت لإرفاق المصحح لعملية دون فقدان استثناء الأصلي.

وإذا كان أي من الأحداث العالمية ينجح في مسعاه، ثم ما يمكن أن محاولة يضع الصيد خطأ في أي أحداث مقابض البرنامج. سهولة هذه تعتمد على تعقيد التطبيقات الخاصة بك. وكتب العديد من التطبيقات مكتوبة مع صافي الإطار لمعالجة الأحداث سواء كان هو تطبيق التقليدية أو تطبيق ويب. من خلال وضع السنانير في الأحداث نفسها يجب أن تكون قادرة على الحفاظ على المعلومات في كومة التي تحتاج إليها.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top