Question How To Handle This Exception

mzeezee

Member
Joined
Jan 29, 2013
Messages
5
Programming Experience
1-3
Dear Friends


I am trying to use EXCEPTION HANDLING for the first time. I have used the following code in my program:


VB.NET:
        Dim checkvalue As Boolean = False
        Try
            checkvalue = SaveImOrder()
            checkvalue = SaveImOrderDetails()
        Catch ex As Exception When checkvalue = False
            Exit Sub
        End Try
        (Rest of the code)


In above mentioned functions I am actually saving records in tables and in case of any error returning "FALSE" back here ... Then I need to catch this FALSE value to exit SUB .... However the code is not working and I am unable to track my mistake .. Please help or advice something better


Best Regards


ZEE
 
That's not an exception. The fact that a variable is set to False is not an exception. It's just that a variable has been set to False. How do you usually test the value of a variable? With an If statement.

By the way, I hope that you're saving that data within a single transaction? You should not allow an order to be saved without its detail. If the first step succeeds and the second fails, what is someone to think when they look in the database and see an order with no detail?
 
In Exception Handling what I think we can create our own exceptions which I did here .. I am performing a task and then passing a TRUE/FALSE to a variable and then checking it as an exception to do the needful. I think it should work.

If the second step fails then I can handle the logic , may be by deleting its control from database. Below please find code of "SaveImOrder" Function:

Private Function SaveImOrder() As Boolean
Dim checkvalue As Boolean = False
SetOrderValues() 'Setting values in objects' variables
checkvalue = ObjOrder.Insert_Record()
Return checkvalue
End Function
 
code is not working
How is is not working for you? What did you expect and what actually happened?

In general you have a Catch-When, this means it will not catch exceptions if When expression is False.
If the function calls in Try block throws an exception they will not return any value, thus checkvalue will not be set for that call.
This implies if first call returns True checkvalue will be set, if then second call throws the exception is not caught. If first call throws it will be caught because that is the initial value for checkvalue variable.

Whether a method should throw an exception when it fails, or itself handle possible exceptional conditions and return a Boolean, is a design decision. In general a method should throw exception if it can't complete. Try for example web search "return boolean or throw exception" to find some discussions about this. In your case 'save order' sounds like something that can either complete or not, and should throw exception and not return any Boolean. One of the reason for this is that a Boolean value says nothing about why the method failed. The opposite case is if you can say it is just as normal and expected for the method to not complete, and the caller/user would never need to know why (apart from checking log later), you could then also add 'Try' to the method name - 'TrySaveOrder' for example, here the result could be yes/no for completion (a Boolean).
Similar for methods that may return objects, try searching: "return nothing or throw exception" - this is an easier decision since it could be valid to return a 'not found' value or 'empty list' and such, but such method may still encounter problems completing and should then throw exception.
 
Jmcilhinney is correct, this is not an exception if you know you may get a false value and you have logic to apply when this happens. The best thing would be after to the two saves to add an If checkvalue = False Then.... and handle this case.

If for some reason you still really want to generate an exception, within the If checkvalue = False Then block you could use Throw New Exception. Note you can change this Exception to a more specific .NET exception or your own custom exception. But again, this doesn't really make sense. Throwing exceptions can also cause performance issues so I would recommend only using them as safety nets to catch unexpected issues.
 
In every procedure you write, structure it as follows. This provides general purpose exception handling for every circumstance. TextBox1 is a TextBox object created in Windows Forms Designer.

Private Sub MyProcedure()
    Try
    '
    ' Your code here
    '
    Exit Sub

Catch ex As Exception
    TextBox1.AppendText(ex.ToString)
    Exit Sub
End Sub
 
In every procedure you write, structure it as follows. This provides general purpose exception handling for every circumstance. TextBox1 is a TextBox object created in Windows Forms Designer.

Private Sub MyProcedure()
    Try
    '
    ' Your code here
    '
    Exit Sub

Catch ex As Exception
    TextBox1.AppendText(ex.ToString)
    Exit Sub
