转自:https://www.jianshu.com/p/a86281df530e

Django多条件筛选查询

主模型只存在外键一对多关系

模型设计

# 快捷筛选状态
class Status(models.Model):
order_number = models.PositiveIntegerField(unique=True, verbose_name='状态编号')
status_tag = models.CharField(max_length=10, verbose_name='状态名称') class Meta:
ordering = ['order_number', ]
verbose_name = '事件选择'
verbose_name_plural = verbose_name def __str__(self):
return self.status_tag # 项目分类
class Project(models.Model):
project_name = models.CharField(max_length=10, verbose_name='项目名称') class Meta:
ordering = ['project_name']
verbose_name = '项目分类'
verbose_name_plural = verbose_name def __str__(self):
return self.project_name # 事件分类
class Category(models.Model):
category_name = models.CharField(max_length=10, verbose_name='分类名称') class Meta:
ordering = ['category_name', ]
verbose_name = '事件分类'
verbose_name_plural = verbose_name def __str__(self):
return self.category_name # 事件级别
class Level(models.Model):
order_number = models.PositiveIntegerField(unique=True, verbose_name='级别编号')
level_tag = models.CharField(max_length=10, verbose_name='级别名称') class Meta:
ordering = ['order_number', ]
verbose_name = '事件级别'
verbose_name_plural = verbose_name def __str__(self):
return self.level_tag # 事件内容
class EventContent(models.Model):
title = models.CharField(max_length=50, verbose_name='事件标题')
content = models.TextField(verbose_name='事件正文')
image = models.ImageField(upload_to='images/%Y/%m', blank=True, null=True, verbose_name='描述图片')
created = models.DateTimeField(auto_now_add=True, verbose_name='创建时间')
updated = models.DateTimeField(auto_now=True, verbose_name='更新时间')
status = models.ForeignKey(Status, on_delete=models.SET_NULL, null=True, blank=True, related_name='event_content', verbose_name='事件状态')
project = models.ForeignKey(Project, on_delete=models.SET_NULL, null=True, blank=True, related_name='event_content', verbose_name='项目分类')
category = models.ForeignKey(Category, on_delete=models.CASCADE, related_name='event_content', verbose_name='事件分类')
level = models.ForeignKey(Level, on_delete=models.SET_NULL, null=True, blank=True, related_name='event_content', verbose_name='事件级别')
user = models.ForeignKey(User, related_name='event_content', verbose_name='创建人')
start_time = models.DateTimeField(default=timezone.now, verbose_name='事件开始时间')
end_time = models.DateTimeField(default=timezone.now, verbose_name='事件结束时间')
pause_time = models.DateTimeField(default=timezone.now, verbose_name='事件暂停时间') class Meta:
ordering = ['-created']
verbose_name = '事件内容'
verbose_name_plural = verbose_name def time_interval(self):
time_diff = (self.end_time-timezone.now())
days = time_diff.days
seconds = time_diff.seconds
minutes = seconds // 60 # 得到这些秒换算的分钟整数
second = seconds % 60 # 得到除去分钟后剩余的秒数
hours = minutes // 60
minute = minutes % 60
if self.status.order_number == 6:
return '事件已关闭!'
if days <= -1:
return '处理已超时!' return '{}天{}时{}分'.format(days, hours, minute) def __str__(self):
return self.title def get_content_as_markdown(self):
"""
当使用Mardown功能时,我们需要先让它转义一下特殊字符,然后再解析出Markdown标签。
这样做之后,输出字符串可以安全的在模板中使用。
:return:
"""
return mark_safe(markdown(self.content, safe_mode='escape'))

路由设计

    url(r'^event/$', event, name='event'),
url(r'^event-(?P<user_id>\d+)-(?P<status_id>\d+)-(?P<level_id>\d+)-(?P<category_id>\d+)-(?P<project_id>\d+).html$', event, name='event_filter'),

视图设计

该视图只需要查看kwargs有值的情况

