When we develop applications using JavaScript, we might encounter errors, and need to be able to deal with them in timely fashion. One of such means to deal with errors is using the try/catch
statement.
In this article, we will discuss error handling and how we can make use of try and catch statements to deal with errors and exceptions.
Error Handling in JavaScript
In JavaScript, an error occurs when the code is executing, and it can’t continue due to an unexpected or invalid situation. For example, a syntax error, reference error, type error or an exception can cause an error to occur. When an error occurs, the code stops executing and an error message is displayed in the console.
With error handling, we can catch the errors and determine how the error affects your system. With such in place, we can prevent our program from crashing or behaving in ways we don’t want it to. That’s where try
and catch
statements.
The basic syntax of the try statement is:
try {
tryStatements
}
[catch (exception)
{catchStatements}]
[finally {finallyStatements}]
The following parts comprise these statements:
tryStatements
: A set of statements that executes once. If these statements throw an exception, execution transfers to a catch statement if there is one.exception
The name of the variable you want to use to hold the object (usually an Error object) passed to the catch statement.catchStatements
: A set of statements that executes if an exception was thrown.finallyStatements
: A set of statements that is executed before the try…catch statement completes. These statements execute whether or not an exception was thrown or caught.
The try/catch
statement
To handle errors in JavaScript, you can use the try
statement. The try
statement is used to wrap a section of code that might cause an error. If an error occurs within the try
block, the code execution is transferred to the catch
block.
Let’s illustrate how the try/catch
statement to deals with error with a simple example. In this example, the code inside the try block is attempting to add 1 to the value of y
, which hasn't been defined. This will cause an error, and the code inside the catch block will execute, displaying the error message "An error occurred: ReferenceError: y is not defined"
.
try {
let x = y + 1;
console.log(x);
} catch (error) {
console.log("An error occured: " + error);
}
In this example, the code in the try
block attempts to perform an operation that may throw an error. If an error is thrown, the code in the catch
block is executed, and the error is passed to it as an argument. The error can then be logged or processed in some way.
Output
An error occured: ReferenceError: y is not defined
Working with Exceptions
Exceptions are a type of error that can be raised in a JavaScript program. They can be raised manually by the programmer using the throw
statement. The throw
statement allows you to raise an exception with a custom message.
Here is the typical structure for how we can create a throw
statement and make use of them with try/catch
statements.
try {
throw "My custom error message";
} catch (error) {
console.log(error);
}
Division in JavaScript can be confusing, and a typical example is division by zero where JavaScript returns Infinity
, we can create a throw
statement that will deal with that which we can use alongside a try/catch
statement to deal with such scenarios.
try {
let dividend = 13;
let divisor = 0;
const result = dividend / divisor;
if (result === Infinity) {
throw new Error("Division by zero");
}
} catch (error) {
console.log("An error occurred: " + error);
}
Output
An error occurred: Error: Division by zero
In the code, we create a new Error exception that throws Division by zero
when a division operation returns Infinity
and the catch
section handles the exception when our codes happens to throw the error.
Conditional catch statements
Since we can determine the type of an error using the Error object’s name property, we can add code to handle specific types of errors. Here’s an example, where we are using a switch statement to handle different types of exceptions:
<HTML>
<HEAD>
<TITLE>
Handling Specific Errors
</TITLE>
</HEAD>
<BODY>
<H1>Handling Specific Errors</H1>
<SCRIPT LANGUAGE="JavaScript">
<!--
try {
var myData = undefinedValue
}
catch (e){
switch (e.name){
case "EvalError":
document.write("An EvalError error occurred.")
break
case "RangeError":
document.write("A RangeError error occurred.")
break
case "ReferenceError":
document.write("A ReferenceError error occurred.")
break
case "SyntaxError":
document.write("A SyntaxError error occurred.")
break
case "TypeError":
document.write("A TypeError error occurred.")
break
case "URIError":
document.write("An URIError error occurred.")
break
default:
document.write("An error occurred.")
}
}
/ / -->
</SCRIPT>
</BODY>
</HTML>
Nested try-catch blocks
It’s possible to include a try...catch
statement inside another try
statement. Indeed, you can go further and have a try...catch
inside the try statement of this inner try...catch
, or even another inside that, the limit being what it’s actually sensible to do.
So why would you use nested try...catch
 statements? Well, you can deal with certain errors inside the inner try...catch statement. If, however, you’re dealing with a more serious error, the inner catch clause could pass that error to the outer catch clause by throwing the error to it.
