Django模型:意外行为

时间:2011-12-05 15:02:24

标签: django django-models

我有这样的观点:

def finish_creation(request, pre_id):
    pre_post = PrePost.objects.get(pk = pre_id)
    if pre_id == pre_post.id:
        this = Post.objects.create(
            author = pre_post.author,
            title = pre_post.title,
            text = pre_post.text
        )

        this.pswd = some_password
        this.save()
        pre_post.delete()
        return HttpResponseRedirect(this.get_absolute_url())

说明:未经授权的用户(作者)可以在网站上写帖子,但首先在数据库中创建一些临时的pre_post,并向其中的链接发送电子邮件以激活(将临时pre_post转移到永久帖子)。在跟随链接从PrePost元素创建Post后,PrePost将从数据库中删除,用户将自动重定向到其发布的帖子。

错误Pre_Post matching query does not exist.

但其他一切都还可以:

1)帖子创造完美,

2)Pre_post删除完美,

且只有return HttpResponseRedirect(this.get_absolute_url())不起作用...

但是,错误页面在视图pre_post = PrePost.objects.get(pk = pre_id)

的第一行引用

怎么可能?

感谢。

编辑:

但是当我没有删除pre_post时,一切都按预期工作正常(删除pre_post除外)。删除()有什么问题?

1 个答案:

答案 0 :(得分:2)

这首先是非常糟糕的设计。您不应该将数据从一个表移动到另一个表来发布它。只需在一个模型中添加一个字段即可。例如:

class Post(models.Model):
    ...
    approved = models.BooleanField(default=False)

然后,您可以编写自定义管理器以仅提取已批准的帖子:

class PostManager(models.Manager):
    def approved(self):
        return self.filter(approved=True)

class Post(models.Model):
    ...
    objects = PostManager()

最后,在您的视图和模板中,只需使用Post.objects.approved(),而不是Post.objects.all()。因此,只有经过批准的帖子才能在网站上显示。

然后,当用户是超级用户或您想要的任何其他名称时,您只能在表单中显示approved字段,并且只有他们能够将其标记为已批准。

您还可以通过许多其他方式执行此操作,例如只有超级用户可以设置的“已发布”状态等,但这是一般性的想法。

编辑当前代码存在的问题是,对象不可能存在。您必须通过始终get块中包含对try...except的调用来解释这种可能性:

try:
    pre_post = PrePost.objects.get(pk = pre_id)
except PrePost.DoesNotExist:
    # Do something or...
    pass
else:
    # object exists; you can do stuff with it here.