def get_group_url_list(url):
"""
将访问的url存储在列表中,用于前端判断
EVENT_MENU_GROUP : 事件菜单组
OTHER_MENU_GROUP : 其他菜单组
:param url:
:return:
"""
group_url_list = list()
group_url_list.append(url)
return group_url_list # 显示事件列表
def event(request, **kwargs):
print('视图**kwargs的值:', kwargs)
if not kwargs:
# 原来的事件列表和post筛选
# events = EventContent.objects.all()
queryset = EventContent.objects.all()
if request.method == 'POST':
visit_url = reverse('event')
event_url_list = get_group_url_list(visit_url) filter_event_form = FilterEventForm(request.POST)
if filter_event_form.is_valid():
print('表单验证通过')
user = filter_event_form.cleaned_data['user']
status = filter_event_form.cleaned_data['status']
project = filter_event_form.cleaned_data['project']
category = filter_event_form.cleaned_data['category']
level = filter_event_form.cleaned_data['level']
queryset = queryset.filter(user=user, status=status, project=project, category=category, level=level)
print(queryset)
else:
visit_url = reverse('event')
event_url_list = get_group_url_list(visit_url) filter_event_form = FilterEventForm() page = request.GET.get('page', 1)
paginator = Paginator(queryset, settings.PAGE_NUM) # paginator是分页对象
try:
events = paginator.page(page)
except PageNotAnInteger:
events = paginator.page(1)
except EmptyPage:
events = paginator.page(paginator.num_pages)
return render(request, 'event.html',
{
'events': events,
'EVENT_MENU_GROUP': event_url_list,
'filter_event_form': filter_event_form,
'old_filter': True
})
else:
"""
多条件事件筛选
event-(?P<user_id>\d+)-(?P<status_id>\d+)-(?P<level_id>\d+)-(?P<category_id>\d+)-(?P<project_id>\d+).html
{'user_id': '0', 'status_id': '0', 'level_id': '0', 'category_id': '0', 'project_id': '0'}
"""
filter_dict = dict()
request_path = request.path
print('请求地址:', request_path)
if kwargs['user_id'] != '0':
filter_dict['user'] = get_object_or_404(User, id=kwargs['user_id'])
if kwargs['status_id'] != '0':
filter_dict['status'] = get_object_or_404(Status, id=kwargs['status_id'])
if kwargs['level_id'] != '0':
filter_dict['level'] = get_object_or_404(Level, id=kwargs['level_id'])
if kwargs['category_id'] != '0':
filter_dict['category'] = get_object_or_404(Category, id=kwargs['category_id'])
if kwargs['project_id'] != '0':
filter_dict['project'] = get_object_or_404(Project, id=kwargs['project_id']) user_list = User.objects.all().values('id', 'username')
# print(user_list)
status_list = Status.objects.all().values('id', 'status_tag')
# print(status_list)
level_list = Level.objects.all().values('id', 'level_tag')
category_list = Category.objects.all().values('id', 'category_name')
project_list = Project.objects.all().values('id', 'project_name') url_id_list = kwargs.values() # url中所有id:[0, 0, 0, 0, 0 ]
visit_url = reverse('event_filter', args=url_id_list)
event_url_list = get_group_url_list(visit_url)
queryset = EventContent.objects.filter(**filter_dict)
page = request.GET.get('page', 1)
paginator = Paginator(queryset, settings.PAGE_NUM) # paginator是分页对象
try:
events = paginator.page(page)
except PageNotAnInteger:
events = paginator.page(1)
except EmptyPage:
events = paginator.page(paginator.num_pages)
return render(request, 'event.html',
{
'events': events,
'EVENT_MENU_GROUP': event_url_list,
'user_list': user_list,
'status_list': status_list,
'level_list': level_list,
'category_list': category_list,
'project_list': project_list,
})

模板设计