End Sub
Although it may seem like a good idea, that is actually quite bad advice. You should certainly not add an arbitrary exception handler to every method you write. You should only ever be handling specific exceptions that you know can reasonably occur and you should only be wrapping the affected blocks in the handler, which will often not be an entire method body. If you can't anticipate a specific exception then how can you possibly know what needs to be done to allow your application to safely proceed? What if an outOfMemoryException is thrown? Is your app just going to go blindly ahead and keep having the same exception thrown over and over but never doing anything about it?

General exception handling should be done with a global exception handler, which means handling the UnhandledException event in a VB.NET application. You can then log as much information as possible and shut down the app, which is the only genuinely safe course of action under those circumstances. If you don't know what went wrong then how can you possibly proceed with confidence? To do so might compound the problem and possibly lead to data corruption.
 
In every procedure you write, structure it as follows. This provides general purpose exception handling for every circumstance. TextBox1 is a TextBox object created in Windows Forms Designer.
That's basically how not to do it according to this: Exception Handling
When you write 'Try' and press Enter you get a default catch for System.Exception, you're supposed to replace that with something meaningful.
There are also some similar thoughts in Exception Class (System) down in 'Performance Considerations'.
 
@jmcilhinney@

Well I agree in part. However when a new application is in its initial stages of development and test, all sorts of unforeseen things can happen. My policy has certainly been to write code to "defend" against every exception that has been generated while the application has been in development and test prior to roll-out. Despite my own extensive testing, I cannot possible foresee every situation that may arise in advance, whereas with your experience perhaps you can?

I still think that general advice to someone with less experience than you is: to provide generic and simple exception handling in the first instance until the application reaches the stage of maturity that exceptions are no longer thrown. In the early days of deployment, my application requests the user to contact me by phone or email if an app exception message is ever reported, and provide to me the "screen scraped" content of TextBox1, which is a complete progress log of everything the user has done in the current working session.

This provides an "adequate" support mechanism in a company that can afford only one developer/ tester, and where typically a 10,000 LOC development has to be completed in a month and then rolled out to meet an urgent business need.

You said:

If you can't anticipate a specific exception then how can you possibly know what needs to be done to allow your application to safely proceed? What if an outOfMemoryException is thrown? Is your app just going to go blindly ahead and keep having the same exception thrown over and over but never doing anything about it?

Your statement is quite defamatory. It assumes (a) the developer provides no testing/ debugging to remove such exceptions, (b) there is no ongoing support mechanism in place, (c) the developer has the foresight of a God in predicting every exception that might be thrown, and (d) that the entire Microsoft .NET 4.5 run time library is bug-free.

If you genuinely do believe that you can anticipate every exception situation that might arise, then I challenge you to write either an Ole-based or an Odbc-based VB.NET routine to write a Data Table of any field size and field type and generate an .xlsx file that will load into Excel without crashing Excel. It must work with any version of Excel that accepts .xlsx files, and must not use Office Automation. I will certainly be glad to "test" your code, and I wager any amount you choose to place on the table that I can provide you with a DataTable that will cause your code and/or the Microsoft Odbc driver to generate a succession of unhandled and unforeseen exceptions, or which will cause Excel to crash when it receives the resulting file. Oh, and the development has to be ready for me to test by Tuesday 6th Feb.
 
@JohnH@

Almost every reference example on Microsoft's web site is like this, containing a simple "catch all" exception handler. Why would Microsoft write example code and supply it as "samples" when it flies in the face of their "advice" elsewhere?

And if the developer budget is limited where do you stop? What happens below if e.g. the file system is full? What happens if there is a memory overflow or memory failure? What happens if the processor overheats? What happens if there is a mains or battery failure that occurs in the middle of the Directory being created but before the System.IO task has completed? ...

DirectoryInfo Class (System.IO)

Imports System
Imports System.IO

Public Class Test
    Public Shared Sub Main()
        ' Specify the directories you want to manipulate. 
        Dim di As DirectoryInfo = New DirectoryInfo("c:\MyDir")
        Try 
            ' Determine whether the directory exists. 
            If di.Exists Then 
                ' Indicate that it already exists.
                Console.WriteLine("That path exists already.")
                Return 
            End If 

            ' Try to create the directory.
            di.Create()
            Console.WriteLine("The directory was created successfully.")

            ' Delete the directory.
            di.Delete()
            Console.WriteLine("The directory was deleted successfully.")

        Catch e As Exception
            Console.WriteLine("The process failed: {0}", e.ToString())
        End Try 
    End Sub 
