auth.py 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119
  1. from datetime import timedelta
  2. from django.conf import settings
  3. from django.utils import timezone
  4. from django.utils.translation import ugettext_lazy as _
  5. from misago.banning.models import check_ban
  6. from misago.security.models import SignInAttempt
  7. from misago.sessions.models import Token
  8. from misago.users.models import User
  9. """
  10. Exception constants
  11. """
  12. CREDENTIALS = 'security/bad_credentials'
  13. ACTIVATION_USER = 'users/activation_user'
  14. ACTIVATION_ADMIN = 'users/activation_admin'
  15. BANNED = 'banning/banned_user'
  16. NOT_ADMIN = 'security/not_admin'
  17. class AuthException(Exception):
  18. """
  19. Auth Exception is thrown when auth_* method finds problem with allowing user to sign-in
  20. """
  21. def __init__(self, type=None, error=None, user=None):
  22. self.type = type
  23. self.error = error
  24. self.user = user
  25. def __str__(self):
  26. return self.error
  27. def get_user(email, password, admin=False):
  28. """
  29. Fetch user from DB using email/pass pair, scream if either of data is incorrect
  30. """
  31. try:
  32. user = User.objects.get_by_email(email)
  33. if not user.check_password(password):
  34. raise AuthException(CREDENTIALS, user)
  35. if not admin:
  36. if user.activation == User.ACTIVATION_ADMIN:
  37. # Only admin can activate your account.
  38. raise AuthException(ACTIVATION_ADMIN, user)
  39. if user.activation != User.ACTIVATION_NONE:
  40. # Only admin can activate your account.
  41. raise AuthException(ACTIVATION_USER, user)
  42. except User.DoesNotExist:
  43. raise AuthException(CREDENTIALS)
  44. return user;
  45. def auth_forum(request, email, password):
  46. """
  47. Forum auth - check bans and if we are in maintenance - maintenance access
  48. """
  49. user = get_user(email, password)
  50. if user.is_banned():
  51. raise AuthException(
  52. BANNED,
  53. user.ban_reason_user
  54. )
  55. return user;
  56. def auth_remember(request, ip):
  57. """
  58. Remember-me auth - check if token is valid
  59. """
  60. if request.firewall.admin:
  61. raise AuthException()
  62. if SignInAttempt.objects.is_jammed(request.settings, ip):
  63. raise AuthException()
  64. cookie_token = settings.COOKIES_PREFIX + 'TOKEN'
  65. try:
  66. cookie_token = request.COOKIES[cookie_token]
  67. if len(cookie_token) != 42:
  68. raise AuthException()
  69. try:
  70. token_rk = Token.objects.select_related().get(pk=cookie_token)
  71. except Token.DoesNotExist:
  72. request.cookie_jar.delete('TOKEN')
  73. raise AuthException()
  74. # See if token is not expired
  75. token_expires = timezone.now() - timedelta(days=request.settings['remember_me_lifetime'])
  76. if request.settings['remember_me_extensible'] and token_rk.accessed < token_expires:
  77. # Token expired because it's last use is smaller than expiration date
  78. raise AuthException()
  79. if not request.settings['remember_me_extensible'] and token_rk.created < token_expires:
  80. # Token expired because it was created before expiration date
  81. raise AuthException()
  82. # Update token date
  83. token_rk.accessed = timezone.now()
  84. token_rk.save(force_update=True)
  85. request.cookie_jar.set('TOKEN', token_rk.id, True)
  86. except (AttributeError, KeyError):
  87. raise AuthException()
  88. return token_rk
  89. def auth_admin(request, email, password):
  90. """
  91. Admin auth - check ACP permissions
  92. """
  93. user = get_user(email, password, True)
  94. if not user.is_admin():
  95. raise AuthException(NOT_ADMIN)
  96. return user;
  97. def sign_user_in(request, user, as_hidden=False):
  98. user.set_last_visit(
  99. request.session.get_ip(request),
  100. request.META.get('HTTP_USER_AGENT', ''),
  101. as_hidden
  102. )
  103. user.save(force_update=True)
  104. request.session.set_user(user)