reauthentication.py 2.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485
  1. # -*- coding: utf-8 -*-
  2. """
  3. flaskbb.auth.services.reauthentication
  4. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  5. Tools for handling reauthentication needs inside FlaskBB.
  6. :copyright: (c) 2014-2018 the FlaskBB Team
  7. :license: BSD, see LICENSE for more details
  8. """
  9. import logging
  10. from flask_babelplus import gettext as _
  11. from werkzeug.security import check_password_hash
  12. from ...core.auth.authentication import (PostReauthenticateHandler,
  13. ReauthenticateFailureHandler,
  14. ReauthenticateManager,
  15. ReauthenticateProvider,
  16. StopAuthentication)
  17. from ...utils.helpers import time_utcnow
  18. logger = logging.getLogger(__name__)
  19. class DefaultFlaskBBReauthProvider(ReauthenticateProvider):
  20. """
  21. This is the default reauth provider in FlaskBB, it compares the provided
  22. password against the current user's hashed password.
  23. """
  24. def reauthenticate(self, user, secret):
  25. if check_password_hash(user.password, secret): # pragma: no branch
  26. return True
  27. class ClearFailedLoginsOnReauth(PostReauthenticateHandler):
  28. """
  29. Handler that clears failed login attempts after a successful
  30. reauthentication.
  31. """
  32. def handle_post_reauth(self, user):
  33. user.login_attempts = 0
  34. class MarkFailedReauth(ReauthenticateFailureHandler):
  35. """
  36. Failure handler that marks the failed reauth attempt as a failed login
  37. and when it occurred.
  38. """
  39. def handle_reauth_failure(self, user):
  40. user.login_attempts += 1
  41. user.last_failed_login = time_utcnow()
  42. class PluginReauthenticationManager(ReauthenticateManager):
  43. """
  44. Default reauthentication manager for FlaskBB, it relies on plugin hooks
  45. to manage the reauthentication flow.
  46. """
  47. def __init__(self, plugin_manager, session):
  48. self.plugin_manager = plugin_manager
  49. self.session = session
  50. def reauthenticate(self, user, secret):
  51. try:
  52. result = self.plugin_manager.hook.flaskbb_reauth_attempt(
  53. user=user, secret=secret
  54. )
  55. if not result:
  56. raise StopAuthentication(_("Wrong password."))
  57. self.plugin_manager.hook.flaskbb_post_reauth(user=user)
  58. except StopAuthentication:
  59. self.plugin_manager.hook.flaskbb_reauth_failed(user=user)
  60. raise
  61. finally:
  62. try:
  63. self.session.commit()
  64. except Exception:
  65. logger.exception("Exception while processing login")
  66. self.session.rollback()
  67. raise