Django模型方法与自定义管理器

时间:2019-01-23 18:54:27

标签: django orm model

在决定使用自定义管理器还是模型方法时遇到麻烦。我有一个模型User,并有一个查询来查找特定用户半径内的其他用户。

所以我的两个选择是:

class UserManager(models.Manager):
    def find_users_in_radius(self, user):
        return super().get_queryset().filter(
            location__distance_lt=(
                user.location, Distance(mi=user.search_radius))).exclude(
            pk=user.pk)

class User(AbstractUser):
    .....
    users_in_radius = UserManager()

User模型上的方法:

class User(AbstractUser):
    .....
    def users_in_search_radius(self):
        return User.objects.filter(
            location__distance_lt=(
                self.location, Distance(mi=self.search_radius))).exclude(
            pk=self.pk)

在我看来,我将使用第一种方法User.users_in_radius.find_users_in_radius(request.user)

获得查询结果。

或第二种方法:request.user.users_in_search_radius()

我更喜欢第二种选择,但是我想知道这是否是不好的做法。我还没有看到人们在模型方法中调用User.objects的任何示例。有另一种方法可以做到这一点,还是自定义管理器是更好的方法?

2 个答案:

答案 0 :(得分:1)

仅在要修改默认管理器(client.on('guildMemberAdd', member => { // Set the member's roles by id member.setRoles([/* role id here */]); // Don't know the role id? const role = guild.roles.find(role => role.name === 'your role name'); member.addRole(role); }); 或添加其他管理器方法(默认管理器中不存在)时才需要定义自定义管理器。

因此,如果您可以使用默认管理器而不必修改它,那么为什么要重新发明轮子。

答案 1 :(得分:1)

具体来说,您应该使用非管理器版本,如果使用定制管理器,那么您还将添加一个方法(不在管理器QuerySet上工作),并且还必须提供用户参数。

使用方法使用户实例负有寻找用户的责任。

更不用说您必须使用第一个选项编写更多的代码,而且它也会变慢。

user.user_in_radiuos.find_users_in_radius(user)  # Two attribute lookpus, redundance: calling object == parameter.
user.users_in_search_radius()  # Clean, no redundance.