VB.Net 2010: Stop code execution, but stay in form

Posted on 2014-08-25
Last Modified: 2014-08-26
The question is pretty simple.  If I encounter an error, and I'm running VB.Net from the executable file I created, I would like to write code that allows me to abandon the execution and send the control back to the functional form.  If the error occurs from a deeply embedded place within code, my strategy has been to create an elaborate architecture of sending the error code back up the successive ranks, finally getting to the original calling routine, from which exiting sends control back to the form.  I'm looking for a shortcut to perform the same thing.

The "Exit Function" and "Exit Sub" routines take me out of the problematic subroutine or function, but the code continues executing from whatever process in which the errant routine was embedded, such as a "for" or "while" loop.  On the other hand, "End" effectively stops all processes, but also has the undesirable side effect of shutting down the form.  If I encounter an error with my input, I want to be able to stop code execution while leaving the form open, allowing me to modify parameters and try again.  

I'm looking for a statement that is more encompassing than "Exit" but stops short of the finality of "End" (a wished-for routine one might call "Exit All").  Does such a thing exist?

Thanks!  ~Peter Ferber
Question by:PeterFrb
    LVL 25

    Expert Comment

    by:Shaun Kline
    If by error, you mean exception, the exception handling of .Net will cause the exception to bubble back up the stack until it is either caught or causes a "run-time" error (effectively stopping your application).

    If the error is a validation issue, you should consider checking for that stuff up front prior to sending data into the depths of your application.
    LVL 25

    Expert Comment

    by:Shaun Kline
    If you are using subs to perform your processing, you could change them to functions and return a value indicating whether the function exited successfully or not. If you are using functions already, you could add an additional variable to the call and use it to return a success of failure.

    Author Comment

    Yes, these are things I do, it's just a little complex if the routine is embedded several layers deep, then it's a matter of getting that return value all the way up the chain.  What I'm hearing you say, thus far, is there's no shortcut around this layering.  That may be the true, but it isn't the thing for which I'd hoped.  

    The issue I'm addressing is validation related, and it's sometimes easier to have the program do the error checking than have me be responsible for it beforehand.  Also, those who inherit this code are not as savvy as I am, so I need to make sure the program provides sensible and relevant feedback and doesn't just shut them down when they make a mistake.  

    There may, in fact, be no shortcut around what I'm already doing.  I'll let the question remain open for a bit, and see if I get more feedback.  Thanks!  ~Peter
    LVL 43

    Expert Comment

    You can use a try...catch block.  An error (exception) will move up as many layers as there are until caught by the catch.
    That is what you are asking for.  Now for the (inevitable) but.
    BUT that is very bad design.  It is really meant for unforseen errors and does not give the routines inbetween the possibility to finish nicely and tidy up.  All you know is something went wrong, not how much was done correctly and what is not yet completed.

    What has been suggested (and what I think you are currently doing) is the 'best' way.
    LVL 40

    Accepted Solution

    An exception is either for something that you know could happen but on which you have no control (such as a broken database connection), or for something that you did not expect at all.

    In the first case, a properly built Try...Catch block will let you recuperate and do whatever you want.

    In the second case, the application is in an unknown situation, and it could be dangerous to go on. This could lead to other problems down the line, corrupted files or databases, who knows, this is something unexpected. The best thing to do there is simply to report or log the error somewhere and stop the application. Find out what is causing the error, handle it and distribute a new version of the application where it is corrected.

    This being said, you can bring unexpected exception to a central processing point with very little code.

    For this to work, you should write your application so that it start in a Sub Main in a module, and point to that sub as the Startup Object for your application. Basically, that module would look something like the following:

    Module Module1
    	Public Sub Main()
    		AddHandler AppDomain.CurrentDomain.UnhandledException, AddressOf UnhandledExceptionHandler
    		AddHandler Application.ThreadException, AddressOf ThreadExceptionHandler
    		Application.Run(New Form1)
    	End Sub
    	Private Sub UnhandledExceptionHandler(ByVal sender As Object, ByVal e As UnhandledExceptionEventArgs)
    		YourReportingMethod(CType(e.ExceptionObject, Exception))
    	End Sub
    	Private Sub ThreadExceptionHandler(ByVal sender As Object, ByVal e As Threading.ThreadExceptionEventArgs)
    	End Sub
    	Private Sub YourReportingMethod(e As Exception)
    		'Report to a file, a database, the event log, in an e-mail... Here we simplify
    	End Sub
    End Module

    Open in new window

    Any error that is not in a Try...Catch block will end up in the last routine.

    If you finish your Try...Catch blocks with a Catch/Throw, as in the following, unexpected errors will also bubble up to that routine:
       'Your code
    Catch ex As SqlException
       'SQL Exception handling
    Catch ex As IO.EndOfStreamException
       'Unexpected end of the file
    Catch ex As IOException
       'File Exception handling
    End Try

    Open in new window

    I am planning a more complete article on the subject in the coming days. Keep a watch for Centralized Exception handling in .NET Windows Applications

    Author Closing Comment

    Thank you!  That's so elegant, and when this site scores, it really sings.  I will try your solution and report back!

    Featured Post

    Highfive + Dolby Voice = No More Audio Complaints!

    Poor audio quality is one of the top reasons people don’t use video conferencing. Get the crispest, clearest audio powered by Dolby Voice in every meeting. Highfive and Dolby Voice deliver the best video conferencing and audio experience for every meeting and every room.

    Join & Write a Comment

    Introduction While answering a recent question about filtering a custom class collection, I realized that this could be accomplished with very little code by using the ScriptControl (SC) library.  This article will introduce you to the SC library a…
    If you need to start windows update installation remotely or as a scheduled task you will find this very helpful.
    Get people started with the process of using Access VBA to control Outlook using automation, Microsoft Access can control other applications. An example is the ability to programmatically talk to Microsoft Outlook. Using automation, an Access applic…
    Show developers how to use a criteria form to limit the data that appears on an Access report. It is a common requirement that users can specify the criteria for a report at runtime. The easiest way to accomplish this is using a criteria form that a…

    734 members asked questions and received personalized solutions in the past 7 days.

    Join the community of 500,000 technology professionals and ask your questions.

    Join & Ask a Question

    Need Help in Real-Time?

    Connect with top rated Experts

    23 Experts available now in Live!

    Get 1:1 Help Now