<div class="card-header">
<h3 class="card-title">事件列表</h3>
</div>
<!-- /.card-header -->
{% if old_filter %}
<div class="card-body card-comment">
<form role="form" action="{% url 'event' %}?page=2" method="post">
<div class="row">
<div class="col-2">
<div class="input-group mb-12">
{% with filter_event_form.user as filter_fields %}
<div class="input-group-prepend">
<label class="input-group-text {% if filter_fields.errors %}bg-danger {% endif %}" for="{{ filter_fields.id_for_label }}">{{ filter_fields.label }}</label>
</div>
<select class="form-control col-sm-12" name="user" id="{{ filter_fields.id_for_label }}">
<option>{% for select in filter_fields %}{{ select }}{% endfor %}</option>
</select>
{% endwith %}
</div>
</div>
<div class="col-2">
<div class="input-group mb-12">
{% with filter_event_form.status as filter_fields %}
<div class="input-group-prepend">
<label class="input-group-text {% if filter_fields.errors %}bg-danger{% endif %}" for="{{ filter_fields.id_for_label }}">{{ filter_fields.label }}</label>
</div>
<select class="form-control col-sm-12" name="status" id="{{ filter_fields.id_for_label }}">
<option>{% for select in filter_fields %}{{ select }}{% endfor %}</option>
</select>
{% endwith %}
</div>
</div>
<div class="col-2">
<div class="input-group mb-12">
{% with filter_event_form.project as filter_fields %}
<div class="input-group-prepend">
<label class="input-group-text {% if filter_fields.errors %}bg-danger {% endif %}" for="{{ filter_fields.id_for_label }}">{{ filter_fields.label }}</label>
</div>
<select class="form-control col-sm-12" name="project" id="{{ filter_fields.id_for_label }}">
<option>{% for select in filter_fields %}{{ select }}{% endfor %}</option>
</select>
{% endwith %}
</div>
</div>
<div class="col-2">
<div class="input-group mb-12">
{% with filter_event_form.category as filter_fields %}
<div class="input-group-prepend">
<label class="input-group-text {% if filter_fields.errors %}bg-danger {% endif %}" for="{{ filter_fields.id_for_label }}">{{ filter_fields.label }}</label>
</div>
<select class="form-control col-sm-12" name="category" id="{{ filter_fields.id_for_label }}">
<option>{% for select in filter_fields %}{{ select }}{% endfor %}</option>
</select>
{% endwith %}
</div>
</div>
<div class="col-2">
<div class="input-group mb-12">
{% with filter_event_form.level as filter_fields %}
<div class="input-group-prepend">
<label class="input-group-text {% if filter_fields.errors %}bg-danger {% endif %}" for="{{ filter_fields.id_for_label }}">{{ filter_fields.label }}</label>
</div>
<select class="form-control col-sm-12" name="level" id="{{ filter_fields.id_for_label }}">
<option>{% for select in filter_fields %}{{ select }}{% endfor %}</option>
</select>
{% endwith %}
</div>
</div>
<button type="submit" class="btn btn-primary">筛选事件</button>
</div>
{% csrf_token %}
</form>
</div>
{% else %}
<div class="card-body d-flex p-0">
<h3 class="card-title p-3">用户</h3>
<ul class="nav nav-pills p-2">
{% active_all request.path 1 %}
{% for user_item in user_list %}
{% active request.path user_item 1 %}
{% endfor %}
</ul>
</div>
<div class="card-body d-flex p-0">
<h3 class="card-title p-3">状态</h3>
<ul class="nav nav-pills p-2">
{% active_all request.path 2 %}
{% for status_item in status_list %}
{% active request.path status_item 2 %}
{% endfor %}
</ul>
</div>
<div class="card-body d-flex p-0">
<h3 class="card-title p-3">级别</h3>
<ul class="nav nav-pills p-2">
{% active_all request.path 3 %}
{% for level_item in level_list %}
{% active request.path level_item 3 %}
{% endfor %}
</ul>
</div>
<div class="card-body d-flex p-0">
<h3 class="card-title p-3">分类</h3>
<ul class="nav nav-pills p-2">
{% active_all request.path 4 %}
{% for category_item in category_list %}
{% active request.path category_item 4 %}
{% endfor %}
</ul>
</div>
<div class="card-body d-flex p-0">
<h3 class="card-title p-3">项目</h3>
<ul class="nav nav-pills p-2">
{% active_all request.path 5 %}
{% for project_item in project_list %}
{% active request.path project_item 5 %}
{% endfor %}
</ul>
</div>
{% endif %}

链接生成模板标签

使用模板标签,在应用下创建templatetags的python包,然后创建active.py文件,需要在模板中通过{% load active %}引入模板标签。

