Django-autocomplete-light 的使用(二)

本文介绍如何使用django-autocomplete-light库优化大型数据集的多选字段选择,减少后台负载,提高用户体验。内容包括安装、项目设置、模型配置、路由与视图函数的添加以及forms.py的修改,通过示例展示了使用该库前后的后台界面差异。

django-autocomplete-light 使用(二)

背景摘要

当我们在使用 dajngo admin 或者 xadminforeignKey 字段时, 后台默认提供是 select2 复选框, 加入我们该字段对应的数据量很多时, 会出现加载很慢的情况,出现这种情况是由于后台默认会给我们加载出该字段所有 model 提供我们去选择, 但实际情况我们只需要其中的某个 model 与当前 model对应即可, 减少不必要的开销。查找相关资料发现django-autocomplete-light能解决该问题。

django-autocomplete-light 使用

安装

pip install django-autocomplete-light
pip install django-querysetsequence

项目 setting 文件中配置相关 django-autocomplete-light app

INSTALLED_APPS = [
‘dal’, # 新增(注意顺序, 最好放在首位)
‘dal_select2’, # 新增
‘django.contrib.admin’,
‘django.contrib.auth’,
‘django.contrib.contenttypes’,
‘django.contrib.sessions’,
‘django.contrib.messages’,
‘django.contrib.staticfiles’,
‘xadmin’,
‘crispy_forms’,
‘reversion’,
]

models.py

class User(models.Model):
    id = models.BigIntegerField(primary_key=True)
    name = models.CharField(max_length=32)
    avatar = models.CharField(max_length=255)
    expiredAt = models.BigIntegerField()

    def expired_time(self):
        if self.expiredAt:
            local_time = time.localtime(self.expiredAt / 1000.0)
            format_time = time.strftime("%Y-%m-%d %H:%M:%S", local_time)
        else:
            format_time = ''
        return format_time

    class Meta:
        db_table = 'user'

    def __str__(self):
        return 'userId: %s-username: %s' %(self.id, self.name)


class Project(models.Model):
   id = models.BigIntegerField(primary_key=True)
    name = models.CharField(max_length=32)
    createdAt = models.BigIntegerField()

    def created_time(self):
        if self.createdAt:
            local_time = time.localtime(self.createdAt / 1000.0)
            format_time = time.strftime("%Y-%m-%d %H:%M:%S", local_time)
        else:
            format_time = ''
        return format_time

    class Meta:
        db_table = 'project'

    def __str__(self):
        return 'projectId: %s-projectName: %s' %(self.id, self.name)


lass UserProjectRelationship(models.Model):
    userId = models.ForeignKey(User, on_delete=None, db_column='userId')
    projectId = models.ForeignKey(Project, on_delete=None, db_column='projectId')
    enable = models.BooleanField(default=True)
    createdAt = models.BigIntegerField()

    def created_time(self):
        if self.createdAt:
            local_time = time.localtime(self.createdAt / 1000.0)
            format_time = time.strftime("%Y-%m-%d %H:%M:%S", local_time)
        else:
            format_time = ''
        return format_time

    def save(self, *args, **kwargs):
        current_time = time.time() * 1000
        if not self.createdAt:
            self.createdAt = current_time
        super(UserProjectRelationship, self).save(*args, **kwargs)

    class Meta:
        db_table = 'user_project_relationship'

app 中配置路由

from django.conf.urls import url

from project import views

urlpatterns = [
    url(r'^user-autocomplete/$', views.UserAutoComplete.as_view(), name='user-autocomplete'),
    url(r'^project-autocomplete/$', views.ProjectAutoComplete.as_view(), name='project-autocomplete'),
]
app 中增加视图函数
from django.shortcuts import render
from dal import autocomplete
from django.db.models import Q

from . models import User, Project
# Create your views here.

class UserAutoComplete(autocomplete.Select2QuerySetView):
    def get_queryset(self):
        if not self.request.user.is_authenticated:			# 这里校验是否为登录用户
            return User.objects.none()

        if self.q:
            qs = User.objects.all()
            qs = qs.filter(Q(id__icontains=self.q) | Q(name__icontains=self.q))	# 复选框搜索条件(id 和 名称)
        else:
            qs = User.objects.none()
        return qs


class ProjectAutoComplete(autocomplete.Select2QuerySetView):
    def get_queryset(self):
        if not self.request.user.is_authenticated:
            return Project.objects.none()

        if self.q:
            qs = Project.objects.all()
            qs = qs.filter(Q(id__icontains=self.q) | Q(name__icontains=self.q))
        else:
            qs = Project.objects.none()
        return qs`

app 中添加 forms.py 文件

from django import forms
from dal import autocomplete

from .models import ProjectServiceResultTypeRelationship, UserProjectRelationship

class UserProjectRelationshipForm(forms.ModelForm):
    class Meta:
        model = UserProjectRelationship
        fields = ('__all__')
        widgets = {
            'userId': autocomplete.ModelSelect2(url='user-autocomplete'),
            'projectId': autocomplete.ModelSelect2(url='project-autocomplete')
        }

```

### adminx.py 文件中使用对应的 forms models
```
import xadmin
from xadmin import views
from .models import UserProjectRelationship
from .forms import UserProjectRelationshipForm

@xadmin.sites.register(UserProjectRelationship)
class UserProjectRelationshipModelAdmin(object):
    form = UserProjectRelationshipForm 		# 使用 forms.py 中定义的 UserProjectRelationshipForm
    list_display = ['id', 'userId', 'projectId', 'created_time']
    list_filter = ['id', 'userId', 'projectId']
    exclude = ['createdAt']

进入后台:

  • 加入 auto-complete-light 后台展示

在这里插入图片描述
在这里插入图片描述

  • 未加入 auto-complete-light 后台展示:
    在这里插入图片描述
    注意⚠️:使用 django 版本在 2.2 以下,否则可能会出现 django-auto-complete-light 不生效
    django-auto-complete-light demo
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值