mirror of
https://github.com/1Panel-dev/MaxKB.git
synced 2025-12-26 18:32:48 +00:00
166 lines
6.4 KiB
Python
166 lines
6.4 KiB
Python
# -*- coding: utf-8 -*-
|
|
|
|
import uuid_utils.compat as uuid
|
|
from django.db import transaction
|
|
from django.db.models import QuerySet, Q
|
|
from django.utils.translation import gettext_lazy as _
|
|
from rest_framework import serializers
|
|
|
|
from common.constants.permission_constants import Group
|
|
from knowledge.models import KnowledgeModule
|
|
from modules.api.module import ModuleCreateRequest
|
|
from tools.models import ToolModule
|
|
from tools.serializers.tool_module import ToolModuleTreeSerializer
|
|
|
|
|
|
def get_module_type(source):
|
|
if source == Group.TOOL.name:
|
|
return ToolModule
|
|
elif source == Group.APPLICATION.name:
|
|
# todo app module
|
|
return None
|
|
elif source == Group.KNOWLEDGE.name:
|
|
return KnowledgeModule
|
|
else:
|
|
return None
|
|
|
|
|
|
MODULE_DEPTH = 2 # Module 不能超过3层
|
|
|
|
|
|
def check_depth(source, parent_id, current_depth=0):
|
|
# Module 不能超过3层
|
|
Module = get_module_type(source)
|
|
|
|
if parent_id != 'root':
|
|
# 计算当前层级
|
|
depth = 1 # 当前要创建的节点算一层
|
|
current_parent_id = parent_id
|
|
|
|
# 向上追溯父节点
|
|
while current_parent_id != 'root':
|
|
depth += 1
|
|
parent_node = QuerySet(Module).filter(id=current_parent_id).first()
|
|
if parent_node is None:
|
|
break
|
|
current_parent_id = parent_node.parent_id
|
|
|
|
# 验证层级深度
|
|
if depth + current_depth > MODULE_DEPTH:
|
|
raise serializers.ValidationError(_('Module depth cannot exceed 3 levels'))
|
|
|
|
|
|
def get_max_depth(current_node):
|
|
if not current_node:
|
|
return 0
|
|
|
|
# 获取所有后代节点
|
|
descendants = current_node.get_descendants()
|
|
|
|
if not descendants.exists():
|
|
return 0
|
|
|
|
# 获取最大深度
|
|
max_level = descendants.order_by('-level').first().level
|
|
current_level = current_node.level
|
|
max_depth = max_level - current_level
|
|
|
|
return max_depth
|
|
|
|
|
|
class ModuleSerializer(serializers.Serializer):
|
|
id = serializers.CharField(required=True, label=_('module id'))
|
|
name = serializers.CharField(required=True, label=_('module name'))
|
|
user_id = serializers.CharField(required=True, label=_('module user id'))
|
|
workspace_id = serializers.CharField(required=False, allow_null=True, allow_blank=True, label=_('workspace id'))
|
|
parent_id = serializers.CharField(required=False, allow_null=True, allow_blank=True, label=_('parent id'))
|
|
|
|
class Create(serializers.Serializer):
|
|
user_id = serializers.UUIDField(required=True, label=_('user id'))
|
|
source = serializers.CharField(required=True, label=_('source'))
|
|
|
|
def insert(self, instance, with_valid=True):
|
|
if with_valid:
|
|
self.is_valid(raise_exception=True)
|
|
ModuleCreateRequest(data=instance).is_valid(raise_exception=True)
|
|
|
|
workspace_id = self.data.get('workspace_id', 'default')
|
|
parent_id = instance.get('parent_id', 'root')
|
|
name = instance.get('name')
|
|
|
|
Module = get_module_type(self.data.get('source'))
|
|
if QuerySet(Module).filter(name=name, workspace_id=workspace_id, parent_id=parent_id).exists():
|
|
raise serializers.ValidationError(_('Module name already exists'))
|
|
# Module 不能超过3层
|
|
check_depth(self.data.get('source'), parent_id)
|
|
|
|
module = Module(
|
|
id=uuid.uuid7(),
|
|
name=instance.get('name'),
|
|
user_id=self.data.get('user_id'),
|
|
workspace_id=workspace_id,
|
|
parent_id=parent_id
|
|
)
|
|
module.save()
|
|
return ModuleSerializer(module).data
|
|
|
|
class Operate(serializers.Serializer):
|
|
id = serializers.CharField(required=True, label=_('module id'))
|
|
workspace_id = serializers.CharField(required=True, allow_null=True, allow_blank=True, label=_('workspace id'))
|
|
source = serializers.CharField(required=True, label=_('source'))
|
|
|
|
@transaction.atomic
|
|
def edit(self, instance):
|
|
self.is_valid(raise_exception=True)
|
|
Module = get_module_type(self.data.get('source'))
|
|
current_id = self.data.get('id')
|
|
current_node = Module.objects.get(id=current_id)
|
|
if current_node is None:
|
|
raise serializers.ValidationError(_('Module does not exist'))
|
|
|
|
edit_field_list = ['name']
|
|
edit_dict = {field: instance.get(field) for field in edit_field_list if (
|
|
field in instance and instance.get(field) is not None)}
|
|
|
|
QuerySet(Module).filter(id=current_id).update(**edit_dict)
|
|
|
|
# 模块间的移动
|
|
parent_id = instance.get('parent_id')
|
|
if parent_id is not None and current_id != 'root':
|
|
# Module 不能超过3层
|
|
current_depth = get_max_depth(current_node)
|
|
check_depth(self.data.get('source'), parent_id, current_depth)
|
|
parent = Module.objects.get(id=parent_id)
|
|
current_node.move_to(parent)
|
|
|
|
return self.one()
|
|
|
|
def one(self):
|
|
self.is_valid(raise_exception=True)
|
|
Module = get_module_type(self.data.get('source'))
|
|
module = QuerySet(Module).filter(id=self.data.get('id')).first()
|
|
return ModuleSerializer(module).data
|
|
|
|
def delete(self):
|
|
self.is_valid(raise_exception=True)
|
|
if self.data.get('id') == 'root':
|
|
raise serializers.ValidationError(_('Cannot delete root module'))
|
|
Module = get_module_type(self.data.get('source'))
|
|
QuerySet(Module).filter(id=self.data.get('id')).delete()
|
|
|
|
|
|
class ModuleTreeSerializer(serializers.Serializer):
|
|
workspace_id = serializers.CharField(required=True, allow_null=True, allow_blank=True, label=_('workspace id'))
|
|
source = serializers.CharField(required=True, label=_('source'))
|
|
|
|
def get_module_tree(self, name=None):
|
|
self.is_valid(raise_exception=True)
|
|
Module = get_module_type(self.data.get('source'))
|
|
if name is not None:
|
|
nodes = Module.objects.filter(Q(workspace_id=self.data.get('workspace_id')) &
|
|
Q(name__contains=name)).get_cached_trees()
|
|
else:
|
|
nodes = Module.objects.filter(Q(workspace_id=self.data.get('workspace_id'))).get_cached_trees()
|
|
serializer = ToolModuleTreeSerializer(nodes, many=True)
|
|
return serializer.data # 这是可序列化的字典
|