对于密码更改,我使用auth_views.password_change
并重置密码auth_views.password_reset
。
当用户成功更改密码时,如何通知我?我不需要知道旧密码或新密码。只是事件发生了,以及哪个用户。
同样,我希望在有人要求重置密码时以及成功完成重置程序时收到通知。
我可以通过信号或一些简单的修补来完成上述操作吗?或者我是否需要编写自己的观点才能做到这一点?
答案 0 :(得分:7)
创建装饰器:
def notify_admins(func):
def wrapper(request, *args, **kwargs):
# send email to admins
return func(request, *args, **kwargs)
return wrapper
然后,只需将其包装在urls.py中的相应视图中:
urlpatterns = patterns('',
...
(r'^password_change/done/$', notify_admins(auth_views.password_change_done)),
(r'^password_reset/done/$', notify_admins(auth_views.password_reset_done)),
(r'^reset/done/$', notify_admins(auth_views.password_reset_complete)),
...
)
请记住,直接从视图发送电子邮件,或者在这种情况下是装饰器,会占用请求。不是直接在那里发送电子邮件,最好是创建一个自定义信号和一个处理程序,它将触发一个线程来实际发送电子邮件。然后,在装饰器中,您只需发送信号。
答案 1 :(得分:4)
您可以撰写传递给password_change_form
的自定义password_change
。此表单将扩展django的PasswordChangeForm
覆盖其save方法,以首先通知您更改,然后调用它的父PasswordChangeForm
保存方法。
关于password_change视图的文档: https://docs.djangoproject.com/en/dev/topics/auth/#django.contrib.auth.views.password_change
ChangeForm上的文档: https://docs.djangoproject.com/en/dev/topics/auth/#django.contrib.auth.forms.PasswordChangeForm
PasswordChangeForm的代码: https://code.djangoproject.com/browser/django/trunk/django/contrib/auth/forms.py
答案 2 :(得分:3)
从Django 1.9开始,您可以定义自己的密码验证器。如果你愿意,你甚至可以简单地重新定义一个现有的。执行此操作时,请添加方法:
from django.contrib.auth.password_validation import MinimumLengthValidator
class MyPasswordValidator(MinimumLengthValidator):
def password_changed(self, password, user):
# put your password changed logic here
请务必在您的设置中添加新课程,如下所示:
AUTH_PASSWORD_VALIDATORS = [
{
'NAME': 'my_package.password_validators.MyPasswordValidator',
'OPTIONS': {
'min_length': 8,
}
},
...
]
现在,每次用户更改密码时,都会通知您的MyPasswordValidator类。根据我的经验,这是最好的方法,因为:
我会提醒您注意password_changed()中的password参数实际上是用户的原始密码。处理此问题时要小心,绝对不要将其存放在未加密/未加密的地方。
答案 3 :(得分:2)
如果您已经在使用auth_views.password_change
内置视图,那么在成功更改后重定向会很容易通知您自己:
https://docs.djangoproject.com/en/dev/topics/auth/#django.contrib.auth.views.password_change
password_change(request[, template_name, post_change_redirect, password_change_form])
如果您将post_change_redirect网址设置为重定向到您自己的某个视图,那么您只需在该视图中执行您想要的任何操作即可发送通知(电子邮件,数据库更新等)。
您甚至可以在重定向视图中执行通知,然后返回password_change_done(request[, template_name])
答案 4 :(得分:1)
您还可以捕获信号并检查密码是否已更改。请记住,每次用户更改时,此代码都会运行。
@receiver(pre_save, sender=User)
def record_password_change(sender, **kwargs):
user = kwargs.get('instance', None)
if user:
new_password = user.password
try:
old_password = User.objects.get(pk=user.pk).password
except User.DoesNotExist:
old_password = None
if new_password != old_password:
# do what you need here