from django.utils.safestring import mark_safe
from django import template register = template.Library() @register.simple_tag
def active_all(request_path, index):
url_part_list = request_path.split('-')
# print(url_part_list)
# ['/event', '0', '0', '0', '0', '0.html']
# 第五组带.html,需要分开判断 if url_part_list[index] == '0' or url_part_list[index] == '0.html':
temp = '''
<li class="nav-item">
<a class="nav-link active" href="{href}">全部</a>
</li>
'''
else:
temp = '''
<li class="nav-item">
<a class="nav-link" href="{href}">全部</a>
</li>
''' if index != 5:
url_part_list[index] = '0'
else:
url_part_list[index] = '0.html' href = '-'.join(url_part_list)
return mark_safe(temp.format(href=href)) @register.simple_tag
def active(request_path, item, index):
url_part_list = request_path.split('-')
# 下面判断中,前面表示 event-0-1-5-1-,后面表示 3.html
if url_part_list[index] == str(item['id']) or url_part_list[index] == str(item['id']) + '.html':
temp = '''
<li class="nav-item">
<a href="{href}" class="nav-link active">{name}</a>
</li>
'''
else:
temp = '''
<li class="nav-item">
<a href="{href}" class="nav-link">{name}</a>
</li>
'''
if index == 5:
# 第五组有后缀.html,需单独处理
url_part_list[index] = str(item['id']) + '.html'
else:
url_part_list[index] = str(item['id'])
href = '-'.join(url_part_list) if index == 1:
"""
event-1-0-0-0-0.html
event-2-0-0-0-0.html
event-3-0-0-0-0.html
"""
return mark_safe(temp.format(href=href, name=item['username']))
if index == 2:
return mark_safe(temp.format(href=href, name=item['status_tag']))
if index == 3:
return mark_safe(temp.format(href=href, name=item['level_tag']))
if index == 4:
return mark_safe(temp.format(href=href, name=item['category_name']))
if index == 5:
return mark_safe(temp.format(href=href, name=item['project_name']))

两级分类筛选

模型设计

from django.db import models
from django.utils.timezone import now class GoodsTag(models.Model):
name = models.CharField(max_length=64, verbose_name='标签名称') def __str__(self):
return self.name class Meta:
ordering = ['name', ]
verbose_name = '商品标签' # 后台显示模型名称
verbose_name_plural = verbose_name # 智能家居、手机、电视、电脑
class FirstCategory(models.Model):
name = models.CharField(max_length=64, verbose_name='分类名称') def __str__(self):
return self.name class Meta:
ordering = ['name', ]
verbose_name = '一级分类'
verbose_name_plural = verbose_name # 小米6、小米8、红米10
class SubCategory(models.Model):
name = models.CharField(max_length=64, verbose_name='分类名称')
first_category = models.ForeignKey(FirstCategory, related_name='sub_categories', verbose_name='上级分类') def __str__(self):
return self.name class Meta:
ordering = ['name', ]
verbose_name = '二级分类'
verbose_name_plural = verbose_name class GoodsInfo(models.Model):
STATUS_CHOICES = (
(1, '上架'),
(2, '下架'),
) title = models.CharField(max_length=100, verbose_name='标题')
content = models.TextField(blank=True, null=True, verbose_name='正文')
image = models.FileField(upload_to='images/goods/%Y/%m', blank=True, null=True, verbose_name='图片')
status = models.IntegerField(choices=STATUS_CHOICES, default=1, verbose_name='状态')
created_time = models.DateTimeField(auto_now_add=True, verbose_name='创建时间')
publish_time = models.DateTimeField(blank=True, null=True, default=now, verbose_name='发布时间')
updated_time = models.DateTimeField(auto_now=True, verbose_name='更新时间')
category = models.ForeignKey(SubCategory, on_delete=models.CASCADE, related_name='goods_info', verbose_name='所属分类')
tags = models.ManyToManyField(GoodsTag, blank=True, verbose_name='标签集合') def __str__(self):
return self.title class Meta:
verbose_name = '商品信息'
verbose_name_plural = verbose_name

主路由

urlpatterns = [
url(r'^test/', include('multiple_filter.urls', namespace='test')),
]

应用路由

访问 http://127.0.0.1:8000/test/goods.html 可跳转到 http://127.0.0.1:8000/test/goods-0-0-0-0.html

urlpatterns = [
url(r'^goods.html$', goods, name='goods'),
url(r'^goods-(?P<first_category_id>\d+)-(?P<sub_category_id>\d+)-(?P<tags_id>\d+)-(?P<status_id>\d+).html', goods, name='goods_filter'),
]

视图

