Sw4   >   Errorhandler   >   Error Handler (All Contents)
The error handler object is an important part of the StudioWorks framework.
In Object-Oriented Programming you need to make a clear distinction between visual classes and non-visual classes. (See Coding Conventions > Visual vs. Non-Visual Classes)
StudioWorks provides you with an error handler object which makes it easy to respect the visual vs. non-visual class rule.
When an error occurs in any method you immediately log the error to the error handler and then at the end of the method you return false or null depending on the type of method. (See Coding Conventions > Quit method return Something) The logged error becomes the current error in the error handler.
When an error condition is returned to a $construct, $control, $event, $print, or $timer method that method is responsible to send a $promptonceLastError message to the error handler object. The error handler opens a prompt window with the last error that was logged.
The error handler is instantiated by the Startup_Task task variable, errhndlr.
To view the error handler's public methods right-click the errhndlr task variable and select . Click on the various $log... methods and review the method description in the tab of the .
Click the button to try out the various error handler object methods.The following is a set of recommended coding conventions for writing code which uses the error handler.
Calculate Mssg as "The error message text."
Calculate Dtls as "Additional details about the error."
Do errhndlr.$logError($cmethod,Mssg,Dtls)
Always enclose your text in double quotes so that you can use single quotes in the text string.
Calculate Mssg as "The error message text"
Calculate Dtls as ''
Do errhndlr.$logError($cmethod,Mssg,Dtls)
; Sample code for $construct, $control, $event, or $timer method
Do $cinst.$someMethodName() Returns FlagOK
If not(FlagOK)
Do errhndlr.$promptonceLastError()
End If
I don't like to include a lot of code in the $event methods because On ev... indents all of the code that follows making it harder to read more than a screen full of $event method code. I find it easer to immediately call an event_evCode method which executes the code for that event and returns the flag. The called method does not need to test pEventCode. Following this convention keeps the $event methods short and simple.
; $event method of a treelist.
On evDrop
Do method event_evDrop Returns FlagOK
If not(FlagOK)
Do errhndlr.$promptonceLastError()
End If
On evTreeExpand
Do method event_evTreeExpand Returns FlagOK
If not(FlagOK)
Do errhndlr.$promptonceLastError()
End If
On evTreeListEditFinishing
Do method event_evTreeListEditFinishing Returns FlagOK
If not(FlagOK)
Do errhndlr.$promptonceLastError()
End If
If a developer version of Omnis is being used, the error handler will open an OK message prompt as soon as an error is logged. You will see DEBUG ERROR in the title of the OK message. Runtime users will not receive this OK message.
The DEBUG ERROR OK message allows the developer to break into the code (Mac: Cmnd+Opt+Delete, Win: Break) Using the
toolbar menu you can then step back to the method where the error was logged and debug your code.If instead of breaking into the code you press the OK button, the code will finish executing and all going well a visual class public method in the method stack will send a $promptonceLastError message to the error handler and the StudioWorks error prompt dialog window will be opened.
The developer debug error prompts can be turned off by setting $:DeveloperErrorPrompts to false.
Do errhndlr.$:DeveloperErrorPrompt.$assign(kFalse)
If the application mode is set to web, the developer debug error prompts are automatically turned off. See Web App Mode for more details.
The oErrorHandler object has a property method $:LogErrorsDestination which returns 3 possible values:
The error handler defaults to using the tracelog until either the logfile on the client computer, or the Errorlog table in the database, has been successfully set.
By default the log errors destination is set to logfile by StudioWorks when the error handler is initialized. This changes the state of $:LogErrorsDestination property from tracelog to logfile. The $:LogFilePath property gives you the path to the error log file.
If you want the errors from all of the users logged to a central location, an Errorlog table in the main database, you will need to make the following changes to the Startup_Task of your main library.
You can copy the method from the main library Startup_Task of StartNewApp
; Get the refs DBSessionObjectRef from the refs object.
Do refs.$:DBSessionObjectRef Returns ObjRef
If ObjRef.$validref
; Set the error handler to use the refs session for logging errors to the database.
Do errhndlr.$setDatabaseSession(SessionRow) Returns FlagOK
End If
Quit method FlagOK
; Redirect to the startup task default methods object.
Do redirect ioStartupTaskDefaultMethods Returns FlagOK
If FlagOK
Do method setErrorHandlerDatabaseSession Returns FlagOK
End If
If the user successfully signs in, they will have successfully logged on to the database. We then send a $setDatabaseSession message to the error handler which points the error handler to the database, checks for an Errorlog server table, creates one if it doesn't exist, and then changes the state of $:LogErrorsDestination to database. From this point on, errors will be logged to the database.
If you want the system administrator to be able to view all of the errors in the error log, you need to make the following changes to your SysAdmin module:
; Add the ErrorlogListView wininst to the nav list if the error handler uses the database for the error log.
If errhndlr.$:LogErrorsDestination.$cando
If errhndlr.$:LogErrorsDestination='database'
Do $cinst.$_addNavigationMenuLine(GroupID,SubgroupID,'ErrorlogListView')
End If
End If
The SysAdmin view of the Errorlog table allows the administrator to view all errors and to delete errors.
Non-SysAdmin users view their own errors by selecting View Log File from the main menu. They are not able to delete errors.
If you want to customize the error log windows you can copy or subclass them to your main library from (wErrorLogEdit, wErrorLogList, wErrorLogListView)Error handler coding is fairly straight forward for non-visual classes... if an error occurs, you log an error and return flag... the $event method at the start of the sequence of calls gets a false return flag and sends the error handler a $promptonceLastError message.
What isn't so simple is if you have a long method that require gather data, prompting the user, then doing some more work, possibly prompting the user again, and then doing more work. This might be batch process that needs the user to confirm things at different stages of the process.
To avoid having one huge long method, you'll need to break the code into several smaller methods. These methods might be scattered among different object classes. The user prompts can't all be excecuted in the $event method of the push button in the window class, so you are going to have some $prompt... methods which you call along the way.
The trouble you run into with those $prompt... methods is that there are 3 things that could happen:
What do you return to the sender to communicate the 3 options?
Returning false if the user cancelled won't work, because the sender will interpret that as an error and send a $promptonceLastError message to the error handler.
The recommended solution is to create a PromptFlag integer variable and return a value of 2 of the user cancelled. To make your code easy to read create the following class variables in any class which deals with prompt flags.
The following sample code shows what the sender method might look like.
; Get all the active vendors and prompt the user to select the vendors to include.
Do method promptselectVendorsToIncludeInReport (VendorsList) Returns PromptFlag
Calculate FlagOK as PromptFlag
If PromptFlag=ckPrompt_continue
; Get all the inventory items for the selected vendors.
Do method getInventoryItemsForSelectedVendors (VendorsList,ItemsList) Returns FlagOK
If FlagOK
; Prompt the user to select the inventory items they wish to include in the report.
Do method promptselectInventoryItemsToIncludeInReport (ItemsList) Returns PromptFlag
Calculate FlagOK as PromptFlag
If PromptFlag=ckPrompt_continue
; Print the report.
Do method printInventoryItemsReport (ItemsList) Returns FlagOK
End If
End If
End If
Quit method FlagOK