Skip to content

Error Handling & Exceptions

Handling errors effectively is critical for building robust, reliable backend systems.

DomusJS encourages clear separation between:

  • Domain errors → business rule violations.
  • Technical errors → infrastructure failures, external system issues.

Let’s break this down.


These represent violations of business rules or invalid operations within the domain.

Examples:

  • Trying to pay for an already-paid order.
  • Registering a user with an email that already exists.
  • Adding a negative quantity to a cart.

✅ These are expected errors → the system should anticipate them.


These come from outside the domain and often relate to infrastructure or external dependencies.

Examples:

  • Database connection failure.
  • Timeout calling an external API.
  • Disk or network errors.

✅ These are unexpected errors → they require robust fallback or recovery mechanisms.


In DomusJS, you can handle domain errors using:

  • Custom exception classes (e.g., UserAlreadyExistsError).
  • The Result pattern → wrapping success/failure outcomes explicitly.

Example with exceptions:

if (userExists) {
throw new UserAlreadyExistsError(email);
}

Example with Result:

if (userExists) {
return Result.fail(new UserAlreadyExistsError(email));
}

✅ Choose the approach that best fits your team’s style and system complexity.


Technical errors should:

  • Be caught at infrastructure boundaries.
  • Logged with enough context for debugging.
  • Exposed to clients only as safe, generic messages (avoid leaking internal details).

Example:

try {
await this.database.save(entity);
} catch (error) {
this.logger.error('Failed to save entity', { error });
throw new InfrastructureError('Database failure');
}

Separate domain vs technical concerns.
Log errors centrally (e.g., use observability tools, tracing).
Provide user-friendly error responses (especially on APIs).
Avoid swallowing errors silently — make sure they surface to where they can be handled.


DomusJS provides:

  • Interfaces for custom exception handling.
  • Middleware hooks to capture and log errors.
  • Integration with observability tools (e.g., OpenTelemetry) for tracing and monitoring.

You can extend or override error strategies depending on your infrastructure.