from .models import GoodsTag, FirstCategory, SubCategory, GoodsInfo
from django.shortcuts import get_object_or_404 def goods(request, **kwargs):
if not kwargs:
return redirect('test:goods_filter', first_category_id='0', sub_category_id='0', tags_id='0', status_id='0')
else:
request_path = request.path
print('\n当前请求路径:', request_path, '\n')
print('kwargs:', kwargs) # {'first_category_id': '0', 'sub_category_id': '0', 'tags_id': '0', 'status_id': '0'} goods_tag_list = GoodsTag.objects.all().values('id', 'name')
first_category_list = FirstCategory.objects.all().values('id', 'name')
sub_category_list = SubCategory.objects.all().values('id', 'name')
status_list = list(map(lambda x: {'id': x[0], 'status': x[1]}, GoodsInfo.STATUS_CHOICES))
filter_dict = dict() if kwargs['first_category_id'] == '0':
# goods-0-x-x-x.html
if kwargs['sub_category_id'] != '0':
# goods-0-1-x-x.html
sub_category = get_object_or_404(SubCategory, id=kwargs['sub_category_id'])
# 选择二级分类后,由于多对一关系,一级分类也会跟着变化
first_category_list = [{'id': sub_category.first_category.id, 'name': sub_category.first_category.name}]
filter_dict['category'] = sub_category
else:
# 一级分类不为0,需要进行筛选
# goods-1-x-x-x.html
first_category = get_object_or_404(FirstCategory, id=kwargs['first_category_id'])
sub_category_list = first_category.sub_categories.values('id', 'name') # 选择一级分类后获取二级分类的列表
if kwargs['sub_category_id'] != '0':
sub_category = get_object_or_404(SubCategory, id=kwargs['sub_category_id'], first_category=first_category)
# 选择二级分类后,由于多对一关系,一级分类也会跟着变化
first_category_list = [{'id': sub_category.first_category.id, 'name': sub_category.first_category.name}]
filter_dict['category'] = sub_category if kwargs['tags_id'] != '0':
filter_dict['tags'] = kwargs['tags_id'] if kwargs['status_id'] != '0':
filter_dict['status'] = int(kwargs['status_id']) goods_list = GoodsInfo.objects.filter(**filter_dict) return render(request, 'goods.html',
{
'first_category_list': first_category_list,
'sub_category_list': sub_category_list,
'goods_tag_list': goods_tag_list,
'status_list': status_list,
'goods_list': goods_list
})

模板

<!DOCTYPE html>
{% load goods_active %}
<html lang="en">
<head>
<meta charset="UTF-8">
<title>多条件筛选</title>
</head>
<body>
{% active_all request.path 1 %}
{% for first_category in first_category_list %}
{% active request.path first_category 1 %}
{% endfor %}
<br><br>
{% active_all request.path 2 %}
{% for sub_category in sub_category_list %}
{% active request.path sub_category 2 %}
{% endfor %}
<br><br>
{% active_all request.path 3 %}
{% for goods_tag in goods_tag_list %}
{% active request.path goods_tag 3 %}
{% endfor %}
<br><br>
{% active_all request.path 4 %}
{% for status in status_list %}
{% active request.path status 4 %}
{% endfor %}
<p>
{% for goods in goods_list %}
<p>
【{{ goods.title }}】{{ goods.content }}
</p>
{% endfor %}
</p>
</body>
</html>

链接生成模板标签

应用下创建templatetags包,创建 goods_active.py 文件,用来放置模板标签

