我实际上更喜欢@Stu和其他人提到的方法,即创建一个新的URL和一个视图,以便我们可以将重定向逻辑放在那里。这样更容易,用户还可以在浏览器中键入example.com/profile
以重定向到他们在example.com/profile/username/
上的个人资料。
但另一种不需要定义额外URL的方法是扩展LoginView
,并使用配置文件视图的URL名称进行重定向。
假设我们有两个名为accounts
和pages
的应用程序,并且我们已经在pages
应用程序中定义了配置文件页面,类似于这样:
from django.views.generic import View
from django.http import HttpResponse
class ProfileView(View):
def get(self, request, username):
return HttpResponse('Hello ' + username + '!')
以及URLConf:
from django.urls import path
from .views import ProfileView
app_name = 'pages'
urlpatterns = [
path('profile/<str:username>/', ProfileView.as_view(), name='profile')
]
请注意,我们必须定义
app_name = 'pages'
,因为我们需要用它来引用
pages
应用程序的URL。
然后,在
accounts
应用程序中,我们扩展
LoginView
并添加重定向逻辑:
from django.contrib.auth.views import LoginView
from django.urls import reverse
class CustomLoginView(LoginView):
def form_valid(self, form):
self.success_url_kwargs = {'username': form.cleaned_data['username']}
return super().form_valid(form)
def get_success_url(self):
return reverse('pages:profile', kwargs=self.success_url_kwargs)
from django.urls import path, include
from .views import CustomLoginView
urlpatterns = [
path('accounts/login/', CustomLoginView.as_view(), name='login'),
path('accounts/', include('django.contrib.auth.urls'))
]
成功登录后,将调用
form_valid()
方法,并将我们要在个人资料URL中使用的参数添加到自定义类属性
success_url_kwargs
中。最后,调用
return super().form_valid(form)
首先登录用户,然后重定向到由
get_success_url()
方法(参见
代码)给出的URL,该方法定义为返回我们想要的自定义URL。
请注意,在我们要访问
accounts/login/
时,我们在自定义登录URL之后包含了
auth
应用程序的URL。
另外,如果我们需要访问用户模型实例,可以调用
form.get_user()
。在某些情况下,这很有用。例如,如果用户使用电子邮件登录,我们需要他的用户名,则可以执行
form.get_user().username
。