I have 4 models -
class Group(models.model):
group_id = models.CharField(max_length=10)
name = models.CharField(max_length=20)
class User(models.model):
user_id = models.CharField(max_length=10)
grp = models.ForeignKey(Group, null=True, blank=True)
user_name = models.CharField(max_length=50)
contact_no = models.CharField(max_length=20)
class DesigType(models.model):
desig_name = models.CharField(max_length=10)
class Designation(models.model):
user = models.ForeignKey(User, null=True, blank=True, related_name='desigs')
desig_type = models.ForeignKey(DesigType, null=True, blank=True, related_name='desigs')
Group
model holds groups of users. User
holds records for each individual user. DesigType
has information about "type of designation", like maybe manager, team lead etc. Designation
stores the exact designation - for example, for manager DesigType
, Designation
might have project manager or account manager; similarly, for team lead DesigType
, Designation
might have front-end lead or back-end lead.
The UI currently shows a list of users under a group. I want to implement a search functionality according to desig_name
. The UI sends me the group_id
and the text entered by the end-user in the search box, and I have to return only those User
s which have the corresponding desig_name
.
I have already done the above, by using a property
to return a list of desig_name
s that a User
has and checking whether the user input exists in the list.
This is a property
under User
-
@cached_property
def desig_types(self):
desig_types = []
for value in self.desigs.select_related('desig_type').values('desig_type__desig_name'):
desig_types.append(value['desig_type__desig_name'])
return desig_types
In my view I have a generic search function which takes any user filter to return the appropriate list of users.
group = Groups.objects.get(pk=grp_id)
_queryset = group.user_set.filter(**user_filter)
The above code works for filtering according to contact_no
and user_name
. For contact_no
, **user_filter
is group.user_set.filter(contact_no=user_input)
, and for user_name
, it's group.user_set.filter(user_name=user_input)
. I want it to also work for filtering according to desig_name
, but I couldn't figure out how to navigate through the relationships so I wrote the code below, that retrieves a list of user_id
s which have the user inputted desig_name
.
required_users = []
for user in group.user_set.all():
user_desig_names = user.desig_types
if user_input in user_desig_names:
required_users.append(user.user_id)
return required_users
I then pass in the filter as group.user_set.filter(user_id__in=required_users)
. But as you see, I have to have an additional code to get the user_id
s, instead of directly using **user_filter
, like with user_name
or contact_no
.
Does anyone know how I can do that?