from django.utils.safestring import mark_safe
from django import template register = template.Library() @register.simple_tag
def active_all(current_url, index):
"""
获取当前url,进行值修改拼接
:param current_url: http://127.0.0.1:8000/test/goods-0-0-0-0.html
:param index:
:return:
"""
a_href_active = """
<a href="{href}" class="active">【全部】</a>
"""
a_href_unactive = """
<a href="{href}">全部</a>
"""
url_part_list = current_url.split('-')
if index == len(url_part_list)-1: # 最后一个带.html要特殊处理
if url_part_list[index] == '0.html':
a_href = a_href_active
else:
a_href = a_href_unactive url_part_list[index] = '0.html'
else:
if url_part_list[index] == '0':
a_href = a_href_active
else:
a_href = a_href_unactive url_part_list[index] = '0' href = '-'.join(url_part_list)
a_href = a_href.format(href=href)
return mark_safe(a_href) @register.simple_tag
def active(current_url, item, index):
"""
获取当前url,进行值修改拼接
:param current_url: http://127.0.0.1:8000/test/goods-0-0-0-0.html
:param index:
:return:
"""
a_href_active = """
<a href="{href}" class="active">【{name}】</a>
"""
a_href_unactive = """
<a href="{href}">{name}</a>
"""
url_part_list = current_url.split('-')
if index == len(url_part_list)-1: # 最后一个带.html要特殊处理
if url_part_list[index] == str(item['id']) + '.html':
a_href = a_href_active
else:
a_href = a_href_unactive url_part_list[index] = str(item['id']) + '.html'
else:
# print(item['id'], type(item['id'])) # item['id']是int类型
if url_part_list[index] == str(item['id']):
a_href = a_href_active
else:
a_href = a_href_unactive url_part_list[index] = str(item['id']) href = '-'.join(url_part_list)
if index in range(1, 4):
a_href = a_href.format(href=href, name=item['name'])
if index == len(url_part_list)-1:
a_href = a_href.format(href=href, name=item['status'])
return mark_safe(a_href)

多对多模型进行筛选

模型

# 课程分类
class Category(models.Model):
weight = models.IntegerField(verbose_name='权重(按从大到小排列)', default=0)
name = models.CharField(max_length=32, verbose_name='分类名称') class Meta:
verbose_name = '分类方向'
verbose_name_plural = verbose_name def __str__(self):
return self.name # 编程语言,一个课程分类里可能有多种编程语言,一种编程语言可能存在不同的课程分类
class Code(models.Model):
weight = models.IntegerField(default=0, verbose_name='权重(按从大到小排列)')
name = models.CharField(max_length=32, verbose_name='编程语言')
category = models.ManyToManyField(Category, related_name='codes', verbose_name='课程分类') class Meta:
verbose_name = '编程语言'
verbose_name_plural = verbose_name def __str__(self):
return self.name # 课程详情
class Course(models.Model):
STATUS_CHOICE = (
(0, '下线'),
(1, '上线')
) LEVEL_CHOICE = (
(1, '初级'),
(2, '中级'),
(3, '高级')
) status = models.IntegerField(choices=STATUS_CHOICE, default=1, verbose_name='状态')
level = models.IntegerField(choices=LEVEL_CHOICE, default=1, verbose_name='难度级别')
category = models.ForeignKey(Category, null=True, blank=True, related_name='courses', verbose_name='课程分类')
weight = models.IntegerField(default=0, verbose_name='权重(按从大到小排列)')
title = models.CharField(max_length=32, verbose_name='标题')
summary = models.CharField(max_length=100, verbose_name='简介')
image = models.ImageField(upload_to='images/course/%Y/%m', verbose_name='图片')
video_url = models.CharField(max_length=256, verbose_name='视频地址')
create_time = models.DateTimeField(auto_now_add=True, verbose_name='创建时间') class Meta:
verbose_name = '课程详情'
verbose_name_plural = verbose_name def __str__(self):
return self.title

路由

urlpatterns = [
# 访问形式http://127.0.0.1:8000/test/course-0-0-0.html,
# 第一个0代表课程分类,第二个0代表编程语言,第三个0代表课程级别
# 0代表全部,然后递增,当选择课程分类中的第一项,第一个0就会变成1
url(r'^course-(?P<code_id>\d+)-(?P<category_id>\d+)-(?P<level_id>\d+).html', course, name='course'),
]

视图

