【问题标题】:User Accessing Other Users' Forms Using django-braces用户使用 django-braces 访问其他用户的表单
【发布时间】:2013-07-03 12:44:28
【问题描述】:

这里有几个问题,我已经搜索了文档和 SO,只是变得更加困惑。

主要问题:

我有一个加载到 views.py 中的 UserProfileForm:

from braces.views import LoginRequiredMixin, CsrfExemptMixin

class UpdateUserProfileView(LoginRequiredMixin, CsrfExemptMixin, UpdateView):
    model = UserProfile
    success_url = reverse_lazy('profile_update')
    form_class = UserProfileForm

在我的 urls.py 中:

urlpatterns = patterns('',
    url(r'^(?P<pk>\d+)/$', UpdateUserProfileView.as_view(), name='profile_update'),
)

当我以user_id 2 登录时,我可以在/profile/2/ 看到我自己的个人资料,但是当我输入/profile/1/ 时,我可以编辑user_id 1 的用户个人资料。我在这里做错了什么吗?我应该如何限制访问?我应该在我的模板中这样做吗? (我之前都以两个用户的身份登录过)

子问题:

  1. reverse_lazy 在这里似乎不起作用,返回此错误:Reverse for 'profile_update' with arguments '()' and keyword arguments '{}' not found. 我在我的模型中添加了一个get_absolute_url,并从我的主项目的 url 中调用了这个 urls.py。

  2. 对于用于创建配置文件的单独视图,防止表单在保存时创建重复键的最佳做法是什么?

编辑:

根据@mariodev 的建议,我重写了我的urls.py:

urlpatterns = patterns('',
    url(r'^create/$', CreateUserProfileView.as_view(), name='profile_create'),
    url(r'^view/$', UpdateUserProfileView.as_view(), name='profile_update'),
)

在views.py中,我添加了一个新类:

class GetProfileMixin(object):
    def get_object(self):
        profile = get_object_or_404(UserProfile, user=self.request.user)

        if profile.user != self.request.user:
            raise Http404
        return profile

并使用以下方法调用 UpdateUserProfileFormView:

class UpdateUserProfileView(LoginRequiredMixin, GetProfileMixin, UpdateView):
     model = UserProfile
     form_class = UserProfileForm

如果我重新访问 createview,再次保存对象时,会留下一些关于 url 和 userprofile 表中的 foreign_key 重复的小问题。我相信这是一个常见问题,我错过了明显的答案。

编辑 2:

更改了以下内容:

def form_valid(self, form):
    try:
        created = UserProfile.objects.get(user=self.request.user)
    except UserProfile.DoesNotExist:
        profile = form.save(commit=False)
        profile.user = self.request.user
        profile.save()
        return super(CreateUserProfileView, self).form_valid(form)
    return HttpResponseRedirect('/accounts/profile/')

不是最优雅的解决方案,即使当前配置文件内部有值,用户也会检索一个空表单,如果提交,只会重定向到配置文件页面。

【问题讨论】:

  • 您是想完全限制对其他用户的个人资料页面的访问,还是只想禁用编辑。
  • 希望限制对其他用户个人资料的访问。

标签: django django-views django-urls


【解决方案1】:

广告 0:不要在您的个人资料网址中使用 ID,只需使用“/profile”并从会话 (request.user) 中获取经过身份验证的用户数据

广告1:如果你有动态url,你需要使用“get_success_url”,然后使用带有适当参数的reverse

【讨论】:

  • 好主意。将我的网址更改为如下所示:url(r'^create/$', CreateUserProfileView.as_view(), name='profile_create'),url(r'^view/$', UpdateUserProfileView.as_view(), name='profile_update'),
【解决方案2】:
  1. 如何限制访问:

您必须明确检查 url 中的 id 是否与登录用户的 id 相同。缺少该检查,因此用户 1 能够查看用户 2 的个人资料。将其放在视图的开头。

  1. reverse_lazy 不工作:

您可以直接创建 url /profile/ 而不是从 django urls 反向匹配。

  1. 在保存时防止表单创建重复键的最佳做法是什么

在创建新对象之前,检查它是否已经存在并更新它。

【讨论】:

  • 我尝试添加try...catch 以检查配置文件是否存在,如果不存在,则保存 CreateView。但是,我收到一条错误消息,上面写着 null value in column "user_id" violates not-null constraint
  • 这意味着 user_id 字段不为空,并且您在创建配置文件对象时没有提供它。在 UserProfile 创建期间传递用户和其他参数。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2018-04-27
  • 1970-01-01
  • 2015-10-23
  • 1970-01-01
  • 1970-01-01
  • 2014-03-02
  • 1970-01-01
相关资源
最近更新 更多