I'm trying to filter category with age range. I want to see people with certain genders and then their age range.
My models:
from django.db import models
# Create your models here.
class catagory(models.Model):
name = models.CharField(max_length=150)
def __str__(self):
return self.name
class Age(models.Model):
range = models.CharField(max_length=150)
def __str__(self):
return self.range
class person(models.Model):
name = models.CharField(max_length=100)
gender = models.ForeignKey(catagory, on_delete=models.CASCADE)
age_range = models.ForeignKey(Age, on_delete=models.CASCADE)
@staticmethod
def get_person_by_cataegoryID(categoryID):
if categoryID:
return person.objects.filter(gender=categoryID)
else:
return person.objects.all()
@staticmethod
def get_person_by_age_range(AGE_RANGE):
if AGE_RANGE:
return person.objects.filter(age_range=AGE_RANGE)
else:
return person.objects.all()
def __str__(self):
return self.name
My views
from django.shortcuts import render
from .models import catagory,person,Age
# Create your views here.
def index(request):
c = catagory.objects.all()
categoryID = request.GET.get('category')
AGE_RANGE = request.GET.get('age_range')
p= person.objects.all()
a = Age.objects.all()
if categoryID:
persons = person.get_person_by_cataegoryID(categoryID)
elif AGE_RANGE:
persons = person.get_person_by_age_range(AGE_RANGE)
else:
persons = person.objects.all()
context = {
"person": p,
"catagory": c,
"age": a
}
context["person"] = persons
return render(request, "index.html", context)
My Template
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<h2>hello</h2>
<div style="display:flex;height:100vh;width:100vw;align-items:center;justify-content:space-around;">
<div style="display:flex;flex-direction:column;">
{% for a in age %}
<a href="/?age_range={{a.id}}">{{a.range}}</a>
{% endfor %}
</div>
<div style="display:flex;flex-direction:column;">
<a href="/">All</a>
{% for c in catagory %}
<a href="/?category={{c.id}}">{{c.name}}</a>
{% endfor %}
</div>
<br>
<div style="display:flex;flex-direction:column;">
{% for p in person %}
<p>{{p.name}}</p>
{% endfor %}
</div>
</div>
</body>
</html>
Please tell me what I'm doing wrong here. The filters work by themselves correctly but my goal is to see a specific gender and then that gender's age range. Currently it shows the gender and age range of the whole group.
CodePudding user response:
if you need gender and age at the same time:
if categoryID and AGE_RANGE:
persons = person.objects.filter(gender=categoryID, age_range=AGE_RANGE)
elif categoryID:
persons = person.get_person_by_cataegoryID(categoryID)
elif AGE_RANGE:
persons = person.get_person_by_age_range(AGE_RANGE)
else:
persons = person.objects.all()
CodePudding user response:
You can use **
dictionary unpacking to determine your model filters. The dictionary itself is created based on whether category/age_range exist in request.GET
:
category = request.GET.get('category')
age_range = request.GET.get('age_range')
filters = {}
if category:
filters['category'] = categoryID
if age_range:
filters['age_range'] = AGE_RANGE
persons = person.objects.filter(**filters)
If filters is an empty dict then it has the same effect as calling all()
Edit - you could also use a list an dict comprehension to remove the if-statement:
fields = ['category','age_range']
filters = {k: v for k, v in request_GET.items() if k in fields and v is not None}