def course(request, *args, **kwargs):
print(args, kwargs) # () {'code_id': '0', 'category_id': '0', 'level_id': '0'}
request_path = request.path # http://127.0.0.1:8000/test/course-0-0-0.html # 筛选字典
filter_dict = dict() code_list = Code.objects.all().values('id', 'name')
category_list = Category.objects.all().values('id', 'name')
level_list = list(map(lambda x: {'id': x[0], 'name': x[1]}, Course.LEVEL_CHOICE)) if kwargs['code_id'] == '0':
if kwargs['category_id'] != '0':
category_list = Category.objects.filter(id=kwargs['category_id']).values('id', 'name')
category = get_object_or_404(Category, id=kwargs['category_id'])
# 分类不是全部,得到这个分类对应的所有编程语言
code_list = category.codes.values('id', 'name')
# 筛选这一分类
filter_dict['category'] = category
else:
# 如果编程语言不为0,则获取对应的编程语言
code = get_object_or_404(Code, id=kwargs['code_id'])
# 得到编程语言对应的所有分类
categories = code.category.all()
category_list = categories.values('id', 'name')
# 筛选课程在这些分类的结果
filter_dict['category__in'] = categories
if kwargs['category_id'] != '0':
# 如果分类不为0,对分类进行筛选,得到该编程语言和该分类下的结果
category = get_object_or_404(categories, id=kwargs['category_id'])
code_list = category.codes.values('id', 'name')
filter_dict['category'] = category if kwargs['level_id'] != '0':
filter_dict['level'] = int(kwargs['level_id']) filter_dict['status'] = 1 course_list = Course.objects.filter(**filter_dict)
return render(request, 'course.html',
{
'category_list': category_list,
'code_list': code_list,
'level_list': level_list,
'course_list': course_list,
})

模板

<!DOCTYPE html>
{% load course_active %}
<html lang="en">
<head>
<meta charset="UTF-8">
<title>多条件筛选多对多模型</title>
</head>
<body> <h3>选择:</h3> <p>
编程语言:
{% active_all request.path 1 %}
{% for code in code_list %}
<!--{{ code }}-->
{% active request.path code 1 %}
{% endfor %}
</p> <p>
课程分类:
{% active_all request.path 2 %}
{% for category in category_list %}
<!--{{ category }}-->
{% active request.path category 2 %}
{% endfor %}
</p> <p>
课程信息:
{% active_all request.path 3 %}
{% for level in level_list %}
<!--{{ level }}-->
{% active request.path level 3 %}
{% endfor %}
</p> <h3>视频:</h3>
{% for course in course_list %}
<a class="item" href="{{ course.video.url }}">
<img src="/media/{{ course.image }}" width="300px" height="200px">
<p>《{{ course.title }}》{{ course.summary }}</p>
<hr>
</a>
{% endfor %} </body>
</html>

链接生成模板标签

应用下创建templatetags包,创建 course_active.py 文件,用来放置模板标签

from django.utils.safestring import mark_safe
from django import template register = template.Library() @register.simple_tag
def active_all(current_url, index):
"""
获取当前url, course-1-1-2.html
:param current_url:
:param index:
:return:
"""
url_part_list = current_url.split('-')
if index == 3:
if url_part_list[index] == '0.html':
temp = '<a href="%s" class="active">【全部】</a>'
else:
temp = '<a href="%s"">全部</a>' url_part_list[index] = '0.html'
else:
if url_part_list[index] == '0':
temp = '<a href="%s" class="active">【全部】</a>'
else:
temp = '<a href="%s"">全部</a>' url_part_list[index] = '0' url_str = '-'.join(url_part_list) temp = temp % (url_str, )
return mark_safe(temp) @register.simple_tag
def active(current_url, item, index):
"""
course-0-0-1.html
:param current_url:
:param item:
:param index:
:return:
"""
# print('\n当前访问地址:', current_url, item, index, type(index))
url_part_list = current_url.split('-')
# print(url_part_list) # ['/test/course', '0', '0', '0.html']
if index == 3:
if str(item['id']) == url_part_list[3].split('.')[0]: # 如果当前标签被选中
temp = '<a href="%s" class="active">【%s】</a>'
else:
temp = '<a href="%s"">%s</a>' url_part_list[index] = str(item['id']) + '.html' # 拼接对应位置的url else:
if str(item['id']) == url_part_list[index]:
temp = '<a href="%s" class="active">【%s】</a>'
else:
temp = '<a href="%s">%s</a>' url_part_list[index] = str(item['id']) url_str = '-'.join(url_part_list) # 拼接整体url
# print(url_str)
temp = temp % (url_str, item['name']) # 生成对应的a标签
return mark_safe(temp)

