|
|
@@ -10,8 +10,7 @@ from sqlalchemy.ext.asyncio import AsyncSession
|
|
|
from sqlalchemy import select, update, and_, or_
|
|
|
from app.sample.models.tag_category import TagCategory
|
|
|
from app.sample.schemas.tag_category import (
|
|
|
- TagCategoryCreate, TagCategoryUpdate, TagCategoryResponse,
|
|
|
- TagCategoryTreeNode
|
|
|
+ TagCategoryCreate, TagCategoryUpdate, TagCategoryResponse
|
|
|
)
|
|
|
from app.services.user_service import UserService
|
|
|
|
|
|
@@ -56,6 +55,7 @@ class TagCategoryService:
|
|
|
tag_category = TagCategory(
|
|
|
parent_id=tag_data.parent_id,
|
|
|
name=tag_data.name,
|
|
|
+ type=tag_data.type or "label",
|
|
|
path=path,
|
|
|
level=level,
|
|
|
sort_no=tag_data.sort_no or 0,
|
|
|
@@ -106,7 +106,10 @@ class TagCategoryService:
|
|
|
) -> List[TagCategoryResponse]:
|
|
|
"""列表查询标签分类"""
|
|
|
try:
|
|
|
- conditions = [TagCategory.is_deleted == 0]
|
|
|
+ conditions = [
|
|
|
+ TagCategory.is_deleted == 0,
|
|
|
+ TagCategory.type == 'label'
|
|
|
+ ]
|
|
|
|
|
|
if parent_id is not None:
|
|
|
conditions.append(TagCategory.parent_id == parent_id)
|
|
|
@@ -121,7 +124,7 @@ class TagCategoryService:
|
|
|
result = await self.session.execute(query)
|
|
|
categories = result.scalars().all()
|
|
|
|
|
|
- return await self._enrich_list_with_user_names(categories)
|
|
|
+ return await self._enrich_list_with_user_names(categories, parent_id)
|
|
|
|
|
|
except Exception as e:
|
|
|
logger.error(f"查询标签分类列表失败: {str(e)}")
|
|
|
@@ -180,6 +183,8 @@ class TagCategoryService:
|
|
|
|
|
|
if tag_data.name is not None:
|
|
|
tag_category.name = tag_data.name
|
|
|
+ if tag_data.type is not None:
|
|
|
+ tag_category.type = tag_data.type
|
|
|
if tag_data.sort_no is not None:
|
|
|
tag_category.sort_no = tag_data.sort_no
|
|
|
if tag_data.status is not None:
|
|
|
@@ -229,7 +234,7 @@ class TagCategoryService:
|
|
|
self,
|
|
|
root_id: int = 0,
|
|
|
include_disabled: bool = False
|
|
|
- ) -> List[TagCategoryTreeNode]:
|
|
|
+ ) -> List[TagCategory]:
|
|
|
"""获取标签分类树"""
|
|
|
try:
|
|
|
conditions = [TagCategory.is_deleted == 0]
|
|
|
@@ -242,32 +247,75 @@ class TagCategoryService:
|
|
|
)
|
|
|
all_categories = result.scalars().all()
|
|
|
|
|
|
- return self._build_tree(all_categories, root_id)
|
|
|
+ # 构建树
|
|
|
+ tree = self._build_tree(all_categories, root_id)
|
|
|
+
|
|
|
+ # 为树节点添加 parent_name 和用户名称
|
|
|
+ await self._enrich_tree_with_names(tree, all_categories)
|
|
|
+
|
|
|
+ return tree
|
|
|
|
|
|
except Exception as e:
|
|
|
logger.error(f"获取分类树失败: {str(e)}")
|
|
|
raise
|
|
|
|
|
|
@staticmethod
|
|
|
- def _build_tree(categories: List[TagCategory], parent_id: int = 0) -> List[TagCategoryTreeNode]:
|
|
|
+ def _build_tree(categories: List[TagCategory], parent_id: int = 0) -> List[TagCategory]:
|
|
|
"""递归构建树形结构"""
|
|
|
tree = []
|
|
|
for cat in categories:
|
|
|
if cat.parent_id == parent_id:
|
|
|
children = TagCategoryService._build_tree(categories, cat.id)
|
|
|
- node = TagCategoryTreeNode(
|
|
|
- id=cat.id,
|
|
|
- parent_id=cat.parent_id,
|
|
|
- name=cat.name,
|
|
|
- path=cat.path,
|
|
|
- level=cat.level,
|
|
|
- sort_no=cat.sort_no,
|
|
|
- status=cat.status,
|
|
|
- children=children if children else None
|
|
|
- )
|
|
|
- tree.append(node)
|
|
|
+ # 直接设置 cat 的 children 属性
|
|
|
+ cat.children = children if children else None
|
|
|
+ tree.append(cat)
|
|
|
return tree
|
|
|
|
|
|
+ async def _enrich_tree_with_names(self, tree: List[TagCategory], all_categories: List[TagCategory]) -> None:
|
|
|
+ """为树节点批量填充 parent_name 和用户名称"""
|
|
|
+ # 构建 category id 到 name 的映射
|
|
|
+ category_map = {cat.id: cat.name for cat in all_categories}
|
|
|
+
|
|
|
+ # 收集所有用户ID
|
|
|
+ user_ids = set()
|
|
|
+ for cat in all_categories:
|
|
|
+ if cat.created_by:
|
|
|
+ user_ids.add(cat.created_by)
|
|
|
+ if cat.updated_by:
|
|
|
+ user_ids.add(cat.updated_by)
|
|
|
+
|
|
|
+ # 批量查询用户信息
|
|
|
+ user_map = {}
|
|
|
+ for user_id in user_ids:
|
|
|
+ try:
|
|
|
+ user = await self.user_service.get_user_by_id(user_id)
|
|
|
+ if user:
|
|
|
+ user_map[user_id] = user.username
|
|
|
+ except Exception as e:
|
|
|
+ logger.warning(f"查询用户 {user_id} 失败: {str(e)}")
|
|
|
+
|
|
|
+ # 递归填充每个节点
|
|
|
+ self._enrich_node_with_names(tree, category_map, user_map)
|
|
|
+
|
|
|
+ def _enrich_node_with_names(self, nodes: List[TagCategory], category_map: dict, user_map: dict) -> None:
|
|
|
+ """递归为节点填充名称"""
|
|
|
+ for node in nodes:
|
|
|
+ # 填充 parent_name
|
|
|
+ if node.parent_id != 0:
|
|
|
+ node.parent_name = category_map.get(node.parent_id)
|
|
|
+ else:
|
|
|
+ node.parent_name = None
|
|
|
+
|
|
|
+ # 填充用户名称
|
|
|
+ if node.created_by:
|
|
|
+ node.created_by_name = user_map.get(node.created_by)
|
|
|
+ if node.updated_by:
|
|
|
+ node.updated_by_name = user_map.get(node.updated_by)
|
|
|
+
|
|
|
+ # 递归处理子节点
|
|
|
+ if hasattr(node, 'children') and node.children:
|
|
|
+ self._enrich_node_with_names(node.children, category_map, user_map)
|
|
|
+
|
|
|
async def get_breadcrumb(self, category_id: int) -> List[Dict[str, Any]]:
|
|
|
"""获取分类的面包屑路径"""
|
|
|
try:
|
|
|
@@ -451,8 +499,8 @@ class TagCategoryService:
|
|
|
|
|
|
return response
|
|
|
|
|
|
- async def _enrich_list_with_user_names(self, categories: List[TagCategory]) -> List[TagCategoryResponse]:
|
|
|
- """为分类列表批量填充用户名"""
|
|
|
+ async def _enrich_list_with_user_names(self, categories: List[TagCategory], parent_id: Optional[int] = None) -> List[TagCategoryResponse]:
|
|
|
+ """为分类列表批量填充用户名和父分类名"""
|
|
|
if not categories:
|
|
|
return []
|
|
|
|
|
|
@@ -472,12 +520,24 @@ class TagCategoryService:
|
|
|
if user:
|
|
|
user_map[user_id] = user.username
|
|
|
|
|
|
+ # 如果指定了 parent_id,所有分类都有相同的父分类,只需查询一次
|
|
|
+ parent_name = None
|
|
|
+ if parent_id is not None and parent_id != 0:
|
|
|
+ result = await self.session.execute(
|
|
|
+ select(TagCategory).where(TagCategory.id == parent_id)
|
|
|
+ )
|
|
|
+ parent = result.scalar_one_or_none()
|
|
|
+ if parent:
|
|
|
+ parent_name = parent.name
|
|
|
+
|
|
|
# 构建响应列表
|
|
|
result = []
|
|
|
for cat in categories:
|
|
|
response = TagCategoryResponse.model_validate(cat)
|
|
|
response.created_by_name = user_map.get(cat.created_by) if cat.created_by else None
|
|
|
response.updated_by_name = user_map.get(cat.updated_by) if cat.updated_by else None
|
|
|
+ # 如果指定了 parent_id,使用查询出的 parent_name;否则为 None
|
|
|
+ response.parent_name = parent_name if parent_id is not None and parent_id != 0 else None
|
|
|
result.append(response)
|
|
|
|
|
|
return result
|