当我要求模型管理器获取一个对象时,当没有匹配的对象时,它会引发DoesNotExist。

go = Content.objects.get(name="baby")

而不是DoesNotExist,我怎么能去是None代替?


当前回答

这是Django get_object_or_404方法的一个副本,只是该方法返回None。当我们必须使用only()查询来只检索某些字段时,这是非常有用的。该方法可以接受模型或查询集。

from django.shortcuts import _get_queryset


def get_object_or_none(klass, *args, **kwargs):
    """
    Use get() to return an object, or return None if object
    does not exist.
    klass may be a Model, Manager, or QuerySet object. All other passed
    arguments and keyword arguments are used in the get() query.
    Like with QuerySet.get(), MultipleObjectsReturned is raised if more than
    one object is found.
    """
    queryset = _get_queryset(klass)
    if not hasattr(queryset, 'get'):
        klass__name = klass.__name__ if isinstance(klass, type) else klass.__class__.__name__
        raise ValueError(
            "First argument to get_object_or_none() must be a Model, Manager, "
            "or QuerySet, not '%s'." % klass__name
        )
    try:
        return queryset.get(*args, **kwargs)
    except queryset.model.DoesNotExist:
        return None

其他回答

你可以在过滤器中使用exists:

Content.objects.filter(name="baby").exists()
#returns False or True depending on if there is anything in the QS

如果你只想知道它是否存在,这是另一种选择

如果发生这样的事呢?

go = (Content.objects.filter(name="value") or [None])[0]

从django 1.6开始,你可以像这样使用first()方法:

Content.objects.filter(name="baby").first()

我们可以使用Django内置的异常,附加到模型命名为。doesnotexist。因此,我们不需要导入ObjectDoesNotExist异常。

而不是做:

from django.core.exceptions import ObjectDoesNotExist

try:
    content = Content.objects.get(name="baby")
except ObjectDoesNotExist:
    content = None

我们可以这样做:

try:
    content = Content.objects.get(name="baby")
except Content.DoesNotExist:
    content = None

从django 1.7开始,你可以这样做:

class MyQuerySet(models.QuerySet):

    def get_or_none(self, **kwargs):
        try:
            return self.get(**kwargs)
        except self.model.DoesNotExist:
            return None


class MyBaseModel(models.Model):

    objects = MyQuerySet.as_manager()


class MyModel(MyBaseModel):
    ...

class AnotherMyModel(MyBaseModel):
    ...

“MyQuerySet.as_manager()”的优点是以下两个都可以工作:

MyModel.objects.filter(...).get_or_none()
MyModel.objects.get_or_none()