feat: 获取该批次的DAG图数据 支持仅直接关系

This commit is contained in:
caoqianming 2025-07-03 14:54:20 +08:00
parent 79f1322c27
commit e3067e115a
2 changed files with 53 additions and 42 deletions

View File

@ -1017,27 +1017,29 @@ def mlog_audit_end(ticket: Ticket):
mlog_submit(ins, ticket.create_by, now)
def get_batch_dag(batch_number: str, version=1):
try:
batch_ins = BatchSt.objects.get(batch=batch_number, version=version)
except Exception:
raise ParseError("该批次号未构建关系链")
# 收集所有相关批次和边
def get_batch_dag(batch_number: str, method="full"):
try:
batch_ins = BatchSt.objects.get(batch=batch_number, version=1)
except Exception:
raise ParseError("该批次号未构建关系链")
r_dict = {
"split": "",
"merge": ""
}
if method == "full":
# 完整DAG模式 - 收集所有相关批次和边(原逻辑)
nodes_set = {batch_ins.id}
edges = []
prev_size = 0
r_dict = {
"split": "",
"merge": ""
}
while len(nodes_set) > prev_size:
prev_size = len(nodes_set)
# 查询所有与当前批次相关的记录作为source或target
logs = BatchLog.objects.filter(Q(source__id__in=nodes_set) | Q(target__id__in=nodes_set)).select_related(
"source", "target"
).order_by("update_time")
# 处理每条记录,扩展节点和边
for log in logs:
source = log.source.id
target = log.target.id
@ -1047,33 +1049,42 @@ def get_batch_dag(batch_number: str, version=1):
'target': target,
"handover": log.handover.id if log.handover else None,
"mlog": log.mlog.id if log.mlog else None,
'label': r_dict.get(log.relation_type, ""), # 使用relation_type作为边的标签
'label': r_dict.get(log.relation_type, ""),
})
# 去重边
# unique_edges = {}
# for edge in edges:
# key = (edge['source'], edge['target'])
# if key not in unique_edges:
# unique_edges[key] = edge
# 将批次号排序
nodes_qs = BatchSt.objects.filter(id__in=nodes_set).order_by('update_time')
# batch_to_id = {batch: idx for idx, batch in enumerate(nodes_list)}
# 构建节点数据,默认使用'rect'形状
nodes = [{
'id': item.id,
'label': item.batch,
'shape': 'rect' # 可根据业务需求调整形状
} for item in nodes_qs]
# 构建边数据
# edges_converted = [{
# 'source': edge['source'],
# 'target': edge['target'],
# 'label': edge['label']
# } for edge in unique_edges.values()]
return {'nodes': nodes, 'edges': edges}
elif method == "direct":
# 直接关系模式 - 只查询直接相连的批次
nodes_set = {batch_ins.id}
edges = []
# 查询作为source或target的直接关系
logs = BatchLog.objects.filter(Q(source__id=batch_ins.id) | Q(target__id=batch_ins.id)).select_related(
"source", "target"
).order_by("update_time")
for log in logs:
source = log.source.id
target = log.target.id
nodes_set.update([source, target])
edges.append({
'source': source,
'target': target,
"handover": log.handover.id if log.handover else None,
"mlog": log.mlog.id if log.mlog else None,
'label': r_dict.get(log.relation_type, ""),
})
else:
raise ParseError("不支持的查询方法,请使用'full''direct'")
# 将批次号排序
nodes_qs = BatchSt.objects.filter(id__in=nodes_set).order_by('update_time')
nodes = [{
'id': item.id,
'label': item.batch,
'shape': 'rect'
} for item in nodes_qs]
return {'nodes': nodes, 'edges': edges}

View File

@ -927,10 +927,10 @@ class BatchLogViewSet(ListModelMixin, CustomGenericViewSet):
获取该批次的DAG图数据
"""
batch = request.data.get("batch", None)
version = request.data.get("version", 1)
method = request.data.get("method", "full")
if not batch:
raise ParseError("缺少batch参数")
return Response(get_batch_dag(batch, version))
return Response(get_batch_dag(batch, method))
@action(methods=['post'], detail=False, perms_map={'post': '*'}, serializer_class=Serializer)
def batches_to(self, request, *args, **kwargs):