نمایش نتایج 1 تا 6 از 6

نام تاپیک: مدیریت خطاها و استثنائات (Exception) و نمایش پیام مناسب با توجه به خطای رخ داده در دلفی

  1. #1
    کاربر دائمی آواتار M_Maskout
    تاریخ عضویت
    اسفند 1387
    محل زندگی
    تهران
    سن
    45
    پست
    150

    Lightbulb مدیریت خطاها و استثنائات (Exception) و نمایش پیام مناسب با توجه به خطای رخ داده در دلفی

    مقدمه
    شیئ Application، ویژگی‌ها، متدها و وقفه‌های جالبی داره که به کمک اونا می‌شه خیلی از مدیریت‌ها رو روی کل برنامه انجام داد.
    مثلاً برای فارسی کردن کیبورد، هرچند می‌شه از کد زیر استفاده کرد

    LoadKeyboardLayout('00000429', KLF_ACTIVATE);

    اما همینطور می‌شه از ویژگی BiDiKeyboard بصورت

    Application.BiDiKeyboard := '00000429';

    استفاده کرد. یا مثلاً متدهای ProcessMessages و HandleMessage که برای جلوگیری از قفل شدن کنسول برنامه و یا حتی کل ویندوز در زمان اجرای حلقه‌ها بسیار مفیدن.
    یکی از کارهایی می‌شه با شیء Application انجام داد، مدیریت خطاهای کل برنامه توسط متد OnException از این شیئه. اصولاً اینکار (مدیریت خطاها) برای اجرای هر چه روان‌تر برنامه لازمه و به عقیده من باید انجام بشه. مخصوصاً تو برنامه‌های فارسی مدیریت خطاهای پیش بینی نشده علاوه بر روانتر شدن محیط کاربری، برنامه رو حرفه‌ای‌تر و قابل استفاده‌تر می‌کنه. به شکل زیر توجه کنید:

    1.PNG

    ".tblTemp: Missing TableName property"؛ شاید حتی دوستان کاملاً حرفه‌ای هم نتونن به درستی تشخیص بدن که این پیام از چه شرایطی نشأت گرفته.
    این خطا در زمانی پیش اومده که من می‌خواستم یه Table رو باز کنم در حالیکه اتصال اون به بانک اطلاعاتی برقرار نشده.

    ADOConnection.Connected := False;
    tblTemp.Active := True;

    پر واضحه که از متن پیام چنین مطلبی برداشت نمی‌شه. حالا پیام زیر رو در نظر بگیرین

    2.PNG

    در اینجا علاوه بر اینکه می‌شه از یه MessageBox کاملاً شخصی استفاده کرد، می‌تونید پیام مناسب رو به فارسی نشون بدین، حتی با کمی صرف وقت بیشتر و به منظور داشتن کنترل بیشتر می‌شه نام Tabel، نام یا caption فرمی که خطا در اون اتفاق افتاده و یا خیلی چیزای دیگه رو به کاربر نشون داد.
    در نظر بیارین زمانی رو که برنامه رو به یه کاربر تو یه شهر دیگه دادین، بعد یه روز با شما تماس می‌گیره و پیام اول رو می‌خونه؛ قطعاً چندتا مشکل رو باید پشت سر بذارین تا بشه یه کم به اون راهنمایی بدین. (کاربر، توان خوندن انکلیسی نداره، کامپیوتر هم بلد نیست، غرورش هم اجازه نمی‌ده از کس دیگه‌ای همونجا کمک بگیره و ...). ولی پیام دوم رو به راحتی می‌تونه بفهمه، حتی با یه آموزش نیم بند، شاید بتونه مشکلات اینچنینی بعدی رو هم رفع کنه.
    دوستانی که با QBasic و همینطور نسخه‌های حرفه‌ای‌تر بعدی اون (مثلاً Quick Basic و یا VB6) آشنایی دارن، می‌دونن که توی این زبان با استفاده از دستور
    ON ERROR GOTO line-number
    می‌شه به راحتی خطاهای پیش بینی نشده رو مدیریت کرد. اما دلفی هم ابزارهای بسیار قدرتمندی برای این منظور داره. هرچند به نظر من حتی QBasic هم این کار رو بسیار روان‌تر انجام می‌ده ولی با داشتن دانش و تسلط کافی روی دلفی، مدیریت خطاها (در کل برنامه) کار خیلی ساده و جذابی خواهد بود.
    ---------------------------------------------------------------------
    برای مدیریت خطاهای پیش بینی نشده در برنامه، لازمه یه روتین برای وقفه‌ی OnException از شیء Application بنویسین و توی اون روتین، خطاهای پیش اومده در کل برنامه رو مدیریت کنین. در اینجا دست شما برای کنترل انواع خطا در زمان رویدار اون باز هست.
    مثلاً در وقفه FormCreate از فرم اصلی برنامه دستور

    Application.OnException := MyException;

    رو قرار بدین بعد هم روتین MyException رو در ادامه به عنوان یکی از متدهای همین فرم تعریف کنین. یه چیزی مثل این:
     
    TfrmMainForm = class(TForm)
    procedure FormCreate(Sender: TObject);
    procedure MyException(Sender: TObject; E: Exception);
    end;

    procedure TfrmMainForm.FormCreate(Sender: TObject);
    begin
    Application.OnException := MyException;
    end;

    procedure TfrmMainForm.MyException(Sender: TObject; E: Exception);
    begin
    ShowMessage(E.Message);
    end;


    از پارامتر E برای تشخیص نوع خطا می‌تونید استفاده کنین. وقتی خطایی در برنامه رخ می‌ده، دلفی یه فرزند از کلاس TObject می‌سازه و خطای بوجود اومده رو با اون نمایش می‌ده.
    با استفاده از پارامتر E و تبدیل اون به کلاس ساخته شده‌ی توسط دلفی، می‌شه خطای بوجود اومده رو مدیریت کرد.
    در اینجا اگر بجای دستور

    ShowMessage(E.Message);

    از دستور

    ShowMessage(E.Message+' ('+E.ClassName+')');

    استفاده بشه، در زمان بروز خطا، عبارت داخل پرانتز در MessageBox نمایش داده شده، نام کلاس خطا نمایش داده می‌شه.
    خطاها یا استثنائات در دلفی چند دسته هستند. که من در اینجا به تعداد از اونا اشاره می‌کنم و از سایر دوستان خواهش می‌کنم علاوه بر اعلام اشکالات متن حاضر، مطالب جا افتاده و تکمیلی رو در این تاپیک بیان کنند.
    ضمناً در ادامه واژه استثنا معادل خطا به کار رفته و این به دلیل این هست که دلفی از کلمه Exception استفاده می‌کنه.
    استثنائات ریاضی:
    استثنائاتی که در زمان عملیات ریاضی بوجود میان. مثل تقسیم بر صفر این استثنائات عبارتند از:
    EDivByZero : (علت وقوع) تقسیم یک عدد صحیح بر صفر.
    ERangeError : (علت وقوع) عدد مورد نظر از دامنه‌ی تعریف شده خارج است (out of range).
    EIntOverflow : (علت وقوع) سرریزی (overflow) در عملیات بر روی عدد صحیح.
    EZeroDivide : (علت وقوع) تقسیم یک عدد حقیقی (اعشاری) بر صفر.

    استثنائات ورودی / خروجی:
    EInOutError : (علت وقوع) اشکال در عملیات I/O.
    در این نوع از استثنا می‌شه بوسیله ویژگی ErrorCode کنترل بیشتری بر روی خطای بوجود آمده انجام داد.
    لیست کدهای خطاهای I/O خارج از حوصله این بحثه.

    استثنائات پایگاه داده:
    EDatabaseError : تمامی خطاهای مربوط به دسترسی به پایگاه داده را پوشش می‌دهد.
    ------------------------------------------------------------
    برای مطالعه بیشتر به تاپیک زیر سری بزنین:
    https://barnamenevis.org/showthread.p...l=1#post761790
    آخرین ویرایش به وسیله M_Maskout : جمعه 12 فروردین 1390 در 20:01 عصر

  2. #2
    کاربر دائمی
    تاریخ عضویت
    دی 1387
    محل زندگی
    تهران
    پست
    106

    نقل قول: مدیریت خطاها و استثنائات (Exception) و نمایش پیام مناسب با توجه به خطای رخ داده در دلفی

    این تاپیک هم بحث مختصری در این باره شده:
    https://barnamenevis.org/showthread.p...A7%D9%85%D9%87

  3. #3

    نقل قول: مدیریت خطاها و استثنائات (Exception) و نمایش پیام مناسب با توجه به خطای رخ داده در دلفی

    ".tblTemp: Missing TableName property"؛ شاید حتی دوستان کاملاً حرفه‌ای هم نتونن به درستی تشخیص بدن که این پیام از چه شرایطی نشأت گرفته.
    این خطا در زمانی پیش اومده که من می‌خواستم یه Table رو باز کنم در حالیکه اتصال اون به بانک اطلاعاتی برقرار نشده.
    البته در مثال مناقشه نیست، ولی پیامی که اونجا داده شده، بارها از پیامی که شما به کاربر نمایش دادید، از نظر فنی با ارزش تر هست. اون پیام داره میگه که دستور SQL ایی که شما برای موتور بانک اطلاعاتی ارسال کردید، فاقد پارامتر الزامی نام جدول هست. با همچین پیامی برنامه نویس اگر از کوئری استفاده کرده باشه، مستقیما میره سراغ SQL نوشته شده، و اگر از کلاس های Table استفاده کرده باشه، نام جدولی که دیتاست بهش متصل هست را چک میکنه.

    دوستانی که با QBasic و همینطور نسخه‌های حرفه‌ای‌تر بعدی اون (مثلاً Quick Basic و یا VB6) آشنایی دارن، می‌دونن که توی این زبان با استفاده از دستور
    ON ERROR GOTO line-number
    می‌شه به راحتی خطاهای پیش بینی نشده رو مدیریت کرد. اما دلفی هم ابزارهای بسیار قدرتمندی برای این منظور داره. هرچند به نظر من حتی QBasic هم این کار رو بسیار روان‌تر انجام می‌ده ولی با داشتن دانش و تسلط کافی روی دلفی، مدیریت خطاها (در کل برنامه) کار خیلی ساده و جذابی خواهد بود.
    چیزی که شما در دلفی دارید، فراتر از یک مکانیزم ساده لاگ کردن خطا هست؛ و بهش Structural Exception Handling (یا به طور اختصار SEH) گفته میشه که خودش یک مبحث پیچیده و پیشرفته در برنامه نویسی هست. ساختارهای try-finally و try-except در دلفی یک مکانیزم سلسله مراتبی برای تشخیص Exception و ارسال آن به ساختارهای بالاتر فراهم می کنند. در هر مرحله بلوک های کنترلی امکان هندل کردن اون Exception رو دارند، و اگر Exception ایی هندل نشه، نهایتا به شی Application میرسه. اما اگر هندل بشه، چیزی به Application نخواهد رسید، مگر اینکه کدی که اون رو هندل کرده، دوباره اون رو raise کنه.

    رویدادی مثل Application.OnException برای Log کردن ابتدایی Exception های هندل نشده، میتونه مناسب باشه. البته برای Log های حرفه ایی و درست و حسابی که بشه برای دیباگ ازشون استفاده کرد، نیاز به مکانیزم های پیچیده تری هست، که در ابزارهایی مثل MadException یا EurekaLog پیاده سازی شدند.


    وَ سَيَعْلَمُ الَّذِينَ ظَلَمُوا [آل محمد حقهم] أَيَّ مُنْقَلَبٍ يَنْقَلِبُونَ - الشعراء (227)
    و ظالمین [حق آل محمد (ص) ] به زودی خواهند دانست که به کدام بازگشتگاه بازخواهند گشت.

  4. #4
    کاربر دائمی
    تاریخ عضویت
    دی 1387
    محل زندگی
    تهران
    پست
    106

    نقل قول: مدیریت خطاها و استثنائات (Exception) و نمایش پیام مناسب با توجه به خطای رخ داده در دلفی

    مدیریت استثنا در دلفی بسیار خوب پیاده سازی شده. تنها ایرادش نبود بلوک try..except..finally هست که در زبانهای دات نت داریم. تنها فایده ای که فارسی سازی پیام های استثنا داره اینه که کاربر وحشت نمی کنه. چون به اشتباه گمان می کنه که شما پیاده سازی کدهای مربوط به ایجاد پیغام رو انجام دادید و این یک چیز مدیریت شده از جانب شماست و از این جهت کمی حرفه ای تر هست
    روش فارسی سازی پیغام های استثنای ایجاد شده توسط خود دلفی در من توی اون لینک قبلی گذاشتم. از اون بهره بگیرید و دست به رویداد OnException و قسمت except بلوک try..except..end نیازید. کاربرد این رویداد رو آقای کشاورز در پست پیشین به درستی بیان کردند. وانگهی دستکاری و ناقص کردن اطلاعات ارائه شده توسط پیغام خطا بدست شما می تونه از حل باگ هایی که خود کاربران بهش بر می خورند را ناممکن کنه.

  5. #5
    کاربر دائمی آواتار M_Maskout
    تاریخ عضویت
    اسفند 1387
    محل زندگی
    تهران
    سن
    45
    پست
    150

    نقل قول: مدیریت خطاها و استثنائات (Exception) و نمایش پیام مناسب با توجه به خطای رخ داده در دلفی

    نقل قول نوشته شده توسط علی کشاورز مشاهده تاپیک
    چیزی که شما در دلفی دارید، فراتر از یک مکانیزم ساده لاگ کردن خطا هست؛ و بهش Structural Exception Handling (یا به طور اختصار SEH) گفته میشه که خودش یک مبحث پیچیده و پیشرفته در برنامه نویسی هست. ساختارهای try-finally و try-except در دلفی یک مکانیزم سلسله مراتبی برای تشخیص Exception و ارسال آن به ساختارهای بالاتر فراهم می کنند. در هر مرحله بلوک های کنترلی امکان هندل کردن اون Exception رو دارند، و اگر Exception ایی هندل نشه، نهایتا به شی Application میرسه.
    در تأیید نوشته‌های آقای کشاورز به یه نکته از کتاب پر ارزش Mastering Delphi 7 نوشته آقای مارکو کانتو اشاره می‌کنم. ایشون تو فصل دوم کتاب، در پایان بخش Program Flow and the" finally Block" (روند برنامه و بلاک finally) این طور نوشتن:

    Handling the exception is generally much less important than using finally blocks, because Delphi can survive most exceptions. Too many exception-handling blocks in your code probably indicate errors in the program flow and possibly a misunderstanding of the role of exceptions in the language.

    "کار کردن با استثنائات معمولاً کم اهمیت‌تر از استفاده از بلاک‌های finally می‌باشد. زیرا دلفی می‌تواند از بیشتر استثنائات جان سالم به در برد. تعداد زیاد مدیریت استثنائات در کد شما، احتمالاً نشان دهنده خطاها در روند برنامه و نیز شاید به خاطر درک نادرست از نقش استثنائات در این زبان می‌باشد."
    با این وجود یه تعداد دیگه‌ای از استثنائات رو در اینجا لیست می‌کنم:

    Exception: Base class
    EAbort: Abort without dialog
    EAbstractError: Abstract method error
    AssertionFailed: Assert call failed
    EBitsError: Boolean array error
    ECommonCalendarError: Calendar calc error
    EDateTimeError: DateTime calc error
    EMonthCalError: Month calc error
    EConversionError: Raised by Convert
    EConvertError: Object convert error
    EDatabaseError: Database error
    EExternal: Hardware/Windows error
    EAccessViolation: Access violation
    EControlC: User abort occured
    EExternalException: Other Internal error
    EIntError: Integer calc error
    EDivByZero: Integer Divide by zero
    EIntOverflow: Integer overflow
    ERangeError: Out of value range
    EMathError: Floating point error
    EInvalidArgument: Bad argument value
    EInvalidOp: Inappropriate operation
    EOverflow: Value too large
    EUnderflow: Value too small
    EZeroDivide: Floating Divide by zero
    EStackOverflow: Severe Delphi problem
    EHeapException: Dynamic memory problem
    EInvalidPointer: Bad memory pointer
    EOutOfMemory: Cannot allocate memory
    EInOutError: IO error
    EInvalidCast: Object casting error
    EInvalidOperation: Bad component op
    EMenuError: Menu item error
    EOSError: Operating system error
    EParserError: Parsing error
    EPrinter: Printer error
    EPropertyError: Class property error#
    EPropReadOnly: Invalid property access
    EPropWriteOnly: Invalid property access
    EThread: Thread error
    EVariantError: Variant problem


    این هم لینک دانلود کامپوننت‌های jcl و JVCL (غیر مستقیم و با حجم تقریباً Mb‏ 19.5)، ابزاری برای مدیریت استثائات در برنامه‌ی اجرایی
    http://jaist.dl.sourceforge.net/proj...-Build3845.zip
    برای دریافت اطلاعات در مورد این کامپوننت به پست زیر نگاه کنید:
    https://barnamenevis.org/showthread.p...l=1#post615322

  6. #6
    کاربر دائمی آواتار M_Maskout
    تاریخ عضویت
    اسفند 1387
    محل زندگی
    تهران
    سن
    45
    پست
    150

    نقل قول: مدیریت خطاها و استثنائات (Exception) و نمایش پیام مناسب با توجه به خطای رخ داده در دلفی

    تو چندتا پست از تاپیک زیر، مطالب خیلی جالبی در مورد مدیریت خطا تو دلفی نوشته شده:

    https://barnamenevis.org/showthread.p...=1#post1241420

    با تشکر فراوان از دوستان عزیز a_mosavian و علی کشاورز

برچسب های این تاپیک

قوانین ایجاد تاپیک در تالار

  • شما نمی توانید تاپیک جدید ایجاد کنید
  • شما نمی توانید به تاپیک ها پاسخ دهید
  • شما نمی توانید ضمیمه ارسال کنید
  • شما نمی توانید پاسخ هایتان را ویرایش کنید
  •