Django多条件筛选查询的更多相关文章

  1. HBase多条件筛选查询方案

    最近的项目需要使用Hbase做实时查询,由于Hbase只支持一级索引,也就是使用rowkey作为索引查询,所以对于多条件筛选查询的支持不够,在不建立二级索引的情况下,只能使用Hbase API中提供的 ...

  2. c#中如何不通过后台直接用js筛选gridview中的数据条件筛选查询?

    js: //条件筛选 var showstate = true; function imagechange() { if (showstate) { $('#_toggle').hide(500, f ...

  3. js前端 多条件筛选查询

    一.前言 在做项目中,遇到多条件筛选案例.实现完成以后,我将我做的代码分享在这里,希望可以帮助到其他朋友. 二.效果截图 三.实现代码 首先我先类型.类别.职位分成三块来处理,如果传到服务器端的话,就 ...

  4. django多条件筛选搜索(项目实例)

    多条件搜索在很多网站上都有用到,比如京东,淘宝,51cto,等等好多购物教育网站上都有,当然网上也有很多开源的比楼主写的好的多了去了,仅供参考,哈哈 先来一张效果图吧,不然幻想不出来是什么样的,前端样 ...

  5. sql条件为空查询全部,不为空按条件查询以及多条件筛选查询。

    procedure queryLackLonOrLatTdCell(i_region_name varchar2, i_state varchar2) is begin select region_n ...

  6. JDBC动态查询MySQL中的表(按条件筛选)

    动态查询实现按条件筛选.PreparedStatement 准备语句指定要查询的表头列,.setString()通过赋值指定行,.executeQuery()执行语句 在数据库test里先创建表sch ...

  7. Asp.net Core C#进行筛选、过滤、使用PredicateBuilder进行动态拼接lamdba表达式树并用作条件精准查询,模糊查询

    在asp.net core.asp.net 中做where条件过滤筛选的时候写的长而繁琐不利于维护,用PredicateBuilder进行筛选.过滤.LInq配合Ef.core进行动态拼接lamdba ...

  8. 齐博x1where 标签动态变量查询/where 实现条件筛选与数据关联

    大家可能对union参数不太习惯的话,也可以用where语句加入动态变量查询,比如 where="fid=$fid&uid=$info[uid]&pid>=$info. ...

  9. Django框架 之 ORM查询操作详解

    Django框架 之 ORM查询操作详解 浏览目录 一般操作 ForeignKey操作 ManyToManyField 聚合查询 分组查询 F查询和Q查询 事务 Django终端打印SQL语句 在Py ...

随机推荐

  1. Java中很少用的CopyOnWriteArrayList

    类注释 /** * A thread-safe variant of {@link java.util.ArrayList} in which all mutative * operations ({ ...

  2. 非阻塞多路IO

    socket.listen() rfds=[] wfds=[] while(select(rfds,wfds,timeout)){//事件循环 client=socket.accept(timeout ...

  3. 吴裕雄--天生自然JAVAIO操作学习笔记:内存操作流、管道流与打印流操作

    import java.io.* ; class Send implements Runnable{ // 线程类 private PipedOutputStream pos = null ; // ...

  4. windows下安装多台mysql数据库且实现主从复制

    版本如下: windows server 2012 R2 mysql server 5.7.25安装版 / mysql server 5.7.25 解压版 * 这里为啥还要有安装版和解压版勒,主要是因 ...

  5. 【LeetCode】三角形最小路径和

    [问题]给定一个三角形,找出自顶向下的最小路径和.每一步只能移动到下一行中相邻的结点上.例如,给定三角形: [ [], [,], [,,], [,,,] ] 自顶向下的最小路径和为 (即, + + + ...

  6. other#一些问题的列表

    centos7及以后修改hostname, hostnamectl set-hostname centos7 centos7之前修改hostname, vi /etc/sysconfig/networ ...

  7. JS:利用for循环进行数组去重

    <script> var a = [1, 3, 2, 4, 5, 3, 2, 1, 4, 6, 7, 7, 6, 6]; //示例数组    var b = []; for(var i = ...

  8. 已解决!kali桌面无法放置快捷方式问题

    kali不知从哪个版本更新之后桌面上就不能添加快捷方式了,经过一番折腾找到了解决方法. 1.终端运行命令:apt-get install gnome-shell-extension-desktop-i ...

  9. POJ2533:Longest Ordered Subsequence

    Longest Ordered Subsequence Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 37454   Acc ...

  10. Windows按键消息—虚拟键码(转)

    源地址:http://c.biancheng.net/cpp/html/1253.html 虚拟键码保存在WM_KEYDOWN.WM_KEYUP.WM_SYSKEYDOWN和WM_SYSKEYUP消息 ...