5

我正在使用django 提供的默认更改密码机制。

post_change_redirect过去常常让提交的表单直接返回我的设置页面,但是我想显示一条消息以向用户保证操作已成功。如何检测我是否由于密码更改成功而进入设置视图,并为此添加一条消息?

4

2 回答 2

7

我不建议在设置视图中检查用户是否通过密码更改到达。我认为理想情况下,密码更改的所有逻辑都包含在同一个地方。这使得查找逻辑变得更容易,并且不需要设置视图了解密码更改视图(因此您可以轻松更改逻辑以将用户重定向到其他地方)。

最好的办法是基于PasswordChangeForm而不是使用内置视图编写自己的password_change视图。通过这种方法,您可以使用消息框架来显示成功消息。(您还必须启用消息框架并将其标记放在您的视图中。)

例如,如果您想显示一条简单的消息并重定向回名为 的 URL 模式'settings',您可以编写如下视图:

from django.contrib import messages
from django.contrib.auth.forms import PasswordChangeForm
from django.core.urlresolvers import reverse_lazy
from django.views.generic import FormView


class PasswordChangeView(FormView):
    template_name = 'registration/password_change_form.html'
    form_class = PasswordChangeForm
    success_url = reverse_lazy('settings')

    def get_form_kwargs(self):
        kwargs = super(PasswordChangeView, self).get_form_kwargs()
        kwargs['user'] = self.request.user
        return kwargs

    def form_valid(self, form):
        form.save()
        messages.success(self.request, "Your password has been changed.")
        return super(FormView, self).form_valid(form)

希望password_change将来该视图将基于类,从而允许使用更少的样板实现相同的行为。

于 2013-06-03T11:10:35.083 回答
3

当用户成功更改密码时,您可以使用Django 消息框架django.contrib.auth.views.PasswordChangeView进行子类化以添加消息。

views.py

from django.contrib import messages
from django.contrib.auth.views import PasswordChangeView
from django.urls import reverse_lazy


class CustomPasswordChangeView(PasswordChangeView):
    # Optional (default: 'registration/password_change_form.html')
    template_name = 'myapp/my_password_change_form.html'
    # Optional (default: `reverse_lazy('password_change_done')`)
    success_url = reverse_lazy('settings')

    def form_valid(self, form):
        messages.success(self.request, 'Your password has been changed.')
        return super().form_valid(form)

然后在您的应用程序中urls.py

from django.conf.urls import url
import myapp.views as views

urlpatterns = [
    url(r'^settings/password/change/$',
        views.CustomPasswordChangeView.as_view(),
        name='password_change'),
    # ...
]

这个答案通过以下方式改进了@enginoid 提供的答案:

  • 该表单的行为与默认密码更改机制几乎相同。
  • 更少的代码重复。
于 2019-07-13T04:19:15.097 回答