OT-Trace 資料治理模板從 OT-Trace 資料中按 traceId 組裝完整對話,經三級去重、語義聚類、多樣性採樣、AI 評估和標註,實現 Trace 層級的 Agent 資料全鏈路治理。
業務情境
AI Agent 在運行過程中產生海量對話資料,直接使用存在大量重複和雜訊。本模板實現 Trace 層級的完整資料治理鏈路,覆蓋從原始 Span 資料到高品質標註資料集的全流程。
主要治理能力:
資料群組裝:將離散 Span 按 traceId 彙總為完整對話寬表,每行代表一條完整 Trace。
三級去重:精確去重、近似去重、語義去重逐級清洗重複資料,大幅降低資料量。
多樣性採樣:語義聚類 + 分組採樣,確保樣本覆蓋多種情境。
AI 評估:對採樣資料進行多維度品質評分。
AI 標註:自動標註任務類型、複雜度、業務領域等標籤。
Pipeline 流程
本模板的 Pipeline 由 4 個階段、12 個節點群組成,完整運算元鏈為:where > extend > make-instance > extend > where > dedup-exact > dedup-fuzzy > dedup-semantic > semantic-cluster > sample > llm-call x 2。
Phase 1:資料群組裝
將 OT-Trace 中的離散 Span 組裝為完整的 Trace 級寬表。
順序 | 節點 | 說明 |
1 | 過濾出包含 | |
2 | 按 Span Kind(ENTRY、LLM、TOOL、AGENT)預先處理欄位,提取使用者輸入、模型資訊、Token 用量、工具調用等結構化資料。 | |
3 | 按 | |
4 | 派生統計指標(總 Token 數、Span 數、LLM 調用次數、工具調用次數、耗時毫秒),並提取使用者查詢文本和完整對話全文。 | |
5 | 過濾出包含有效使用者輸入的 Trace,排除缺少使用者查詢的空記錄。 |
Phase 2:三級去重
遞進式去重:精確去重、近似去重、語義去重逐級清洗,大幅降低資料量。
順序 | 節點 | 說明 |
6 | 基於SimHash完全符合,去除 | |
7 | 基於SimHash海明距離,去除 | |
8 | 基於 Embedding 向量距離,去除語義含義相似的記錄。預設閾值為 0.1。 |
Phase 3:多樣性採樣
對去重後的資料進行語義聚類和分組採樣,確保產出資料覆蓋多種情境。
順序 | 節點 | 說明 |
9 | 複用語義去重階段產生的 | |
10 | 按 |
Phase 4:AI處理
對採樣後的代表性資料進行AI 品質評估和情境標註。
順序 | 節點 | 說明 |
11 | llm-call(評估) | 使用Prompt模板 |
12 | llm-call(標註) | 使用 |
完整配置
本模板提供 JSON 配置格式。
以下為完整的 Pipeline JSON 配置,可直接通過 API 提交建立 Pipeline。
{
"name": "ot_trace_data_governance",
"description": "OT-Trace Trace 粒度:Agent 對話資料治理",
"source": {
"type": "logstore",
"logstore": {
"project": "<your-project>",
"logstore": "<your-logstore>",
"query": "*"
}
},
"pipeline": {
"nodes": [
{
"id": "kind_filter",
"type": "where",
"parameters": {
"filter": "\"attributes.gen_ai.span.kind\" IS NOT NULL AND \"attributes.gen_ai.span.kind\" != ''"
}
},
{
"id": "kind_preprocess",
"type": "extend",
"parameters": {
"entry_input": "CASE WHEN \"attributes.gen_ai.span.kind\" = 'ENTRY' THEN \"attributes.gen_ai.input.messages\" ELSE CAST(NULL AS VARCHAR) END",
"entry_output": "CASE WHEN \"attributes.gen_ai.span.kind\" = 'ENTRY' THEN \"attributes.gen_ai.output.messages\" ELSE CAST(NULL AS VARCHAR) END",
"llm_model": "CASE WHEN \"attributes.gen_ai.span.kind\" = 'LLM' THEN CASE WHEN \"attributes.gen_ai.request.model\" IS NOT NULL AND ... THEN \"attributes.gen_ai.request.model\" ELSE spanname END ELSE CAST(NULL AS VARCHAR) END",
"llm_input_messages": "...",
"llm_output_messages": "...",
"llm_input_tokens": "...",
"llm_output_tokens": "...",
"tool_name": "...",
"agent_name": "...",
"process_label": "..."
}
},
{
"id": "assemble",
"type": "make-instance",
"parameters": {
"by": "traceid",
"session_id": "first(\"attributes.gen_ai.session.id\")",
"user_input": "first(entry_input)",
"final_output": "last(entry_output)",
"model_list": "array_distinct(llm_model)",
"total_input_tokens": "sum(llm_input_tokens)",
"total_output_tokens": "sum(llm_output_tokens)",
"tool_name_list": "array_distinct(tool_name)",
"tool_call_chain": "join(tool_name, ' → ')",
"process_chain": "join(process_label, chr(10))",
"span_kind_list": "array(\"attributes.gen_ai.span.kind\")",
"start_time": "first(__time__)",
"end_time": "last(__time__)",
"trace_duration": "max(CAST(duration AS BIGINT))"
}
},
{
"id": "derive",
"type": "extend",
"parameters": {
"total_tokens": "total_input_tokens + total_output_tokens",
"span_count": "cardinality(span_kind_list)",
"llm_count": "cardinality(filter(span_kind_list, x -> x = 'LLM'))",
"tool_count": "cardinality(filter(span_kind_list, x -> x = 'TOOL'))",
"trace_duration_ms": "CAST(trace_duration AS DOUBLE) / 1000000.0",
"user_query": "CASE WHEN user_input IS NOT NULL ... END",
"full_text": "concat('## 使用者輸入', chr(10), ..., '## 執行過程', ..., '## 最終輸出', ...)"
}
},
{
"id": "filter_valid",
"type": "where",
"parameters": {
"filter": "(user_input IS NOT NULL AND user_input != '') OR (first_llm_input IS NOT NULL AND first_llm_input != '')"
}
},
{
"id": "exact_dedup",
"type": "dedup-exact",
"parameters": { "field": "user_query" }
},
{
"id": "fuzzy_dedup",
"type": "dedup-fuzzy",
"parameters": { "field": "user_query", "threshold": "3" }
},
{
"id": "semantic_dedup",
"type": "dedup-semantic",
"parameters": { "field": "user_query", "threshold": "0.1" }
},
{
"id": "cluster",
"type": "semantic-cluster",
"parameters": { "field": "__dedup_emb", "n": 20 }
},
{
"id": "sample_per_cluster",
"type": "sample",
"parameters": { "n": 3, "by": "__cluster_id" }
},
{
"id": "evaluate",
"type": "llm-call",
"parameters": {
"prompt": "@eval/trace-eval-prompt.md",
"fields": "user_query,process_chain,full_text",
"format": "json",
"as": "eval"
}
},
{
"id": "annotate",
"type": "llm-call",
"parameters": {
"prompt": "@anno/trace-label-prompt.md",
"fields": "user_query,process_chain",
"format": "json",
"model": "qwen-plus",
"as": "anno"
}
}
]
},
"sink": {
"type": "dataset",
"dataset": {
"workspace": "<your-workspace>",
"dataset": "<your-dataset>"
}
},
"executePolicy": {
"mode": "run_once",
"run_once": { "fromTime": 0, "toTime": 0 }
}
}
配置中的source.logstore和sink.dataset需替換為實際資源。kind_preprocess節點的完整運算式較長,此處以省略符號表示,請參見下方 SPL 格式擷取完整運算式。
預留位置說明:
<your-project>:SLS Project 名稱。<your-logstore>:儲存 OT-Trace 資料的 Logstore 名稱。在目標 Project 中,選擇日誌儲存查看 Logstore 列表。<your-workspace>:資料集所屬的工作空間名稱。在Log Service控制台左側導覽列選擇資料集,查看已有工作空間。<your-dataset>:Pipeline 輸出目標資料集名稱。可使用已有資料集或在建立 Pipeline 時建立。
建立並運行 Pipeline
完成 Pipeline 配置後,通過以下方式提交並運行。
通過控制台建立
登入AgentLoop控制台,在左側導覽列資料集-資料處理中,選擇應用模板,挑選OT-AI Trace 資料治理模板,單擊建立任務。
參數說明
以下為各節點的關鍵參數,可根據實際業務需求調整,控制資料治理的力度和產出規模。
參數 | 預設值 | 調整說明 |
| 3 | SimHash 海明距離閾值。值越小去重越嚴格,值越大保留越多近似資料。詳細說明請參見dedup-fuzzy。 |
| 0.1 | Embedding 向量距離閾值。值越小去重越嚴格,值越大保留越多語義相似資料。詳細說明請參見dedup-semantic。 |
| 20 | 聚類數量。更多簇代表更細粒度的分類,但每簇內樣本量可能減少。詳細說明請參見semantic-cluster。 |
| 3 | 每簇採樣數量。影響下遊 AI 處理的資料量和成本。當前預設配置下最多產出 20 x 3 = 60 條資料。詳細說明請參見sample。 |
| 模板引用 | 可自訂評估和標註的Prompt模板。評估節點使用 |
| 系統預設 / qwen-plus | 評估節點使用系統預設模型,標註節點使用 |
運行結果
Pipeline 運行完成後,產出的資料集中每條記錄包含以下關鍵字段:
欄位 | 來源 | 說明 |
| 組裝 | Trace 唯一標識。 |
| 派生 | 提取的使用者查詢文本,優先取 ENTRY 輸入,回退取首條 LLM 輸入。 |
| 組裝 | 完整執行鏈路,按時間順序拼接每個Span的處理標籤(如 |
| 組裝 | 去重後的模型名稱列表。 |
| 派生 | 輸入和輸出 Token 總數。 |
| 組裝 | 工具調用鏈路。 |
| 派生 | Trace 總耗時(毫秒)。 |
| AI評估 | 多維度品質評估結果(JSON 格式)。 |
| AI標註 | 任務類型、複雜度、業務領域等標註結果(JSON 格式)。 |
注意事項
使用本模板前,請注意以下常見問題及處理方式。
情境 | 預期行為 | 排查與建議 |
源 Logstore 中無 OT-Trace 資料 | Pipeline 正常運行但輸出資料集為空白,不會報錯。 | 確認目標應用已正確接入 OT 探針併產生 Trace 資料。在 Logstore 中執行 |
LLM 調用失敗或逾時 |
| 檢查 LLM 服務的連通性和配額。如果逾時頻繁,可在 |
三級去重後資料量極少或為零 | 下遊聚類和採樣階段輸入資料不足,輸出結果可能無法反映真實分布。 | 適當放寬去重閾值:增大 |
許可權不足 | Pipeline 建立或運行時報 | 確認當前帳號或 RAM 角色具備源 Logstore 的讀取許可權和目標 Dataset 的寫入許可權。 |
Token 配額超限 | Pipeline 運行失敗並返回配額相關錯誤資訊。 | 檢查當前帳號的 LLM 調用配額上限。如需處理更多資料,請提升配額上限或減少 |
定製建議
可在本模板基礎上進行以下定製:
調整去重力度:修改
dedup-fuzzy.threshold和dedup-semantic.threshold參數值。提高閾值保留更多資料,降低閾值去重更嚴格。詳見上方參數說明中的對應參數。調整採樣規模:修改
semantic-cluster.n和sample.n參數。聚類數 x 每簇採樣數 = 最終產出上限。詳見上方參數說明中的對應參數。自訂Prompt模板:替換評估和標註的Prompt模板,適配特定評估維度或標註體系。
添加文本統計:在採樣後、LLM 調用前插入doc-stats節點,統計文本長度、詞頻等資訊。
向外延展群組裝欄位:在
kind_preprocess和assemble節點中添加更多欄位提取和彙總規則,豐富Trace寬表資料。