这样如何通过非模型远程字段进行订购?

问题描述

我有一张这样的桌子:

class SystemPushLog(models.Model):
    ...
    user_id = models.IntegerField(null=True)

您在上面的模型中可以看到,user_idIntegerField,而不是外键。从gRPC调用中检索出Cuz用户信息输出系统。现在,我想通过last_login来排序查询集,这是用户信息中的一个字段。 我在annotate中尝试过使用get_queryset

    def get_queryset(self):
        queryset = super().get_queryset().annotate(
            last_login=self.__class__.get_user_last_login(F('user_id'))
        )

下面是get_user_last_login

    @staticmethod
    def get_user_last_login(user_id):
        print('user_id',user_id)  # <<< user_id F(user_id)
        print('type of user_id',type(user_id))  # <<< type of user_id <class 'django.db.models.expressions.F'>

        # retrieving user info from rpc call.
        user = do_user_actions({'id': user_id})
        return user.last_login

如您所见,传递给函数F('user_id')django.db.models.expressions.F的一种类型,而不是实际的user_id

也许annotate可以采用一些简单的表达式,例如annotate(off_price=F('original_price') - F('discount_price'))

那么,我应该如何实现这种远程现场订购?

解决方法

如果您不介意在SystemPushLog中添加last_login字段,可以通过将last_login字段设置为空,则可以通过覆盖django @classmethod def create()来填充last_login,因为它具有last_login字段,因此可以轻松订购模型

我还没有尝试过,但是类似的东西应该可以工作

def create(self,*args,**kwargs):
    if 'user_id' in kwargs and isinstance(kwargs['type'],int):
        # retrieving user info from rpc call.
        user = do_user_actions({'id': user_id})
        kwargs['last_login'] = user.last_login
    return super(SystemPushLog,self).create(*args,**kwargs)

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...