In Quorum, we may occasionally encounter an error. Errors in computer programs we write can be caused by a wide variety of problems, from incorrect user input to bugs in our programs. For example, if a user attempts to divide a number by zero, Quorum will alert us to a DivideByZeroError. We can reproduce this error in Quorum with the following code:
number result = 12/0 output result
When this error is encountered Quorum will stop running and the user will be provided an error message, indicating that a divide by zero error has occurred. Sometimes we may want Quorum to do something more intelligent when an error is encountered. This is what error handling will allow us to do. In the sections to follow you will learn how to handle errors that might happen and how to create our own custom errors. Because error handling in Quorum online is slightly different than offline, development environments will not be provided for this tutorial. We encourage trying this tutorial in offline mode.
The Error class
The error class is a class in the Quorum standard library that represents a general error in Quorum(Quorum.Language.Errors.Error). This error stores an error message, a general message telling the user something about the error, and a stack trace, the state of the call stack when the error occurred.
All errors in Quorum inherit from the Error class (this is important when we create our own custom error). Some of these errors include, CastError, IndexOutOfBoundsError, and DivideByZeroError.
Detecting an Error
Sometimes we might want to handle an error that has occurred. For example, using the divide by zero example, suppose our code asked the user to enter a divisor. If the user entered 0 your program would stop running and display an error message(see the following code example).
text userInput = input("divide by?") integer divisor = cast(integer, userInput) result = 12/divisor output result
Instead of causing the program to fail, we could detect the error, let the user know about the problem, and set the divisor to 1. We can do this using the check/detect statement. In the check block you place the code that may cause the error.
integer result = 0 check text userInput = input("divide by?") integer divisor = cast(integer, userInput) result = 12/divisor end output result
Then we can use the detect block to specify what type of error to handle or detect. The detect follows the format
detect <name> is <error type> It first specifies the name of the error variable (this can be a name of your choosing, but we use "e"). Then you can specify the type of error you will detect. In this case we want the DivideByZeroError.
detect e is DivideByZeroError //give the user the error and set the divisor to 1 say e:GetErrorMessage() result = 12/1 end output result
In addition to the check and detect blocks, we can specify an optional always block. In the always block you can specify code that needed to execute no matter what the outcome of the check block (it will execute if an error occurred or no error occurred).
always output "calculating result" end
Putting it all together: the following code will ask the user for a number and check it for the specified error. In this detect block we will detect more than one type of error, a general Error and a DivideByZeroError, because the user could input text which would also be invalid (e.g. "zero"). Once the check and detect blocks are executed the always will be called and a result will be given.
use Libraries.Language.Errors.Error use Libraries.Language.Errors.DivideByZeroError class Main action Main number result = 0 check text userInput = input("divide by?") integer divisor = cast(integer, userInput) result = 12/divisor detect e is Error or DivideByZeroError output e:GetErrorMessage() result = 12/1 always output "calculating result" end output "The result is " + result end end
Sometimes we may need to trigger an error manually. This can be done using alerts which follow two formats, alert(<text>) and alert(<error>). In the first format an error of type Error is generated with the message specified by <text>.
alert("Zero is not a valid input")
In the last format the full error is passed. The following is an example:
DivideByZeroError error error:SetErrorMessage("Zero is not a valid input") alert(error)
Creating your own custom errors in Quorum is requires that we extend the Libraries.Language.Errors.Error class.
use Libraries.Language.Errors.Error class MyError is Error end
It is also important to note that the error handling system does not support inheritance hierarchies, like most of Quorum. In other words, errors can inherit from only one other class: Error. When using the detect statement, we can either detect all types of errors with Error or a list of specific errors you wish to detect.
In the next tutorial, we will discuss Writing Quorum Plugins, which describes How to connect to Java (or other languages) from Quorum.