Error Handling
Understand how you can handle the errors of the CLI Application.
Introduction
When you start a new Athenna project, error and exception handling is already configured for you. But you can configure your own extending the Athenna error handler. We'll dive deeper into how to do that throughout this documentation.
When you start a new Athenna project, error and exception handling is already configured for you. But you can configure your own extending the Athenna error handler. We'll dive deeper into how to do that throughout this documentation.
This documentation will cover about error handling in the CLI
application, which means that only errors that happens inside
the handle()
method of commands and bellow that will be handled:
import { BaseCommand } from '@athenna/artisan'
import { AppService } from '#src/services/AppService'
export class AppCommand extends BaseCommand {
public static signature(): string {
return 'app'
}
public static description(): string {
throw new Error('This error will be handled by @athenna/core.') 👈
return `Get some information's about the application.`
}
public async handle(): Promise<void> {
const appService = ioc.safeUse<AppService>('App/Services/AppService')
const json = JSON.stringify(appService.findOne(), null, 2)
throw new Error('ConsoleExceptionHandler will handle this error.') 👈
this.logger.info(`Application information's: ${json}`)
}
}
Errors handled by @athenna/core
usually means that a
bootstrap failure has been found in your application.
Configuration
The debug
option in your
Path.config('app.ts')
./src/config/app.ts
APP_DEBUG
environment
variable, which is stored in your .env
file.
During local development, you should set the APP_DEBUG
environment variable to true
. In your production
environment, this value should always be false
. If the
value is set to true
in production, you risk exposing
sensitive configuration values to your application's end
users.
Every error will be logged by default using the console
driver from @athenna/logger
. By default, Athenna uses the
exception
channel of your
Path.config('logging.ts')
./src/config/logging.ts
You can change the driver and formatter of exception
channel inside
Path.config('logging.ts')
./src/config/logging.ts
Custom exceptions
You can create custom exception by executing the following Artisan command:
node artisan make:exception BadCommandException
Next, import and raise the exception as follows.
import { BadCommandException } from '#src/exceptions/BadCommandException'
throw new BadCommandException('Your command is bad.')
Always try to use a custom exception to throw your errors
inside Athenna. If you use Error
, TypeError
and other
classes, it will not be treated by the handlers and will
always be considered as a not treated exception.
Simple exceptions
When talking about exceptions in Artisan and CLI applications,
we can divide them into two categories: simple exceptions and
the more complex ones. Simple exceptions are exceptions that
when handled by the ConsoleExceptionHandler
will only log the
exception message. The more complex will log the entire exception
including code, message, help and stack trace.
Simple exceptions are recognized by ConsoleExceptionHandler
by
the code
. If the code is E_SIMPLE_CLI
, it will be considered
as a simple exception:
import { Exception } from '@athenna/common'
export class NotFoundDatabaseException extends Exception {
public constructor(databaseName: string) {
const code = 'E_SIMPLE_CLI' 👈
super({ code, message: `Database ${databaseName} not found.` })
}
}
Implementing your own exception handler
Let's suppose you want to write a custom logic for handling your exceptions. You can do so by creating your own exception handler:
import { ConsoleExceptionHandler } from '@athenna/artisan'
export class Handler extends ConsoleExceptionHandler {
public async handle(error: any) {
// Implement your own logic
}
}
Now you need to register your exception handler when bootstrapping your application:
await ignite.console(process.argv, {
displayName: 'Athenna',
exceptionHandlerPath: '#src/console/exceptions/Handler', 👈
})