End Class

 
Why would Microsoft write example code and supply it as "samples" when it flies in the face of their "advice" elsewhere?
Um, because it's an example. I write examples and use names like TextBox1 and Button1 when I would never do so in production code or recommend that anyone else do so either.

I don't think that you've read my post very carefully. I never said that I or anyone else could or would be able to anticipate every possible exception and I specifically stated that that's why you should have a global exception handler. That will catch any exceptions that you haven't specifically accounted for and allow you to log appropriate information and exit gracefully.

What you're espousing is the exact opposite of how you should implement exception handling. Rather than starting with exception handling everywhere you should have it nowhere, except in places that you know immediately could throw an exception, in which case you should handle that exception specifically. You then go about your business and test your code and it will crash when an exception is thrown. At that point you examine the code that threw the exception and decide what to do about it. If you can reasonably prevent the exception then you do so and if you can't then you add an appropriate exception handler, again for that exception specifically
 
@jmcilhinney@

Thanks. I am keen to learn from you and to take your advice and recommendations. I realize that your thinking is at a more advanced level than my own. Let's assume I delete all my "per Sub/ per Function" exception handling code. What I would then need is a framework which nevertheless captures unforeseen exceptions wherever they may arise, and write them to a log file, and generate a visible "pop up" to warn the user. In the log file I would need to see a full stack trace by name and I would need to identify the VB line number at which the exception occurred, preferably the variable name and value as well. Because the application is a Windows Forms app with several DataGridViews and DataTables being manipulated, I would not want an exception to cause the application to shut down, but instead I want to leave that choice to the user. In most circumstances it is still possible to save the current working session, for example, since the code to write DataTables to .xlsx files is now 100% reliable.

So, please can you help me as follows? My Windows Form app contains a run once Initialization section and then everything else is triggered by mouse clicks, text changed or button click events. How might I implement the type of generic exception handling mechanism that you advocate, which "logs errors to file" and also creates a dialog pop-up for the user giving the user the choice to continue or close the application? Could you please supply "example VB code" to get me started?

PS I have plenty of Application.DoEvent() calls to release control to Windows Forms framework in any operation that takes more than a 1/10 second to perform. This has the "merit" of achieving very low processor demand if other Windows OS processes need to run, and my application never shows "not responding" when viewed in Task Manager. The "discovery" of Application.DoEvent() was a major step forward for me, whereas I am sure has been obvious to you for a long time. The "windows Forms framework" code in "Visual Studio Express 2012 Desktop Edition" is unmodified by me, except for those aspects that are configured using the Forms Designer.

In developing a complex processor intensive Windows Forms app, I "stumbled upon" key information, rather than finding any good general-purpose guidance on how things "should" be done. Example code snippets such as those on MS web site and in tutorials from MS led me into bad practices, as you can see. Does such a "guide" or an exemplary application framework exist?

Many thanks in advance if you are willing to help me in this way.
 
Last edited:
@jmcilhinney@

Thanks. I am keen to learn from you and to take your advice and recommendations. I realize that your thinking is at a more advanced level than my own. Let's assume I delete all my "per Sub/ per Function" exception handling code. What I would then need is a framework which nevertheless captures unforeseen exceptions wherever they may arise, and write them to a log file, and generate a visible "pop up" to warn the user. In the log file I would need to see a full stack trace by name and I would need to identify the VB line number at which the exception occurred, preferably the variable name and value as well. Because the application is a Windows Forms app with several DataGridViews and DataTables being manipulated, I would not want an exception to cause the application to shut down, but instead I want to leave that choice to the user. In most circumstances it is still possible to save the current working session, for example, since the code to write DataTables to .xlsx files is now 100% reliable.

