exc.py 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106
  1. from __future__ import annotations
  2. import typing as t
  3. from datetime import datetime
  4. class BadData(Exception):
  5. """Raised if bad data of any sort was encountered. This is the base
  6. for all exceptions that ItsDangerous defines.
  7. .. versionadded:: 0.15
  8. """
  9. def __init__(self, message: str):
  10. super().__init__(message)
  11. self.message = message
  12. def __str__(self) -> str:
  13. return self.message
  14. class BadSignature(BadData):
  15. """Raised if a signature does not match."""
  16. def __init__(self, message: str, payload: t.Any | None = None):
  17. super().__init__(message)
  18. #: The payload that failed the signature test. In some
  19. #: situations you might still want to inspect this, even if
  20. #: you know it was tampered with.
  21. #:
  22. #: .. versionadded:: 0.14
  23. self.payload: t.Any | None = payload
  24. class BadTimeSignature(BadSignature):
  25. """Raised if a time-based signature is invalid. This is a subclass
  26. of :class:`BadSignature`.
  27. """
  28. def __init__(
  29. self,
  30. message: str,
  31. payload: t.Any | None = None,
  32. date_signed: datetime | None = None,
  33. ):
  34. super().__init__(message, payload)
  35. #: If the signature expired this exposes the date of when the
  36. #: signature was created. This can be helpful in order to
  37. #: tell the user how long a link has been gone stale.
  38. #:
  39. #: .. versionchanged:: 2.0
  40. #: The datetime value is timezone-aware rather than naive.
  41. #:
  42. #: .. versionadded:: 0.14
  43. self.date_signed = date_signed
  44. class SignatureExpired(BadTimeSignature):
  45. """Raised if a signature timestamp is older than ``max_age``. This
  46. is a subclass of :exc:`BadTimeSignature`.
  47. """
  48. class BadHeader(BadSignature):
  49. """Raised if a signed header is invalid in some form. This only
  50. happens for serializers that have a header that goes with the
  51. signature.
  52. .. versionadded:: 0.24
  53. """
  54. def __init__(
  55. self,
  56. message: str,
  57. payload: t.Any | None = None,
  58. header: t.Any | None = None,
  59. original_error: Exception | None = None,
  60. ):
  61. super().__init__(message, payload)
  62. #: If the header is actually available but just malformed it
  63. #: might be stored here.
  64. self.header: t.Any | None = header
  65. #: If available, the error that indicates why the payload was
  66. #: not valid. This might be ``None``.
  67. self.original_error: Exception | None = original_error
  68. class BadPayload(BadData):
  69. """Raised if a payload is invalid. This could happen if the payload
  70. is loaded despite an invalid signature, or if there is a mismatch
  71. between the serializer and deserializer. The original exception
  72. that occurred during loading is stored on as :attr:`original_error`.
  73. .. versionadded:: 0.15
  74. """
  75. def __init__(self, message: str, original_error: Exception | None = None):
  76. super().__init__(message)
  77. #: If available, the error that indicates why the payload was
  78. #: not valid. This might be ``None``.
  79. self.original_error: Exception | None = original_error