【Dv3Admin】工具视图配置文件解析
在开发后台管理系统时,处理复杂的 CRUD 操作是常见的需求。Django Rest Framework(DRF)通过 ModelViewSet
提供了基础的增删改查功能,但在实际应用中,往往需要扩展更多的功能,如批量操作、权限控制、查询优化等。dvadmin/utils/viewset.py
模块通过继承并扩展 ModelViewSet
,为开发者提供了一个高效且统一的数据接口处理方案。
本文解析了 CustomModelViewSet
类的实现,重点讲解了如何通过自定义视图集扩展 Django 的标准视图功能,包含数据导入导出、权限控制、过滤查询等功能。此外,介绍了如何通过自定义方法实现批量删除等操作,以及如何优化查询性能,简化开发工作。
文章目录
- viewset.py
- 项目源码解析
- 应用案例
- 总结
viewset.py
dvadmin/utils/viewset.py
模块扩展了 Django 的 ModelViewSet
,通过自定义 CustomModelViewSet
类实现了统一的数据接口处理,包括新增、查询、更新、删除等常见操作。该模块集成了数据导入导出、权限控制、过滤查询等功能,并针对性能优化、序列化器灵活应用等方面提供了增强的支持,旨在简化和统一系统的 API 视图集实现。
项目特点 | 描述 |
---|---|
技术栈 | Django Rest Framework(DRF) |
功能定位 | 自定义视图集,支持标准化数据接口和高效的操作处理 |
性能优化 | 支持 values_queryset 以减少数据库查询开销 |
集成功能 | 导入导出、权限控制、查询过滤、批量操作 |
dvadmin/utils/viewset.py
主要通过继承 ModelViewSet
提供统一的 API 接口,定义了自定义视图集 CustomModelViewSet
。该视图集集成了 CRUD 操作的标准化响应,包括分页、序列化等处理,同时通过自定义过滤类和权限类扩展功能,确保了数据的高效查询与精确权限控制。此外,还提供了批量删除等批处理操作,并通过 swagger_auto_schema
生成接口文档。
模块职责 | 说明 |
---|---|
自定义视图集扩展 | 继承 ModelViewSet 实现统一的 API 操作 |
序列化器灵活应用 | 为不同方法使用不同的序列化器,如创建、更新、查询等操作 |
性能优化 | 通过 values_queryset 提高 ORM 查询效率 |
导入导出支持 | 提供 ImportSerializerMixin 和 ExportSerializerMixin 支持 |
批量删除功能 | 通过 multiple_delete 实现批量删除功能 |
在需要处理复杂的 CRUD 操作的后台管理系统中,dvadmin/utils/viewset.py
提供的 CustomModelViewSet
可以有效简化开发工作,同时保证接口的一致性与高效性。适用于大规模数据的批量处理、权限控制严格的 API 服务,以及多功能视图集的场景。
使用场景 | 说明 |
---|---|
后台管理系统数据管理 | 统一处理数据的增删改查,并支持批量删除与导入导出功能 |
高效数据查询与过滤 | 使用自定义过滤类 CoreModelFilterBankend 和 DataLevelPermissionsFilter 进行数据过滤 |
需要灵活权限控制的 API | 结合 CustomPermission 实现详细的权限控制与访问管理 |
数据批量操作 | 实现批量删除和导入数据等功能,减少重复代码并提高效率 |
接口文档自动生成 | 使用 swagger_auto_schema 自动生成接口文档,减少手动编写文档的工作 |
项目源码解析
自定义视图集类
CustomModelViewSet
是对 DRF 中 ModelViewSet
的扩展,结合了导入、导出、查询优化、数据权限控制等功能,提供了一个高可复用的标准视图集基础类。它支持分页查询、排序、动态序列化器切换、数据权限过滤,并实现了数据导入导出功能。此类结合了多个自定义混入(Mixin)和权限、过滤等功能,适用于复杂的业务场景。
class CustomModelViewSet(ModelViewSet, ImportSerializerMixin, ExportSerializerMixin, QueryArgumentsMixin):values_queryset = Noneordering_fields = '__all__'create_serializer_class = Noneupdate_serializer_class = Nonefilter_fields = '__all__'search_fields = ()extra_filter_class = [CoreModelFilterBankend, DataLevelPermissionsFilter]permission_classes = [CustomPermission]import_field_dict = {}export_field_label = {}
该方法继承自 DRF 的 ModelViewSet
,通过 filter_backends
和 extra_filter_class
来扩展查询集的过滤功能。可以在该方法中为不同的查询条件添加额外的过滤逻辑,满足权限和数据筛选需求。
def filter_queryset(self, queryset):for backend in set(set(self.filter_backends) | set(self.extra_filter_class or [])):queryset = backend().filter_queryset(self.request, queryset, self)return queryset
该方法用于返回资源的列表数据,支持分页。若请求中包含分页参数,则使用分页功能;否则,返回完整数据。数据经过序列化后,返回一个统一的成功响应格式。
def list(self, request, *args, **kwargs):queryset = self.filter_queryset(self.get_queryset())page = self.paginate_queryset(queryset)if page is not None:serializer = self.get_serializer(page, many=True, request=request)return self.get_paginated_response(serializer.data)serializer = self.get_serializer(queryset, many=True, request=request)return SuccessResponse(data=serializer.data, msg="获取成功")
该方法用于获取单个资源的详细信息,并返回该资源的序列化数据。如果资源不存在,DRF 会自动抛出 404 错误,并通过自定义的异常处理机制返回标准错误响应。
def retrieve(self, request, *args, **kwargs):instance = self.get_object()serializer = self.get_serializer(instance)return DetailResponse(data=serializer.data, msg="获取成功")
此方法处理资源的部分更新和完全更新。在更新时,使用不同的序列化器根据请求的字段进行数据验证,并保存更新后的资源。若更新成功,将返回带有更新数据的成功响应。
def update(self, request, *args, **kwargs):partial = kwargs.pop('partial', False)instance = self.get_object()serializer = self.get_serializer(instance, data=request.data, request=request, partial=partial)serializer.is_valid(raise_exception=True)self.perform_update(serializer)if getattr(instance, '_prefetched_objects_cache', None):instance._prefetched_objects_cache = {}return DetailResponse(data=serializer.data, msg="更新成功")
该方法实现删除功能,删除目标资源后返回成功响应。删除操作也会通过自定义的异常处理进行管理,保证数据的一致性和操作的原子性。
def destroy(self, request, *args, **kwargs):instance = self.get_object()instance.delete()return DetailResponse(data=[], msg="删除成功")
支持批量删除操作,通过 keys
列表提供待删除资源的主键。该方法通过 swagger_auto_schema
装饰器提供了 API 文档生成支持,帮助开发者生成清晰的接口文档。返回成功或失败信息。
@swagger_auto_schema(request_body=openapi.Schema(type=openapi.TYPE_OBJECT,required=['keys'],properties={'keys': keys}), operation_summary='批量删除')@action(methods=['delete'], detail=False)def multiple_delete(self, request, *args, **kwargs):request_data = request.datakeys = request_data.get('keys', None)if keys:self.get_queryset().filter(id__in=keys).delete()return SuccessResponse(data=[], msg="删除成功")else:return ErrorResponse(msg="未获取到keys字段")
应用案例
自定义视图集在后台管理系统中的应用
在后台管理系统中,处理复杂的 CRUD 操作是日常开发的常见需求。dvadmin/utils/viewset.py
模块通过继承 DRF 的 ModelViewSet
,扩展了标准的增删改查功能,增加了批量操作、权限控制、查询优化等功能,极大提升了开发效率和系统灵活性。CustomModelViewSet
为开发者提供了一个高效且统一的数据接口处理方案,使得复杂的业务逻辑可以通过标准化接口快速实现。
功能点 | 内容描述 |
---|---|
场景需求 | 在后台管理系统中高效处理复杂的 CRUD 操作,支持批量操作、权限控制、动态序列化器选择和查询优化等功能。 |
核心模块 | dvadmin/utils/viewset.py :扩展 DRF 的 ModelViewSet ,提供统一的数据接口处理方案,简化复杂业务逻辑的实现。 |
支持功能 | - 动态序列化器选择:根据不同的请求场景(如创建、更新、查询等)动态选择序列化器,提升灵活性。 |
- 批量操作支持:支持批量删除、批量更新等功能,简化大量数据的处理操作。 | |
- 查询优化:通过 values_queryset 等方法减少数据库查询开销,提升性能。 | |
- 权限控制:集成细粒度的权限控制机制,确保不同用户角色的访问安全性。 | |
- 导入导出功能:支持批量导入和导出数据,提升数据管理效率。 | |
实现机制 | - 继承 DRF 的 ModelViewSet:扩展默认的 CRUD 功能,适配复杂业务需求。 |
- 动态序列化器:通过重载 get_serializer_class 方法实现动态选择序列化器。 | |
- 优化查询集:通过自定义查询方法,减少冗余查询并提升响应效率。 |
例如,CustomModelViewSet
支持动态选择序列化器来适应不同的请求场景,如创建、更新、查询等操作都可以通过自定义序列化器来进行灵活处理。该视图集还支持查询优化,通过 values_queryset
等方法减少数据库查询的开销,同时支持批量删除和导入导出功能,简化了后端管理系统中大量数据操作的开发工作。
功能点 | 内容描述 |
---|---|
应用场景 | - 用户管理:实现用户信息的增删改查,支持批量禁用用户或导出用户数据。 |
- 商品管理:通过动态序列化器支持商品的多场景操作,如批量更新库存、导入商品列表等。 | |
- 日志管理:提供优化查询的日志数据接口,支持快速检索和批量导出。 | |
优势 | - 提升开发效率,减少重复代码编写。 - 增强系统灵活性,适应复杂业务场景。 - 提高查询性能,优化系统整体响应速度。 |
扩展能力 | - 支持更多批量操作类型,如批量审核、批量分配角色等。 - 增强导入导出功能,支持更多格式(如 CSV、JSON)。 |
自定义视图集的实际应用案例
在用户管理模块中,开发者通过 CustomModelViewSet
实现了统一的增删改查接口,同时加入了批量删除功能,允许管理员一次性删除多个用户,减少重复代码并提高效率。代码如下:
class UserViewSet(CustomModelViewSet):queryset = User.objects.all()serializer_class = UserSerializercreate_serializer_class = UserCreateSerializerupdate_serializer_class = UserUpdateSerializer@swagger_auto_schema(request_body=openapi.Schema(type=openapi.TYPE_OBJECT,required=['keys'],properties={'keys': openapi.Schema(type=openapi.TYPE_ARRAY, items=openapi.Items(type=openapi.TYPE_INTEGER))}), operation_summary='批量删除')@action(methods=['delete'], detail=False)def multiple_delete(self, request, *args, **kwargs):keys = request.data.get('keys', [])if keys:self.get_queryset().filter(id__in=keys).delete()return SuccessResponse(data=[], msg="删除成功")else:return ErrorResponse(msg="未获取到keys字段")
通过以上代码,管理员可以通过传递一个包含 keys
的列表进行批量删除,这样不仅提升了操作效率,还避免了单个删除操作的频繁请求。
分页与查询优化应用
在数据展示场景中,如用户列表、订单日志等,系统需要对大量数据进行分页展示。CustomModelViewSet
提供的分页机制能够通过 paginate_queryset
方法根据请求参数动态生成分页数据,同时支持查询优化,减少数据库的负担。以下代码展示了如何在视图集内实现分页查询:
class UserViewSet(CustomModelViewSet):queryset = User.objects.all()serializer_class = UserSerializerdef list(self, request, *args, **kwargs):queryset = self.filter_queryset(self.get_queryset())page = self.paginate_queryset(queryset)if page is not None:serializer = self.get_serializer(page, many=True, request=request)return self.get_paginated_response(serializer.data)serializer = self.get_serializer(queryset, many=True, request=request)return SuccessResponse(data=serializer.data, msg="获取成功")
在这个例子中,paginate_queryset
方法根据请求参数(如 page
和 limit
)对数据进行分页处理,而 get_paginated_response
方法则生成符合统一格式的分页响应数据,包含了分页所需的所有信息,如当前页、总页数、是否有下一页等字段。
导入导出功能的实现
除了基本的 CRUD 操作外,CustomModelViewSet
还支持数据的导入导出功能。例如,在用户管理模块中,管理员可以通过导入用户数据的接口批量上传用户信息,或将用户数据导出为 Excel 文件。代码示例如下:
class UserViewSet(CustomModelViewSet, ImportSerializerMixin, ExportSerializerMixin):queryset = User.objects.all()serializer_class = UserSerializer@action(methods=['post'], detail=False)def import_data(self, request, *args, **kwargs):import_serializer = UserImportSerializer(data=request.data)if import_serializer.is_valid():import_serializer.save()return SuccessResponse(data=[], msg="导入成功")return ErrorResponse(msg="导入失败")@action(methods=['get'], detail=False)def export_data(self, request, *args, **kwargs):users = self.get_queryset()export_serializer = UserExportSerializer(users, many=True)return SuccessResponse(data=export_serializer.data, msg="导出成功")
通过继承 ImportSerializerMixin
和 ExportSerializerMixin
,开发者能够快速实现数据的批量导入和导出功能。这个功能对于需要批量处理数据的场景非常实用,避免了手动操作的繁琐。
CustomModelViewSet
扩展了 Django Rest Framework 的 ModelViewSet
,结合了分页、排序、查询过滤、权限控制等功能,并提供了批量删除和数据导入导出的支持。该视图集统一了复杂业务逻辑的处理,减少了重复代码,增强了系统的可维护性和扩展性。
总结
CustomModelViewSet
基于 ModelViewSet
进行扩展,整合了分页、排序、查询过滤、权限控制等常见功能,减少了重复代码。通过混入多个功能类(如导入导出、查询优化),使得该视图集能适应复杂的业务场景,增强了灵活性和可扩展性。
虽然该模块提供了丰富的功能,但其复杂的多功能集成可能会增加理解和维护的难度。部分功能,如批量操作和数据导入导出,可以进一步拆分为独立模块,以提高可复用性和解耦性。此外,查询优化虽然得到了改进,但在高并发环境下仍有提升空间。