Django 4.0 - Попытка выполнить запрос на основе результата другого запроса

Парни!

Вот что я пытаюсь сделать: У меня есть модель User, модель LinkedOrganization, модель Organization, которая выглядит следующим образом:

class User(AbstractBaseUser, PermissionsMixin):
    email = models.EmailField(db_index=True, unique=True)
    first_name = models.CharField(max_length=50)
    last_name = models.CharField(max_length=50)
    mobile = models.CharField(max_length=12)

    is_staff =  models.BooleanField(default=False)
    is_active = models.BooleanField(default=True)
    is_superuser = models.BooleanField(default=False)

    objects = UserManager()

    USERNAME_FIELD = 'email'
    REQUIRED_FIELDS = ['first_name', 'last_name', 'mobile']

    class Meta:
        verbose_name = 'User'
        verbose_name_plural = 'Users'

# Organization fields
class Organization(models.Model):
    organization_name = models.CharField(max_length=50, unique=True)
    
    def __str__(self):
        return self.organization_name

class LinkedOrganization(models.Model):
    user = models.ForeignKey(User, on_delete=models.CASCADE, related_name='linked_user')
    organization = models.ForeignKey(Organization, on_delete=models.CASCADE, related_name='linked_organization')
    is_manager = models.BooleanField(default=False)
    is_admin = models.BooleanField(default=False)
    class Meta:
        unique_together = (
            ("user", "organization")
        )

В моем API представлении я пытаюсь вернуть всех пользователей, которые связаны с организацией, менеджером которой является запросчик.

Теперь, один запросчик может быть менеджером 1 или более организаций, и мне нужно получить всех пользователей, связанных с этими организациями. То есть мне нужно, чтобы это было что-то вроде "является членом организации A" ИЛИ "является членом организации B", и итерация по всем организациям. Возможно ли это сделать с помощью Queryset в Django?

Когда я писал это, я понял, что могу просто получить организации и использовать ReverseObjectManager для получения пользователей организаций, просмотреть их и составить нужные мне словари в Python, но если получение запроса и использование результата в queryset является функцией Django, это будет проще.

Возможно, вам будет полезно использовать немного другую схему базы данных, не только для этого запроса, но и вообще. Рассмотрим следующее:

class User(AbstractBaseUser, PermissionsMixin):
    email        = models.EmailField(db_index=True, unique=True)
    first_name   = models.CharField(max_length=50)
    last_name    = models.CharField(max_length=50)
    mobile       = models.CharField(max_length=12)
    organization = models.ForeignKey('Organization', on_delete=models.CASCADE, related_name='user_organization')
    is_staff     = models.BooleanField(default=False)
    is_active    = models.BooleanField(default=True)
    is_superuser = models.BooleanField(default=False)

    objects = UserManager()

    USERNAME_FIELD = 'email'
    REQUIRED_FIELDS = ['first_name', 'last_name', 'mobile']

    class Meta:
        verbose_name = 'User'
        verbose_name_plural = 'Users'

# Organization fields
class Organization(models.Model):
    organization_name = models.CharField(max_length=50, unique=True)
    manager           = models.ForeignKey(User, etc...)
    
    def __str__(self):
        return self.organization_name

В этом сценарии у каждого пользователя есть организация, а у каждой организации есть менеджер. Просто. Также обратите внимание, что я сослался на 'Organization' в поле внешнего ключа как на строку, поскольку она объявлена выше, где определена модель Organization. Таким образом, вы можете сделать запрос следующим образом:

managed_users = User.objects.filter(user_organization__manager=request.user)

Обычной практикой является создание модели профиля для пользователя, куда могут быть добавлены дополнительные поля, такие как его организация, контактная информация и т.д. В этом случае у вас будет что-то вроде этого:

class Profile(models.Model):
    user         = models.OneToOneField(User, on_delete=models.CASCADE)
    organization = models.ForeignKey(Organization, etc...)
Вернуться на верх