<!DOCTYPE html>
<html lang="en">
<head>
<title>Chapter 18: Example 1</title>
</head>
<body>
<script>
try {
try {
ablurt("This code has an error");
} catch(exception) {
var name = exception.name;
if (name == "TypeError" || name == "ReferenceError") {
alert("Inner try...catch can deal with this error");
} else {
throw exception;
}
}
} catch(exception) {
alert("The inner try...catch could not handle the exception.");
}
</script>
</body>
</html>
In this code you have two try...catch
 pairs, one nested inside the other.
The inner try
 statement contains a line of code that contains an error. The catch
 statement of the inner try...catch
 checks the value of the error’s name. If the exception’s name is either TypeError
 or ReferenceError
, the inner try...catch
 deals with it by way of an alert
 box (see Appendix B for a full list of error types and their descriptions). Unfortunately, and unsurprisingly, the type of error thrown by the browser depends on the browser itself. In the preceding example, IE reports the error as a TypeError
 whereas the other browsers report it as a ReferenceError
.
If the error caught by the inner catch
 statement is any other type of error, it is thrown up in the air again for the catch
 statement of the outer try...catch
 to deal with.
Throwing an Exception
You also can throw exceptions yourself, using the throw statement:
throw expression
Here is an example, Suppose you bite into a pickle, but that you can’t stand pickles. In that case, you could throw a bad taste exception like this:
<HTML>
<HEAD>
<TITLE>
Throwing an Exception
</TITLE>
</HEAD>
<BODY>
<H1>Throwing an Exception</H1>
<SCRIPT LANGUAGE="JavaScript">
<!--
try {
throw "Bad Taste Exception"
}
catch (e){
document.write("An error occurred: " + e)
}
// -->
</SCRIPT>
</BODY>
</HTML>
This throws the simple text string "Bad Taste Exception
" as an exception, and that string is passed to the catch statement, where the code displays it. However, the more standard way to do this is to create an Error object, throw that object, and use the object’s message property in a catch statement to find out what error occurred:
The finally
statement
The finally
statement is an optional part of the try/catch/finally structure in JavaScript. The finally
block is executed after the try block and catch block, regardless of whether an error occurs or not. The finally
block can be used to clean up resources or perform any other necessary tasks, even if an error occurs in the try block. The syntax for using the finally
block is:
try {
// code to be executed
} catch (error) {
// code to be executed if an error occurs
} finally {
// code to be executed after the try and catch blocks
}
To illustrate, we can add a finally
statement to the previous code snippet that will show that our operation has been completed. So, after either the try/catch
as done its operation, the finally
statement gets executed.
try {
let dividend = 13;
let divisor = 0;
const result = dividend / divisor;
if (result === Infinity) {
throw new Error("Division by zero");
}
} catch (error) {
console.log("An error occured: " + error);
} finally {
console.log("Math operation completed.");
}
Output
An error occured: Error: Division by zero
Math operation completed.
Summary
In conclusion, error handling is an important aspect of JavaScript programming that allows developers to write code that can handle exceptions and errors. The try
statement is used to wrap a section of code that might cause an error, the catch
statement is used to handle errors that occur within the try
block, and the finally
statement is an optional block that can be used to clean up resources or perform other necessary tasks. With the use of the try
, catch
, and finally
statements, JavaScript developers can write code that is more robust and less prone to errors.
References
try...catch - JavaScript | MDN (mozilla.org)