So, please can you help me as follows? My Windows Form app contains a run once Initialization section and then everything else is triggered by mouse clicks, text changed or button click events. How might I implement the type of generic exception handling mechanism that you advocate, which "logs errors to file" and also creates a dialog pop-up for the user giving the user the choice to continue or close the application? Could you please supply "example VB code" to get me started?

PS I have plenty of Application.DoEvent() calls to release control to Windows Forms framework in any operation that takes more than a 1/10 second to perform. This has the "merit" of achieving very low processor demand if other Windows OS processes need to run, and my application never shows "not responding" when viewed in Task Manager. The "discovery" of Application.DoEvent() was a major step forward for me, whereas I am sure has been obvious to you for a long time. The "windows Forms framework" code in "Visual Studio Express 2012 Desktop Edition" is unmodified by me, except for those aspects that are configured using the Forms Designer.

In developing a complex processor intensive Windows Forms app, I "stumbled upon" key information, rather than finding any good general-purpose guidance on how things "should" be done. Example code snippets such as those on MS web site and in tutorials from MS led me into bad practices, as you can see. Does such a "guide" or an exemplary application framework exist?

Many thanks in advance if you are willing to help me in this way.

As I said, you should handle the UnhandledException event of the application. In that event handler you have access to the exception and all the information it contains. You can set e.ExitApplication to False if you want to keep the application running but I cannot recommend strongly enough that you do not do that. If you didn't know that the exception could be thrown then how can you possibly know what the exact cause was and, more importantly, what state the app is in? I agree that in many, if not most, situations it would be OK to continue but even if it only happens one out of every hundred times that it's not and that time causes data corruption as a result then your app is a pile of garbage.
 
OK thanks I will implement the advice you have given me. Is this the mechanism?

AppDomain.UnhandledException Event (System)

Sub Main()
   Dim currentDomain As AppDomain = AppDomain.CurrentDomain
   AddHandler currentDomain.UnhandledException, AddressOf MyHandler

   Try 
      Throw New Exception("1")
   Catch e As Exception
      Console.WriteLine("Catch clause caught : " + e.Message)
   End Try 

   Throw New Exception("2")

   ' Output: 
   '   Catch clause caught : 1 
   '   MyHandler caught : 2 
End Sub 'Main

Sub MyHandler(sender As Object, args As UnhandledExceptionEventArgs)
   Dim e As Exception = DirectCast(args.ExceptionObject, Exception)
   Console.WriteLine("MyHandler caught : " + e.Message)
End Sub 'MyUnhandledExceptionEventHandler


Another thing that the exception handler should "ideally" do is to test for memory usage approaching say 1GB. On a computer equipped with only 4GB RAM, an "out of memory" exception can be thrown if memory usage for in memory DataTables gets near to 1.5GB, but then it is too late to recover. What I really want to do is to "detect" when memory usage is reaching a "high but recoverable" level prior to an , and then write or page some of the DataTable content to a file, and thereafter implement a mechanism to recover from file the rows from the DataTable when they are being processed.

I expect you will advise me to abandon use of DataTables and use a proper database such as SQL instead. If that is the advice, then I still want the level of user interaction (data sorting, text entry/editing etc.) that is provided currently by a DataGridView bound to (currently) a DataTable. So is there any "generic" advice you can give me in this area, and is there any exemplary framework code that you can refer me to?

Thanks a lot for your patience with me!
 
Last edited:
Another thing that the exception handler should "ideally" do is to test for memory usage approaching say 1GB. On a computer equipped with only 4GB RAM, an "out of memory" exception can be thrown if memory usage for in memory DataTables gets near to 1.5GB, but then it is too late to recover. What I really want to do is to "detect" when memory usage is reaching a "high but recoverable" level, and then write or page some of the DataTable content to a file, and thereafter implement a mechanism to recover from file the rows from the DataTable when they being processed.

I expect you will advise me to abandon use of DataTables and use a proper database such as SQL instead. If that is the advice, then I still want the level of user interaction (data sorting, text entry/editing etc.) that is provided currently by a DataGridView bound to (currently) a DataTable. So is there any "generic" advice you can give me in this area, and is there any exemplary framework code that you can refer me to?

I think that we're getting a bit off-topic now.
 
Back
Top