Source code for paperap.exceptions

"""
----------------------------------------------------------------------------

   METADATA:

       File:    exceptions.py
        Project: paperap
       Created: 2025-03-04
        Version: 0.0.8
       Author:  Jess Mann
       Email:   jess@jmann.me
        Copyright (c) 2025 Jess Mann

----------------------------------------------------------------------------

   LAST MODIFIED:

       2025-03-04     By Jess Mann

"""

from __future__ import annotations

from string import Template

import pydantic


[docs] class PaperapError(Exception): """Base exception for all paperless client errors."""
[docs] class ModelValidationError(PaperapError, ValueError): """Raised when a model fails validation."""
[docs] def __init__(self, message: str | None = None, model: pydantic.BaseModel | None = None) -> None: if not message: message = f"Model failed validation for {model.__class__.__name__}." super().__init__(message)
[docs] class ReadOnlyFieldError(ModelValidationError): """Raised when a read-only field is set."""
[docs] class ConfigurationError(PaperapError): """Raised when the configuration is invalid."""
[docs] class PaperlessError(PaperapError): """Raised due to a feature or error of paperless ngx"""
[docs] class APIError(PaperlessError): """Raised when the API returns an error.""" status_code: int | None = None
[docs] def __init__(self, message: str | None = None, status_code: int | None = None) -> None: self.status_code = status_code if not message: message = "An error occurred." message = f"API Error {status_code}: {message}" message = Template(message).safe_substitute(status_code=status_code) super().__init__(message)
[docs] class AuthenticationError(APIError): """Raised when authentication fails."""
[docs] class InsufficientPermissionError(APIError): """Raised when a user does not have permission to perform an action."""
[docs] class FeatureNotAvailableError(APIError): """Raised when a feature is not available."""
[docs] class FilterDisabledError(FeatureNotAvailableError): """Raised when a filter is not available."""
[docs] class RequestError(APIError): """Raised when an error occurs while making a request."""
[docs] class BadResponseError(APIError): """Raised when a response is returned, but the status code is not 200."""
[docs] class ResponseParsingError(APIError): """Raised when the response can't be parsed."""
[docs] class ResourceNotFoundError(APIError): """Raised when a requested resource is not found.""" resource_name: str | None = None
[docs] def __init__(self, message: str | None = None, resource_name: str | None = None) -> None: self.resource_name = resource_name if not message: message = "Resource ${resource} not found." message = Template(message).safe_substitute(resource=resource_name) super().__init__(message, 404)
[docs] class RelationshipNotFoundError(ResourceNotFoundError): """Raised when a requested relationship is not found."""
[docs] class ObjectNotFoundError(ResourceNotFoundError): """Raised when a requested object is not found.""" model_id: int | None = None
[docs] def __init__(self, message: str | None = None, resource_name: str | None = None, model_id: int | None = None) -> None: self.model_id = model_id if not message: message = "Resource ${resource} (#${pk}) not found." message = Template(message).safe_substitute(resource=resource_name, pk=model_id) super().__init__(message, resource_name)
[docs] class MultipleObjectsFoundError(APIError): """Raised when multiple objects are found when only one was expected."""
[docs] class DocumentError(PaperapError): """Raised when an error occurs with a local document."""
[docs] class NoImagesError(DocumentError): """Raised when no images are found in a pdf."""
[docs] class DocumentParsingError(DocumentError): """Raised when a document cannot be parsed."""