feat: add tests for import polling, login page, money utilities, and query keys
- Implemented tests for import polling functionality, ensuring correct behavior for active and terminal import statuses. - Created tests for the login page, validating user interactions and error handling. - Added unit tests for money utility functions, covering parsing, formatting, and summation of monetary values. - Developed tests for query keys, ensuring proper scoping and invalidation roots. chore: setup testing environment and configuration - Added setup file for testing with Vitest and Testing Library. - Configured TypeScript and Vite for the frontend project. - Created Docker and Nginx configurations for local development and production environments. - Established a PostgreSQL initialization script for setting up application roles. docs: add README and environment configuration for infra - Included README for the infra directory, detailing local development setup and service descriptions. - Created an example environment configuration file for local development with placeholders for sensitive information.
This commit is contained in:
@@ -0,0 +1,48 @@
|
||||
from typing import Any
|
||||
|
||||
|
||||
class AppError(Exception):
|
||||
"""Domain error rendered as a machine-readable JSON error payload."""
|
||||
|
||||
status_code: int = 400
|
||||
code: str = "APP_ERROR"
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
message: str,
|
||||
*,
|
||||
code: str | None = None,
|
||||
status_code: int | None = None,
|
||||
details: Any = None,
|
||||
) -> None:
|
||||
super().__init__(message)
|
||||
self.message = message
|
||||
if code is not None:
|
||||
self.code = code
|
||||
if status_code is not None:
|
||||
self.status_code = status_code
|
||||
self.details = details
|
||||
|
||||
|
||||
def bad_request(code: str, message: str, details: Any = None) -> AppError:
|
||||
return AppError(message, code=code, status_code=400, details=details)
|
||||
|
||||
|
||||
def unauthorized(code: str, message: str, details: Any = None) -> AppError:
|
||||
return AppError(message, code=code, status_code=401, details=details)
|
||||
|
||||
|
||||
def forbidden(code: str, message: str, details: Any = None) -> AppError:
|
||||
return AppError(message, code=code, status_code=403, details=details)
|
||||
|
||||
|
||||
def not_found(code: str, message: str, details: Any = None) -> AppError:
|
||||
return AppError(message, code=code, status_code=404, details=details)
|
||||
|
||||
|
||||
def conflict(code: str, message: str, details: Any = None) -> AppError:
|
||||
return AppError(message, code=code, status_code=409, details=details)
|
||||
|
||||
|
||||
def unprocessable(code: str, message: str, details: Any = None) -> AppError:
|
||||
return AppError(message, code=code, status_code=422, details=details)
|
||||
Reference in New Issue
Block a user