我正在学习和尝试DRF。
我正在学习创建路线(端点)以对模型进行自定义修改的操作。
我成功地构造了:deactivate
,deactivate_all
,activate_all
。
但不是reverse_status
,这是为了将客户的当前状态更改为相反的状态。如果为customer.active = True
,则将其更改为False
,反之亦然。
我的动作:
@action(detail=False, methods=['PUT']) #when true only applies to 1 object / else to a list of objects
def reverse_status(self, request, **kwargs):
customers = Customer.objects.all()
import pdb; pdb.set_trace()
customers = [customer.update(active=False) for customer in customers if customer.active]
serializer = CustomerSerializer(customers, many=True)
return Response(serializer.data)
您注意到,我已经设置了一个断点,以了解列表理解后客户所持有的东西,但是它将转换为空列表:
原始:
<QuerySet [<Customer: Gregory>, <Customer: Julia>, <Customer: Naty>]>
列表理解后:
[]
为什么?
尝试这样的事情:
@action(detail=False, methods=['PUT'])
def reverse_status(self, request, **kwargs):
active_customers = Customer.objects.filter(active=True)
active_customers.update(active=False)
serializer = CustomerSerializer(active_customers, many=True)
return Response(serializer.data)
这应该可以解决问题:
@action(detail=False, methods=['PUT'])
def reverse_status(self, request, **kwargs):
Customer.objects.update(active=Q(active=False))
serializer = CustomerSerializer(Customer.objects.all(), many=True)
return Response(serializer.data)
Q(active=False)
构造具有翻转布尔值的魔力。
Q
的注释非常不完整doc上的Q
有点短而且开放。关于在过滤器表达式中使用它的例子有很多,但是描述暗示了更普遍的用法:
一个Q()对象,像F对象一样,将SQL表达式封装在一个可以在与数据库相关的操作中使用的Python对象。
通常,通过Q()对象可以定义和重用条件。这允许构建复杂的数据库查询使用| (OR)和&(AND)运算符;特别是不是可以在QuerySet中使用OR。
短语“定义和重用条件”显然是一个非常有力的通用声明。老实说,我不确定我是从哪儿首次了解到可以在filter
之外使用它的,但是在示例中here is an S/O answer除外。