Anyway, I'm a little confused about when to propagate an exception and when to wrap it, and the differences.
At the moment, my understanding tells me that wrapping an exception would involve taking an exception like DriveNotFound (in IO) and then wrap it with the general IOException.
But with the concept of propagating an exception, is this only something that happens if I have an empty catch clause? So in an ASP.NET web app, it would propagate to global.asax. Or in the case of a recently deployed web app, an unhandled HTTPException gave a yellow screen of death and wrote a log to Windows Server (this is a web app I'm rewriting). So the exception happens in a method, it could be handled at the class level, displayed in the page, and then goes up to global.asax or Windows Server.
Why exactly do I want to wrap an exception with a more generic one? The rule is to handle an exception with the most specific type (so DriveNotFound for obviously a drive not found). Also, how would I choose between wrapping and replacing an exception?
Is the exception handling chain just the try and catch (or catches) clauses? I assume from the wording, yes.
Finally, why and how would I want to let an exception propagate up the callstack?
I did read the MS PandP guide on exception handling, but I guess the examples didn't engage me enough to fully understand everything.
This question comes from Enterprise Library the ability to wrap/propagate an exception and etc. It's the propagating I'm not sure about, and the differences in replacing/wrapping an exception.
Also, is it ok to insert complex error handling logic in a catch block (e.g. ifs/elses and things like that).
Thanks
No less than 6 questions :-)
But with the concept of propagating an exception, is this only something that happens if I have an empty catch clause?
An exception will propagate upwards until it is caught by a catch block further up the call stack that handles either that specific exception's type or an exception type nearer the base type of that exception's hierarchy. So, for example, all managed exceptions derive from System.Exception, so a catch block that intercepts System.Exception will catch every managed exception.
Why exactly do I want to wrap an exception with a more generic one?
I'm not sure what you mean by "wrap". Do you mean catch an exception, replace it with another, and add the original as the InnerException property of the new exception? Or something else?
I think there's rarely a good reason to replace an exception with a more generic exception. But you can certainly replace an exception with another exception, for one or more of 3 reasons:
To hide implementation details from the caller.
To improve the level of an abstraction so that it's more meaningful to the caller.
To throw a custom exception that's very specific to the problem in hand.
Also, how would I choose between wrapping and replacing an exception?
I'm sorry, but I still don't understand how you're defining these two as different.
Is the exception handling chain just the try and catch (or catches) clauses?
Here are the basics of what happens when an exception is thrown:
The CLR walks sequentially down the list of Catch blocks within the local Try...End Try block, looking for a local Catch block with an exception filter matching the exception that was thrown.
If a local Catch block has an exception filter that matches the exact exception that was thrown, the code in that Catch block is executed, followed by the code in the Finally block. Then execution continues at the first statement following the End Try.
Alternatively, if the exception that was thrown derives from the exception specified by a local Catch block, the same actions happen as described in the second step. For example, an exception filter that catches ArgumentException will also catch exceptions derived from ArgumentException, such as ArgumentNullException, InvalidEnumArgumentException, DuplicateWaitObjectException, and ArgumentOutOfRangeException.
If no local Catch block matches the exception that was thrown, the CLR walks back up the call stack, method by method, looking for a Catch block that wants to respond to the exception. If no matching Catch block is found in the call stack, the exception is considered to be unhandled.
Alternatively, if a matching Catch block is found somewhere in the call stack, the code in every Finally block between the throw and the catch is executed. This starts with the Finally belonging to the Try block where the exception was thrown and finishes with the Finally in the method below the method where the exception was caught.
After this clean-up has been completed for all methods below where the exception was caught, control is transferred to the Catch block that caught the exception, and this code is executed. Next to run is the Finally block of the Try where the exception was caught. Now that the call stack has been unwound and the error clean-up has been completed, the final step is to continue execution at the first statement following the End Try where the exception was caught.
If code within a Catch block causes another exception to be thrown, the original exception is automatically appended to the new exception using the InnerException property. In this way, exceptions can be stacked without any loss of information.
You should avoid placing clean-up code within a Finally block that might throw an exception, unless that code is within its own Try block. Without this added protection, the CLR behaves as though the new exception was thrown after the end after the Finally block and looks up the call stack for a remote Catch block that wants to respond to the new exception. The original exception will be lost unless the original Catch block saved it.
Finally, why and how would I want to let an exception propagate up the callstack?
Why: Whenever you don't specifically understand the exception and know how to recover from it, you should let it propagate upwards.
How: By only catching exception types that you understand and know how to handle. Occasionally you need the details of any exception in order to do a proper recovery. In this case, you can catch it, do the recovery, then re-throw it by using the throw; statement.
Also, is it ok to insert complex error handling logic in a catch block (e.g. ifs/elses and things like that).
Generally yes, because any new exception caused by code in your Catch block will have the old exception automatically attached to it via the InnerException property. But it's not wise to provoke this mechanism if you can avoid it, so the simpler code you have, the better. Another good reason to keep your Catch code simple is that it often won't go through the same degree of testing as your main-line code.
There is already a rather good question about this with lots of good answers and discussion. See here:
Best Practice for Exception Handling in a Windows Forms Application?
It's all about conveying the right meaning to your callers. I doubt there's cause to wrap a specific exception in a more generic one - that helps no one.
Consider an API that has nothing to do with file access but accesses a config file behind the scenes. If the config file is not present you might wrap the FileNotFoundException in a ConfigurationException so that the correct problem is conveyed to callers.
why and how would I want to let an
exception propagate up the callstack?
You would let an exception propagate if you can't handle it. It's that simple. If there is nothing your code can or should do to work around the exception, then let it propagate. When propagating, be careful how you do so:
throw ex;
is different to:
throw;
The former throws away the old stack trace and creates another from the point the exception is thrown. The latter preserves the original stack trace.
Of course, if you can't handle the exception then you might not bother to catch it in the first place (maybe you want to log though).
I usually do this:
Business logic assemblies (dlls) don't handle exceptions unless they are FULLY understood
Exceptions that are expected but not handleable are wrapped in a single exception type and are allowed to roll up the call stack (i.e., all the different exceptions that can happen during a database interaction are wrapped in a single RepositoryException and thrown)
Unexpected exceptions are allowed to propagate (never include a catch(Exception ex) in a dll)
Exceptions are handled only at the last possible moment (i.e., controller for the UI)
Its usually only far up in the call stack that you know exactly what you're doing (what the current business process is) and how to handle exceptions properly.
This is the best resource I've found for implementing a coherent exception handling strategy in .NET
http://msdn.microsoft.com/en-us/library/cc511522.aspx
Related
So I have been doing some research into how I should be doing try-catch-finally blocks and there is some conflicting information in every post I read. Can someone clarify?
One common idea is to not catch exceptions that you do not know what to do with at that point in the code. The exception will bubble up until it presumably gets to a global exception handler if nothing else catches it. So at that point you display a message to the user that an unknown type of exception occurred, log it, etc.
Now after reading it sounds like this is the only exception handler that you will need? You should not be using it for flow control, so you should be checking if something is returned as null or is invalid causing the exception and correcting it in code. ie. testing for null and doing something about it before it can cause the exception.
But then there are other things such as running out of memory that you would not be able to test for, it would just occur during an operation and the exception would be thrown. But I would not be able to do anything about this either so this would be bubbled up to the global handler.
I think there are some that I am missing, like when dealing with files there can be some thrown from the external code. File not found exception seems like one that may come up often, so I would catch it and in the finally block gracefully close down anything I opened related to other code/processing and then notify the user and log it right there?
The only reason why you would want to catch an exception is for the finally part of the block to make sure that whatever you started before the exception is closed/finalized in a known state? But even then you would want to throw this exception after performing these tasks so the user is notified by the global exception handler, there is no point duplicating this code at this point?
So other than a global exception handler you would have try-catch-finally blocks for these scenarios.
So assuming that I am missing something here, there may be the possibility that you want to try and catch a specific type of exception and then do something with it. I cannot think of anything that you would want to do in the catch block though since the global one would log/notify the user and if you have an exception that usually means that there is no deal for the code to continue on.
Is there any easy way to know which exceptions will be thrown from which modules? I think the only way I have read is to read the MSDN or component suppliers documentation, other than that there is no way to know what exception you would be trying to catch if you were looking for a specific one (not sure why you would)
This question came up since in my application I had a section of code in a try-catch block, and it ended up that when an exception occurred it was either because an object was null, or a string was invalid. Once I wrote code to handle those scenarios the try-catch block is no longer needed, if an exception is encountered now there is nothing the code can do to recover so it should be logged and let the user know so it can be fixed.
But this goes against what I have been reading and what has been preached to me, bad code is code with no try-catch blocks. So how does this all tie together and what piece am I missing here?
The first part of your question is all correct: you should only catch exceptions that you know how to handle. Otherwise, just let them bubble up until they reach code that can handle them.
(Note that "handle" doesn't mean "log" or "display an error". It means to correct the problem that caused the exception, or work around it in some way.)
If they never encounter code that can handle them, or if they are unhandlable exceptions (like OutOfMemory), then they will eventually reach the global unhandled exception handler. This is where you will log the exception (if appropriate), display a generic error to the user (if appropriate), and more often than not, terminate the application. You cannot simply continue as if nothing happened—the exception indicates that the application is in an unexpected state. If you try and continue, you're just going to crash, or worse.
I think there are some that I am missing, like when dealing with files there can be some thrown from the external code. File not found exception seems like one that may come up often, so I would catch it and in the finally block gracefully close down anything I opened related to other code/processing and then notify the user and log it right there?
FileNotFound is a good example of an exception that you will want to handle locally. In the same method (or perhaps one level up, in your UI code) that attempts to load the file, you'll have a catch block for FileNotFound exceptions. If appropriate, display a friendly error message to the user and ask them to choose another file. If it's internal code, give up and try something else. Whatever you need to do. There are few good reasons for FileNotFound to bubble up outside of your code.
This is sort of like using exceptions for flow control, but unavoidable. There is no way to avoid using exceptions (or error codes) for I/O, so you just need to handle the failure case. You could try and verify that the file exists first, before trying to open it, but that would not solve the race issue wherein the file gets deleted or becomes otherwise inaccessible between the time your verification code runs and when you actually try and open it. So now all you've done is duplicated your error-handling code in two places, which serves little purpose.
You have to handle exceptions like FileNotFound locally. The further away from the code that throws, the less likely you can do anything reasonable about it.
Another good example of this, aside from I/O-related exceptions, is a NotSupportedException. For example, if you try to call a method that isn't supported, you might get this exception. You will likely want to handle it and have code in the catch block that falls back to a safe alternative.
The only reason why you would want to catch an exception is for the finally part of the block to make sure that whatever you started before the exception is closed/finalized in a known state? But even then you would want to throw this exception after performing these tasks so the user is notified by the global exception handler, there is no point duplicating this code at this point?
This does not require catching the exception. You can have a try block with only a finally block. A catch block is not required. In fact, this is precisely what using statement implements. If you have state that needs to be cleaned up in the event of an exception being thrown, you should implement the IDisposable pattern and wrap usage of that object in a using block.
Is there any easy way to know which exceptions will be thrown from which modules? I think the only way I have read is to read the MSDN or component suppliers documentation, other than that there is no way to know what exception you would be trying to catch if you were looking for a specific one (not sure why you would)
Precisely. This is not really a problem, though, since you are only catching the exceptions that you can do something about. If you don't know that a module can throw a particular exception, you obviously can't have written code that can handle that exception.
The documentation will tell you all of the important exceptions that you might need to handle, like FileNotFound, SecurityException, or what have you.
This question came up since in my application I had a section of code in a try-catch block, and it ended up that when an exception occurred it was either because an object was null, or a string was invalid. Once I wrote code to handle those scenarios the try-catch block is no longer needed, if an exception is encountered now there is nothing the code can do to recover so it should be logged and let the user know so it can be fixed.
Avoiding exceptions in the first place is always the best option. For example, if you can design your application so that a null object or invalid string is impossible, great. That is what we call robust code. In that case, you don't need to catch these exceptions because there's no way that you can handle it. You thought you already handled the problem, so if an exception is getting thrown anyway, it is a sign of a bug. Don't gloss over it with a catch block.
But sometimes, catch blocks are still necessary, and you write code inside of the catch block to handle the problem. In that case, there's probably no reason to re-throw the exception or log it, so you don't have any code duplication.
But this goes against what I have been reading and what has been preached to me, bad code is code with no try-catch blocks. So how does this all tie together and what piece am I missing here?
Completely wrong. I don't know where you've been reading that, but it is nonsense. Exceptions are exceptional conditions. If your code has catch blocks strewn all over it, that is a sign that you are doing it wrong. Either you're using exceptions for flow control, you're swallowing exceptions in a misguided attempt to "improve reliability", or you don't know about the global unhandled exception handler.
Doesn't sound like you're missing anything to me.
The only thing I feel compelled to mention that doesn't fit strictly into any of your questions is that sometimes you might want to catch an exception and rethrow it as a different exception. The most common situation where you would do this is if you were designing a library of re-usable code. Inside of the library, you might catch internal exceptions and, if you cannot handle them, rethrow them as general exceptions. The whole point of a library is encapsulation, so you shouldn't let exceptions bubble up that the caller cannot possibly do anything about.
There is no true guide for exceptions management (raising and handling). Every app has to decide what level of flow control should be used and how exception has to be raised/handled.
General rules are:
exceptions are raised in exceptional situations
handle exception you can handle and do meaningful things for your app so
exception raising can be used in flow control, actually it's the only way you can reliably handle flow control when you are dealing with devices, so hardware interrupts. (printers, bill validators, file transfer...)
The rest is up to you. The meaning of exception management is made by you.
Imagine you need to download some files from an FTP server, one you don't control. Of course you can't trust other people so you need to prepare for temporary outages and such. So you wrap your downloading code in a try-catch-block and look for WebException if you catch one you might check for FtpStatusCode.ActionNotTakenFileUnavailableOrBusy if that was the error you simply retry. Similarly if you call a web service a 404 might be trouble, but a 429 means that you wait a little and retry, because you had been rate-limited.
Usually you can know which exceptions can be thrown by experience or documentation but C# lacks checked exceptions. Things like NullPointerException or ArgumentNullException can be properly handled with guards in your code. But other things, like errors external dependencies can sometimes be caught and handled by you without crashing the application.
Is there a rule of thumb for handling exceptions wrt whether they should be handled in the same method of the exception-raising code or the caller?
In relation to this, what is the rule of thumb/general practise for deciding when to use "throw new" or catch blocks?
Thanks
Catch means you can handle the exception.
You should catch exceptions when you can handle the condition and do something useful. Otherwise you should let it bubble up the call stack and perhaps someone above you can handle it. Some apps have unhandled exception handlers to handle it at the outer most layer but in general, unless you know you have some useful way to handle it, let it go.
throw new means you're creating an error condition that someone above you may want to catch. Remember that the callers may want to handle/catch your error so do not throw new "Exception" or "ApplicationException" - throw a specific exception type that inherits from exception so the user knows what they're handling.
Last but not least, ensure exceptions are exceptional. Do not throw unless it's an exceptional error case. For example, code that checks if something exists should not throw and catch - it causes the debugger to break and it's expensive if called frequently. On our team, we always look for code to run clean if no error case was encountered.
Here's a related post:
Trying to understand exceptions in C#
Handling should be done on the lowest level that can handle the exception. E.g. if a low level arithmetic function gives a division by zero exception you can maybe continue. If a file I/O error occurs, maybe it should be handled very high in the flow of the application, it depends.
Throw new should be used where you want to throw an exception, so at the location where the exception occurs.
Catch blocks should be added where exceptions can be handled, and as written above, it depends where you want to catch them, preferably as soon as possible but high enough to be able to handle them.
I don't know what we can do with a custom exception, what we can't do with a built-in one. It seems a naive question but I really have no idea about that.
What do you think?
The reason for the different types of exceptions is to allow you to be able to catch just the ones you want with your handlers, letting the others go on up the stack. So you can arrange to catch exceptions for certain, occasionally-expected situations just by the type of the exception.
You may not need to create your own very often at all, actually. But if you do, it would be because you need to be able to throw and capture an exception type more specific than what is available, and perhaps with additional information attached.
It is useful to create a custom exception if:
There is no built-in exception that expresses the type of error condition you have.
You want to catch only that specific type of exception and not exceptions coming from the framework.
But usually if there already is an exception in the framework that you could use then it is better to use it instead of creating your own exception for the same thing.
You could use it for implementing special error handling for things related to your application. Suppose you build a banana application, then you could have an OutOfBananasException. If your application gets out of bananas you can throw the exception and catch it later on with special error handling.
try
{
EatBananas();
}
catch(OutOfBananasException oobe)
{
GetMoreBananas();
}
catch(Exception e)
{
TellUserAndAbort();
}
Edit:
The reason to use your own Exceptions instead of the built in is to make it clear to everyone reading you code or using your library what type of error has occurred. You should only create your own exceptions when you can not find any suitable built in exception.
Edit2:
One thing you can do with your own exceptions that you can not do with built in is to add properties describing things about the error condition that the error handler might use. If you have an exception relating to customers you exception could have properties for customer name and customer id and thus make it possible for the error handler to display informative error messages to the user.
There's only a few exceptions in .NET that are treated in a special manner, like ThreadAbortException, which can't (normally) be caught and handled and swallowed.
Other than that, exception types are just exception types. You can do pretty much the same with your own exceptions that you can do with the ones defined in the framework.
The benefits of custom exceptions have been outlined here, but before you create your own make sure the BCL doesn't already have one fitting your needs:
http://mikevallotton.wordpress.com/2009/07/08/net-exceptions-all-of-them/
(There's 141 of them!)
One annoyance with the built-in exceptions is that there is no systematic distinction made between exceptions that indicate that
an operation failed but a retry might succeed; the system state is as it was before the operation was attempted.
an operation failed, and a retry isn't likely to help; nonetheless, the system state is as it was before the operation was attempted;
an operation has failed in such a way as to potentially corrupt something else.
It may be useful to catch exceptions and rethrow one of three custom exceptions (meanings defined above) based upon where the exception was caught. When the exception is rethrown, pass the original exception as the InnerException parameter.
Incidentally, it's possible to define generic exceptions. I'm not quite sure of the pros and cons of doing so, and I've never seen anyone else do it. One could define e.g. a TransientFaultException(of T) which inherits from a (custom) TransientFaultException; an application which catches a TimeoutException could rethrow as a TransientFaultException(of TimeOutException) and have it caught as either a TransientFaultException(of TimeoutException) or a TransientFaultException. Unfortunately, one would have to know the type of the exception to be taught to create the proper generic. If one were to catch an Exception and pass it to a factory method for TransientFaultException, the new exception would be of type TransientFaultException(of Exception), regardless of what type of exception was originally thrown.
Custom exceptions allow you to do 2 things:
Capture custom typed-data in the exception
Capture a custom exception occurrence
You should only create a custom exception when there isn't a built in exception to handle as necessary.
As an example, in our application we have DataLayerException which is thrown when the datalayer encounters an error (and includes the specific DBMS exception as an inner exception).
We also have DataLayerSingleResultNoneException - which is when we expect a single result back but there is no result, and DataLayerSingleResultManyException which is when we expect a single result but get many back. This allows us to catch the different problems an action them accordingly.
I have a large C# code base. It seems quite buggy at times, and I was wondering if there is a quick way to improve finding and diagnosing issues that are occuring on client PCs.
The most pressing issue is that exceptions occur in the software, are caught, and even reported through to me. The problem is that by the time they are caught the original cause of the exception is lost.
I.e. If an exception was caught in a specific method, but that method calls 20 other methods, and those methods each call 20 other methods. You get the picture, a null reference exception is impossible to figure out, especially if it occured on a client machine.
I have currently found some places where I think errors are more likely to occur and wrapped these directly in their own try catch blocks. Is that the only solution? I could be here a long time.
I don't care that the exception will bring down the current process (it is just a thread anyway - not the main application), but I care that the exceptions come back and don't help with troubleshooting.
Any ideas?
I am well aware that I am probably asking a question which sounds silly, and may not have a straightforward answer. All the same some discussion would be good.
Exceptions maintain the call stack which you can use to trace the source of the exception unless the exception is rethrown improperly or is swallowed. By the former, I mean something like:
try
{
//...
}
catch ( Exception e )
{
//do stuff with exception
throw e;
}
Instead of :
try
{
//...
}
catch ( Exception )
{
//do stuff with exception
throw;
}
The later maintains the call stack whereas the former does not. In general, code should only catch exceptions that it plans on handling rather than all exceptions. If the code is properly designed this way, then when the top most layer catches the exception, you should have via the call stack the method that started the chain of events.
I’m used to having try/catch blocks in every method. The reason for this is so that I can catch every exception at the point of infraction and log it. I understand, from my reading and conversations with others, that this isn’t a popular view. One should only catch what one is prepared to handle. However, if I don’t catch at the point of infraction, then it would be possible to never log that infraction and know about it. Note: When I do catch and don’t handle, I still throw. This allows me to let the exception propagate to something that will handle it, yet still let me log it at the point of infraction.
So... How does one avoid try/catch in every method, yet still log the error at the point at which it occurred?
No, don't catch everything. Exceptions propagate higher up on the stack. All you have to do is make sure that the exception is caught before it gets to the top of the stack.
This means, for instance, that you should surround the code of an event handler with a try/catch block. An event handler may be the "top of the stack". Same for a ThreadStart handler or a callback from an asynchronous method.
You also want to catch exceptions on layer boundaries, though in that case, you might just want to wrap the exception in a layer-specific exception.
In the case of ASP.NET, you may decide to allow ASP.NET Health Monitoring to log the exception for you.
But you certainly don't ever need to catch exceptions in every method. That's a major anti-pattern. I would loudly object to you checking in code with that kind of exception handling.
You can see everything at stack trace - no need to try/catch every method.
Stick to few rules:
Use try/catch only if you want to use a custom exception type
Define a new exception type only if upper levels needs to know that
Try/catch at top level instead of doing that for each method
OK, having read all the answers saying you should have a single try/catch at the top level, I'm going to weigh in with an alternative view.
I wouldn't put a try/catch in every method, far from it. But I would use a try/catch around sections of code that I expected to fail (e.g. opening a file), and where I wanted to add additional information to the exception (to be logged higher up the chain).
A stack trace saying and a message saying "permission denied" might be enough to allow you as a programmer to figure out what went wrong, but my goal is to provide the user with meaningful information, such as "Could not open file 'C:\lockedfile.txt'. Permission denied.".
As in:
private void DoSomethingWithFile(string filename)
{
// Note: try/catch doesn't need to surround the whole method...
if (File.Exists(filename))
{
try
{
// do something involving the file
}
catch (Exception ex)
{
throw new ApplicationException(string.Format("Cannot do something with file '{0}'.", filename), ex);
}
}
}
I'd also like to mention that even the people saying "only have one try/catch" would presumably still use try/finally throughout their code, since that's the only way to guarantee proper cleanup, etc.
Catching and rethrowing an exception that you cannot handle is nothing more than a waste of processor time. If you can't do anything with or about the exception, ignore it and let the caller respond to it.
If you want to log every exception, a global exception handler will do just fine. In .NET, the stack trace is an object; its properties can be inspected like any other. You can write the properties of the stack trace (even in string form) to your log of choice.
If you want to ensure that every exception is caught, a global exception handler should do the trick. In point of fact, no application should be without one.
Your catch blocks should only catch exceptions that you know that you can gracefully recover from. That is, if you can do something about it, catch it. Otherwise, let the caller worry about it. If no callers can do anything about it, let the global exception handler catch it, and log it.
I definitely don't use a try catch wrapper around every method (oddly enough, I did when I first started but that was before I learned better ways).
1) To prevent the program from crashing and the users losing their info, I do this
runProgram:
try
{
container.ShowDialog();
}
catch (Exception ex)
{
ExceptionManager.Publish(ex);
if (MessageBox.Show("A fatal error has occurred. Please save work and restart program. Would you like to try to continue?", "Fatal Error", MessageBoxButtons.YesNo) == DialogResult.Yes)
goto runProgram;
container.Close();
}
container is where my application starts so this basically puts a wrapper around my entire app so that nothing causes a crash that can't be recovered. This is one of those rare instances where I don't really mind using a goto (it is a small amount of code and still quite readable)
2) I only catch exceptions in methods where I expect something could go wrong (such as a timeout).
3) Just as a point of readibility, if you have a try catch block with a bunch of code in the try section and a bunch in the catch section, it is better to extract that code to a well named method.
public void delete(Page page)
{
try
{
deletePageAndAllReferences(page)
}
catch (Exception e)
{
logError(e);
}
}
To do it at the point of occurrence, you would still need a try/catch. But you don't necessarily need to catch the exceptions everywhere. They propagate up the call stack, and when they are caught, you get a stack trace. So if a problem emerges, you can always add more try/catches as needed.
Consider checking out one of the many logging frameworks that are available.
I don't think you need to catch everything at the point of infraction. You can bubble up your exceptions, and then use the StackTrace to figure out where the point of infraction actually occurred.
Also, if you need to have a try catch block, the best approach I've heard is to isolate it in a method, as to not clutter the code with huge try catch blocks. Also, make as few statements as possible in the try statement.
Of course, just to reiterate, bubbling up your exceptions to the top and logging the stacktrace is a better approach than nesting try-catch-log-throw blocks all throughout your code.
I would look into using ELMAH for exception handling, which is pretty much a concept of "let exceptions happen". ELMAH will take care of logging them and you can even set it to email you when exceptions for a certain project reach or exceed a specific threshold. In my department, we stay as far away from try/catch blocks as possible. If something is wrong in the application, we want to know right away what the issue is so we can fix it, instead of repressing the exception and handling it in code.
If an exception happens, that means that something isn't right. The idea is to make your application do only what it should do. If it's doing something different and causing exceptions, your response should be to fix the reason it's happening, not let it happen and handle it in code. This is just my/our philosophy and it's not for everyone. But we've all been burned way too many times by an application "eating" an exception for some reason or another and no one knows that something is wrong.
And never, ever, EVER catch a general Exception. Always, always, always catch the most specific exception so that if an exception is thrown, but it's not the type you're expecting, again, you'll know because the app will crash. If you just catch (Exception e), then no matter what type of exception is thrown, your catch block will now be responsible for responding to every single type of exception that could possibly be thrown. And if it doesn't, then you run into the whole "eating" exceptions, where something is going wrong but you never know until it is likely too late.
How does one avoid try/catch in every method, yet still log the error at the point at which it occurred?
It depends on the hosting env. Asp.Net, WinForms, and WPF all have different ways of capturing unhandled exceptions. But once the global handler is passes an exception instance you can determine the point of throw from the exception, as each exception includes a stacktrace.
Realistically, avoid granular try/catches. Allow the exception to traverse upwards in the stack and be caught in as high a level as possible. If you have a specific point of concern, then place logging in the immediate catch, if you are worried about the exception cascading - although you would still be able to resolve these by drilling into the inner exceptions.
Exception handling should not be an afterthought. Make sure that you do it consistently. I have seen a lot of people put a broad try/catch from the beginning to the end of every method and catch the general exception. People think that this helps them get more information, when in fact, it doesn't. More is less in some cases, as less is more. I never get tired of the axiom that "Exceptions should be used to note exceptional behavior." Recover if you can, and try to reduce the number of overall exceptions. Nothing is more frustrating when you are trying to troubleshoot an issue and seeing hundreds of the same NullReferenceException, or similar, when something goes wrong.
Exceptions are implemented so that they have no cost unless thrown.
This means to me that performance ramifications is not a strong argument against. Exceptional conditions usually are ... exceptional.