Major Changes: - Add StreamingService with OpenAI Compatible format - Upgrade Chat component V2 with Ant Design X integration - Implement AIA module with 12 intelligent agents - Update API routes to unified /api/v1 prefix - Update system documentation Backend (~1300 lines): - common/streaming: OpenAI Compatible adapter - modules/aia: 12 agents, conversation service, streaming integration - Update route versions (RVW, PKB to v1) Frontend (~3500 lines): - modules/aia: AgentHub + ChatWorkspace (100% prototype restoration) - shared/Chat: AIStreamChat, ThinkingBlock, useAIStream Hook - Update API endpoints to v1 Documentation: - AIA module status guide - Universal capabilities catalog - System overview updates - All module documentation sync Tested: Stream response verified, authentication working Status: AIA V2.0 core completed (85%)
14 KiB
2025-12-07 摰峕㟲 UI 隡睃<E99AA1>銝𤾸<E98A9D><F0A4BEB8>賢<EFBFBD>撘?
**<2A>冽<EFBFBD><E586BD>漤<EFBFBD>撽勗𢆡<E58B97><F0A286A1><EFBFBD><EFBFBD>V<EFBFBD><EFBCB6>?*嚗? 銝芸<E98A9D><E88AB8>桅䔮憸睃<E686B8><E79D83>其耨憭?
<EFBFBD><EFBFBD> <20>冽<EFBFBD><E586BD>漤<EFBFBD><E6BCA4><EFBFBD>䔮憸?
- <EFBFBD>?銵冽聢瘝⊥<EFBFBD><EFBFBD>㰘蝸<EFBFBD>𣂼<EFBFBD> - AG Grid 璅∪<E79285><E288AA>芣釣<E88AA3>?
- <EFBFBD>?<EFBFBD>港<EFBFBD><EFBFBD>屸𢒰<EFBFBD>𧼮虜蝎㛖<EFBFBD> - 銝𤾸<E98A9D><F0A4BEB8>见㦛撌株<E6928C>憭?
- <EFBFBD>?*AI <20>桃<EFBFBD>瘝⊥<E7989D>甈Z<E79488>霂? - <20>冽<EFBFBD>銝滨䰻<E6BBA8>枏<EFBFBD>雿蓥蝙<E893A5>?
- <EFBFBD>?颲枏<EFBFBD>獢<EFBFBD><EFBFBD>摰嫣<EFBFBD>皜<EFBFBD>征 - <20>煾<EFBFBD><E785BE><EFBFBD>隞滢<E99A9E><E6BBA2>?
- <EFBFBD>?*憿菟𢒰<EFBFBD>箇緵皛𡁜𢆡<EFBFBD>? - 雿㯄<E99BBF>銝滚末
- <EFBFBD>?隞<EFBFBD><EFBFBD><EFBFBD>芸𢆡<EFBFBD>扯<EFBFBD> - <20>冽<EFBFBD><E586BD>䭾<EFBFBD><E4ADBE>批<EFBFBD>
- <EFBFBD>?*蝞<EFBFBD><EFBFBD>閖䔮憸䀹<EFBFBD>瘜訫<EFBFBD>蝑? - 靘见<E99D98>"<22>匧<EFBFBD>撠𤑳撩憭勗<E686AD>潘<EFBFBD>"
<EFBFBD>?摰峕㟲靽桀<E99DBD><E6A180>寞<EFBFBD>
1. 靽桀<EFBFBD> AG Grid 璅∪<E79285>瘜典<E7989C><E585B8>躰秤 <20>?
**<2A>桅<EFBFBD>**嚗?
AG Grid: error #272 No AG Grid modules are registered!
**靽桀<E99DBD>**嚗?
// DataGrid.tsx
import { ColDef, ModuleRegistry, AllCommunityModule } from 'ag-grid-community';
// 潃?瘜典<E7989C> AG Grid 璅∪<E79285>
ModuleRegistry.registerModules([AllCommunityModule]);
**蝏𤘪<E89D8F>**嚗尠<E59A97> 銵冽聢甇<E881A2>虜<EFBFBD>㰘蝸嚗峕㺭<E5B395>桀<EFBFBD><E6A180>湔遬蝷?
2. *隡睃<EFBFBD><EFBFBD>港<EFBFBD><EFBFBD>屸𢒰嚗<EFBFBD>笆<EFBFBD>批<EFBFBD><EFBFBD>见㦛嚗? <20>?
2.1 靽格㺿 AI <20>拇<EFBFBD><E68B87>滨妍
// Sidebar.tsx
<span>AI <EFBFBD>唳旿皜<EFBFBD><EFBFBD><EFBFBD>拇<EFBFBD></span> // <20><>䔉嚗鋫I Copilot
2.2 隡睃<E99AA1><E79D83>厰僼<E58EB0>瑕<EFBFBD>
// Header.tsx - 餈𥪜<E9A488><F0A5AA9C>厰僼
<button className="flex items-center gap-1.5 px-2.5 py-1.5 rounded-md hover:bg-slate-50 text-slate-500 hover:text-slate-700 transition-colors text-xs">
<ArrowLeft className="w-3.5 h-3.5" />
<span className="font-normal">餈𥪜<EFBFBD>撌乩<EFBFBD><EFBFBD>?/span>
</button>
// <20>日<EFBFBD>/<2F>滚<EFBFBD><E6BB9A>厰僼
<div className="flex items-center bg-slate-50 rounded-lg p-0.5 border border-slate-200">
<button className="p-1.5 text-slate-300 hover:text-slate-600 rounded hover:bg-white transition-colors">
<Undo2 size={14} />
</button>
</div>
**<2A>寡<EFBFBD>**嚗?
- <EFBFBD>?<3F>厰僼<E58EB0>游<EFBFBD>撌改<E6928C>14px <20>暹<EFBFBD>嚗<EFBFBD><E59A97><EFBFBD>?16-18px嚗?
- <EFBFBD>?憸𡏭𠧧<F0A18FAD>湔<EFBFBD><E6B994>䕘<EFBFBD>slate-300/500嚗<30><E59A97><EFBFBD>?slate-400/600嚗?
- <EFBFBD>?颲寞<E9A2B2><E5AF9E>渡<EFBFBD>嚗?px嚗<78><E59A97><EFBFBD>?2px嚗?
- <EFBFBD>?餈<>腹<EFBFBD><E885B9><EFBFBD><EFBFBD>湔<EFBFBD><E6B994>?
2.3 瘛餃<E7989B> AI <20>拇<EFBFBD><E68B87><EFBFBD>揢<EFBFBD>厰僼
// Header.tsx
<button
onClick={onToggleSidebar}
className={`flex items-center gap-1.5 px-3 py-1.5 rounded-lg text-xs font-medium transition-all ${
isSidebarOpen
? 'bg-emerald-100 text-emerald-700 hover:bg-emerald-200'
: 'bg-slate-100 text-slate-600 hover:bg-slate-200'
}`}
>
<MessageSquare size={14} />
<span>AI<EFBFBD>拇<EFBFBD></span>
</button>
**蝏𤘪<E89D8F>**嚗尠<E59A97> <20>喲𡡒<E596B2>𤾸虾隞仿<E99A9E><E4BBBF>唳<EFBFBD>撘<EFBFBD>嚗𣬚𠶖<F0A3AC9A><F0A0B696><EFBFBD><EFBFBD>?
2.4 憓𧼮撩閫<E692A9><E996AB><EFBFBD><EFBFBD><EFBFBD>
// Sidebar.tsx
<div className="w-[480px] bg-white border-l-2 border-slate-200 flex flex-col shadow-lg">
<div className="h-14 border-b border-slate-200 flex items-center justify-between px-4 bg-gradient-to-r from-emerald-50 to-white">
**<2A>寡<EFBFBD>**嚗?
- <EFBFBD>?摰賢漲憓𧼮<E68693>嚗?80px嚗<78><E59A97><EFBFBD>?420px嚗?
- <EFBFBD>?撌虫儒颲寞<E9A2B2><E5AF9E>删<EFBFBD>嚗?px嚗?
- <EFBFBD>?瘛餃<E7989B><E9A483>游蔣嚗ìhadow-lg嚗?
- <EFBFBD>?憭湧<E686AD>皜𣂼<E79A9C><F0A382BC>峕艶
2.5 隡睃<E99AA1>銵冽聢摰孵膥
// DataGrid.tsx
<div className="bg-white border-2 border-slate-200 shadow-lg rounded-2xl overflow-hidden h-full">
**<2A>寡<EFBFBD>**嚗?
- <EFBFBD>?颲寞<E9A2B2><E5AF9E>删<EFBFBD>嚗?px嚗?
- <EFBFBD>?<3F>游蔣憓𧼮撩嚗ìhadow-lg嚗?
- <EFBFBD>?<3F><><EFBFBD>憓𧼮之嚗ǐounded-2xl嚗?
3. *瘛餃<EFBFBD> AI 甈Z<E79488>霂? <20>?
**<2A>桅<EFBFBD>**嚗𡁶鍂<F0A181B6>瑚<EFBFBD>隡䭾<E99AA1>隞嗅<E99A9E>嚗淾I 撖寡<E69296>獢<EFBFBD>糓蝛箇蒾<E7AE87>?
**靽桀<E99DBD>**嚗?
// ChatContainer.tsx
const initialMessages = defaultMessages.length > 0 ? defaultMessages : [{
id: 'welcome',
role: 'assistant' as const,
content: '<27>典末嚗<E69CAB><E59A97><EFBFBD>舀<EFBFBD><E88880>?AI <20>唳旿<E594B3><E697BF><EFBFBD>撣<EFBFBD><E692A3><EFBFBD><EFBFBD><EFBFBD>臭誑撣格<E692A3>蝻硋<E89DBB>隞<EFBFBD><E99A9E><EFBFBD>交<EFBFBD>瘣埈㺭<E59F88>柴<EFBFBD><E69FB4><EFBFBD>霂閗秩嚗?<3F>𠰴僑樴<E58391>之鈭?0<><30>挽銝箄<E98A9D><E7AE84>僑蝏?<3F>?,
status: 'success' as const,
timestamp: Date.now(),
}];
**蝏𤘪<E89D8F>**嚗尠<E59A97> <20>冽<EFBFBD>蝡见朖<E8A781>见<EFBFBD>撘訫紡嚗𣬚䰻<F0A3AC9A>枏<EFBFBD>雿蓥蝙<E893A5>?
4. *皜<EFBFBD>征颲枏<EFBFBD>獢?+ 憓𧼮捐撖寡<E69296>獢? <20>?
4.1 皜<>征颲枏<E9A2B2>獢?
// Sidebar.tsx
const [inputValue, setInputValue] = useState('');
<ChatContainer
senderProps={{
placeholder: '颲枏<E9A2B2><E69E8F>唳旿憭<E697BF><E686AD><EFBFBD><EFBFBD>瘙?..嚗𠄌nter<65>煾<EFBFBD><E785BE><EFBFBD>',
value: inputValue,
onChange: (value) => setInputValue(value),
}}
onMessageSent={() => {
setInputValue(''); // 潃?<3F>煾<EFBFBD><E785BE><EFBFBD>皜<EFBFBD>征
}}
/>
4.2 憓𧼮捐撖寡<E69296>獢?
// Sidebar.tsx
<div className="w-[480px] ..."> // <20><>䔉嚗鯱-[420px]
**蝏𤘪<E89D8F>**嚗?
- <EFBFBD>?<3F>煾<EFBFBD><E785BE><EFBFBD><EFBFBD>臬<EFBFBD>颲枏<E9A2B2>獢<EFBFBD>䌊<EFBFBD>冽<EFBFBD>蝛?
- <EFBFBD>?撖寡<E69296>獢<EFBFBD>凒摰踝<E691B0><E8B89D><EFBFBD>捆<EFBFBD>曄內摰峕㟲
5. *蝘駁膄憿菟𢒰皛𡁜𢆡<EFBFBD>? <20>?
**<2A>桅<EFBFBD>**嚗𡁏㟲銝芷△<E88AB7>W枂<EFBCB7>唳赤<E594B3>穃<EFBFBD>蝥萄<E89DA5>皛𡁜𢆡<F0A1819C>?
**靽桀<E99DBD>**嚗?
// index.tsx
<div className="h-screen w-screen flex flex-col bg-gradient-to-br from-slate-50 to-slate-100 overflow-hidden">
<div className="flex-1 flex overflow-hidden">
<div className="flex-1 flex flex-col min-w-0 overflow-hidden">
<Toolbar />
<div className="flex-1 p-4 overflow-hidden"> {/* 潃?<3F>喲睸嚗駅verflow-hidden */}
<DataGrid data={state.data} columns={state.columns} />
</div>
</div>
</div>
</div>
**<2A>喲睸<E596B2>?*嚗?
- <EFBFBD>?<3F><><EFBFBD>厩<EFBFBD>摰孵膥霈曄蔭
overflow-hidden - <EFBFBD>?<3F>芸銁 DataGrid <20><><EFBFBD><EFBFBD>㗇<EFBFBD><E39787>冽辺
- <EFBFBD>?蝘駁膄憭帋<E686AD><E5B88B>?
overflow-auto
**蝏𤘪<E89D8F>**嚗尠<E59A97> 憿菟𢒰<E88F9F>䭾<EFBFBD><E4ADBE>冽辺嚗<E8BEBA>蘨<EFBFBD>㕑”<E39591>澆<EFBFBD><E6BE86>典虾皛𡁜𢆡
6. *隞<EFBFBD><EFBFBD><EFBFBD>见𢆡<EFBFBD>扯<EFBFBD>嚗<EFBFBD><EFBFBD><EFBFBD>芸𢆡餈鞱<EFBFBD>嚗? <20>?
**<2A>桅<EFBFBD>**嚗鋫I <20><><EFBFBD>隞<EFBFBD><E99A9E><EFBFBD>𡒊<EFBFBD><F0A1928A>單<EFBFBD>銵䕘<E98AB5><E49598>冽<EFBFBD><E586BD>䭾<EFBFBD><E4ADBE>批<EFBFBD>
**靽桀<E99DBD>**嚗?
6.1 靽格㺿<E6A0BC>滨垢靚<E59EA2>鍂
// Sidebar.tsx
providerConfig={{
apiEndpoint: `/api/v1/dc/tool-c/ai/generate`, // 潃?<3F>嫣蛹<E5ABA3>芰<EFBFBD><E88AB0>?
requestFn: async (message: string) => {
// <20>芰<EFBFBD><E88AB0>𣂷誨<F0A382B7><E8AAA8><EFBFBD>銝齿<E98A9D>銵?
const response = await fetch(`/api/v1/dc/tool-c/ai/generate`, {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ sessionId, message }),
});
const result = await response.json();
return {
messageId: result.data?.messageId,
explanation: result.data?.explanation,
code: result.data?.code, // 潃?<3F>芾<EFBFBD><E88ABE>硺誨<E7A1BA><E8AAA8><EFBFBD>銝齿<E98A9D>銵?
success: true,
metadata: {
messageId: result.data?.messageId,
},
};
},
}}
6.2 <20>冽<EFBFBD><E586BD>孵稬"餈鞱<E9A488>隞<EFBFBD><E99A9E>"<22>厰僼
// Sidebar.tsx
const handleExecuteCode = async (code: string, messageId?: string) => {
setIsExecuting(true);
try {
const response = await fetch(`/api/v1/dc/tool-c/ai/execute`, {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ sessionId, code, messageId }),
});
const result = await response.json();
if (result.data?.newDataPreview) {
onDataUpdate(result.data.newDataPreview); // 潃?<3F>湔鰵銵冽聢
antdMessage.success('隞<><E99A9E><EFBFBD>扯<EFBFBD><E689AF>𣂼<EFBFBD>');
}
} finally {
setIsExecuting(false);
}
};
**瘚<><E7989A>**嚗?
1. <20>冽<EFBFBD>颲枏<E9A2B2><E69E8F><EFBFBD>瘙?
<20>?
2. AI <20><><EFBFBD>隞<EFBFBD><E99A9E>嚗<EFBFBD>遬蝷箏銁撖寡<E69296>獢<EFBFBD><E78DA2>
<20>?
3. <20>冽<EFBFBD><E586BD>亦<EFBFBD>隞<EFBFBD><E99A9E>
<20>?
4. <20>冽<EFBFBD><E586BD>孵稬"餈鞱<E9A488>隞<EFBFBD><E99A9E>"<22>厰僼 潃?<3F>见𢆡<E8A781>批<EFBFBD>
<20>?
5. <20>扯<EFBFBD>隞<EFBFBD><E99A9E>嚗峕凒<E5B395>啗”<E59597>?
**蝏𤘪<E89D8F>**嚗尠<E59A97> <20>冽<EFBFBD>摰<EFBFBD><E691B0><EFBFBD>批<EFBFBD>隞<EFBFBD><E99A9E><EFBFBD>扯<EFBFBD><E689AF>嗆㦤
7. *<EFBFBD>舀<EFBFBD>蝞<EFBFBD><EFBFBD>閖䔮蝑? <20>?
**<2A>桅<EFBFBD>**嚗𡁶<E59A97><F0A181B6>閖䔮憸矋<E686B8>憒?<3F>匧<EFBFBD>撠𤑳撩憭勗<E686AD>潘<EFBFBD>"嚗㗇<E59A97>瘜訫<E7989C>蝑䈑<E89D91>AI 撘箏<E69298><E7AE8F><EFBFBD><EFBFBD>隞<EFBFBD><E99A9E>
**閫<><E996AB><EFBFBD>寞<EFBFBD>**嚗𡁏溶<F0A1818F>䭾鰵<E4ADBE>?/ai/chat 蝡舐<E89DA1>
7.1 <20>𡒊垢<F0A1928A>啣<EFBFBD> API
// AIController.ts
async chat(request: FastifyRequest, reply: FastifyReply) {
const { sessionId, message } = request.body;
// <20>瑕<EFBFBD> Session 靽⊥<E99DBD>
const session = await sessionService.getSession(sessionId);
// 靚<>鍂 LLM 餈𥡝<E9A488>蝞<EFBFBD><E89D9E>閖䔮蝑?
const llm = LLMFactory.getAdapter('deepseek-v3');
const response = await llm.chat([
{
role: 'system',
content: `雿䭾糓銝<E7B393>銝芣㺭<E88AA3>桀<EFBFBD><E6A180>𣂼𨭌<F0A382BC>卝<EFBFBD><E58D9D><EFBFBD><EFBFBD>齿㺭<E9BDBF>桅<EFBFBD>靽⊥<E99DBD>嚗?
- <20><>辣<EFBFBD>㵪<EFBFBD>${session.fileName}
- <20>餉<EFBFBD><E9A489>堆<EFBFBD>${session.totalRows}
- <20>餃<EFBFBD><E9A483>堆<EFBFBD>${session.totalCols}
- <20>堒<EFBFBD>嚗?{session.columns.join(', ')}
霂瑞凒<EFBFBD>亙<EFBFBD>蝑𠉛鍂<EFBFBD>瑞<EFBFBD><EFBFBD>桅<EFBFBD>嚗䔶<EFBFBD>閬<EFBFBD><EFBFBD><EFBFBD>𣂷誨<EFBFBD><EFBFBD><EFBFBD><EFBFBD>
},
{ role: 'user', content: message }
], {
temperature: 0.7,
maxTokens: 500,
});
return reply.send({
success: true,
data: {
messageId: Date.now().toString(),
content: response.content,
explanation: response.content,
}
});
}
7.2 頝舐眏瘜典<E7989C>
// routes/index.ts
fastify.post('/ai/chat', {
handler: aiController.chat.bind(aiController),
});
7.3 <20>滨垢<E6BBA8>箄<EFBFBD><E7AE84>斗鱏
**<2A>寞<EFBFBD>**嚗𡁜<E59A97>蝡臬虾隞交覔<E4BAA4>桃鍂<E6A183>瑁<EFBFBD><E79181>交惣<E4BAA4>賡<EFBFBD>㗇𥋘靚<F0A58B98>鍂<EFBFBD>芯葵 API
// <20>芣䔉隡睃<E99AA1>嚗𡁏惣<F0A1818F>賢ế<E8B3A2>?
const isSimpleQuestion = (message: string) => {
const questionKeywords = ['憭𡁜<E686AD>', '<27>匧<EFBFBD>', '隞<>銋?, '<EFBFBD>芯<EFBFBD>', '<EFBFBD>臬炏', '憒<EFBFBD><EFBFBD>'];
return questionKeywords.some(kw => message.includes(kw));
};
// 憒<><E68692><EFBFBD>舐<EFBFBD><E88890>閖䔮憸矋<E686B8>靚<EFBFBD>鍂 /ai/chat
// 憒<><E68692><EFBFBD>舀㺭<E88880>桀<EFBFBD><E6A180><EFBFBD><EFBFBD>瘙<EFBFBD><E79899>靚<EFBFBD>鍂 /ai/generate
敶枏<EFBFBD>摰䂿緵嚗𡁜<EFBFBD>雿輻鍂 /ai/generate嚗<EFBFBD><EFBFBD><EFBFBD>𦦵鍂<EFBFBD>琿<EFBFBD>閬<EFBFBD><EFBFBD><EFBFBD>閖䔮蝑䈑<EFBFBD><EFBFBD>臭誑<EFBFBD>见𢆡<EFBFBD><EFBFBD>揢
**蝏𤘪<E89D8F>**嚗尠<E59A97> <20>舀<EFBFBD>銝斤<E98A9D>撖寡<E69296>璅∪<E79285>
<EFBFBD><EFBFBD> 摰峕㟲靽格㺿皜<E3BABF><E79A9C>
| <EFBFBD><EFBFBD>辣 | 靽格㺿<EFBFBD><EFBFBD>捆 | 銵峕㺭 | <EFBFBD>嗆<EFBFBD>? |
|---|---|---|---|
| <EFBFBD>滨垢 | |||
DataGrid.tsx |
瘜典<EFBFBD> AG Grid 璅∪<E79285> | +2 | <EFBFBD>? |
DataGrid.tsx |
隡睃<EFBFBD>摰孵膥<EFBFBD>瑕<EFBFBD>嚗<EFBFBD>器獢<EFBFBD><EFBFBD><EFBFBD>狍敶晞<EFBFBD><EFBFBD><EFBFBD>閫𡜐<EFBFBD> | ~10 | <EFBFBD>? |
ChatContainer.tsx |
瘛餃<EFBFBD>甈Z<EFBFBD>霂? | +8 | <EFBFBD>? |
ChatContainer.tsx |
<EFBFBD>脫迫<EFBFBD>煾<EFBFBD><EFBFBD>征瘨<EFBFBD><EFBFBD> | +1 | <EFBFBD>? |
chat.css |
憓𧼮撩颲寞<EFBFBD><EFBFBD><EFBFBD>狍敶晞<EFBFBD><EFBFBD><EFBFBD><EFBFBD>䁅<EFBFBD><EFBFBD>? | ~25 | <EFBFBD>? |
Sidebar.tsx |
靽格㺿<EFBFBD>滨妍銝?AI <20>唳旿皜<E697BF><E79A9C><EFBFBD>拇<EFBFBD>" | +1 | <EFBFBD>? |
Sidebar.tsx |
憓𧼮捐撖寡<EFBFBD>獢<EFBFBD><EFBFBD>480px嚗? | +1 | <EFBFBD>? |
Sidebar.tsx |
瘛餃<EFBFBD>颲枏<EFBFBD>獢<EFBFBD>𠶖<EFBFBD><EFBFBD>恣<EFBFBD>? | +5 | <EFBFBD>? |
Sidebar.tsx |
靽格㺿銝箏蘨<EFBFBD><EFBFBD><EFBFBD>隞<EFBFBD><EFBFBD>嚗䔶<EFBFBD><EFBFBD>芸𢆡<EFBFBD>扯<EFBFBD> | ~15 | <EFBFBD>? |
Header.tsx |
隡睃<EFBFBD><EFBFBD>厰僼<EFBFBD>瑕<EFBFBD>嚗<EFBFBD>凒撠誩概<EFBFBD><EFBFBD><EFBFBD><EFBFBD>䕘<EFBFBD> | ~20 | <EFBFBD>? |
Header.tsx |
瘛餃<EFBFBD> AI <20>拇<EFBFBD><E68B87><EFBFBD>揢<EFBFBD>厰僼 | +15 | <EFBFBD>? |
index.tsx (Tool C) |
蝘駁膄憿菟𢒰皛𡁜𢆡<EFBFBD>? | ~5 | <EFBFBD>? |
index.tsx (Tool C) |
隡𣳇<EFBFBD>鍦<EFBFBD><EFBFBD>X<EFBFBD><EFBFBD>桀<EFBFBD>靚? | +2 | <EFBFBD>? |
index.tsx (Tool C) |
蝘駁膄摨笔<EFBFBD><EFBFBD>?handleSendMessage | -90 | <EFBFBD>? |
index.tsx (DC) |
靽桀<EFBFBD> Spin tip 霅血<E99C85> | +1 | <EFBFBD>? |
toolC.ts |
<EFBFBD>湔鰵蝐餃<EFBFBD>摰帋<EFBFBD> | ~5 | <EFBFBD>? |
| <EFBFBD>𡒊垢 | |||
AIController.ts |
瘛餃<EFBFBD> chat <20>寞<EFBFBD>嚗<EFBFBD><E59A97><EFBFBD>閖䔮蝑䈑<E89D91> | +58 | <EFBFBD>? |
AIController.ts |
瘛餃<EFBFBD>敹<EFBFBD><EFBFBD><EFBFBD><EFBFBD>紡<EFBFBD>? | +3 | <EFBFBD>? |
routes/index.ts |
瘜典<EFBFBD> /ai/chat 頝舐眏 | +4 | <EFBFBD>? |
| <EFBFBD>餉恣 | *19 銝芣<E98A9D>隞? | *~180 銵? | *<EFBFBD>? |
<EFBFBD>綫 閫<><E996AB>撖寞<E69296>
靽桀<EFBFBD><EFBFBD>?<3F>?
| <EFBFBD><EFBFBD><EFBFBD> | <EFBFBD>桅<EFBFBD> |
|---|---|
| 銵冽聢 | 銝齿遬蝷綽<EFBFBD>璅∪<EFBFBD><EFBFBD>躰秤嚗? |
| <EFBFBD>厰僼 | 憭芸之<EFBFBD><EFBFBD>云<EFBFBD>溻<EFBFBD><EFBFBD>器獢<EFBFBD><EFBFBD> |
| AI 撖寡<E69296>獢? | 憭芰<EFBFBD>嚗?20px嚗㚁<E59A97><E39A81>䭾洽餈舘祗 |
| 颲寞<EFBFBD> | 1px嚗䔶<EFBFBD>皜<EFBFBD>苊 |
| <EFBFBD>港<EFBFBD> | <EFBFBD><EFBFBD>像<EFBFBD><EFBFBD><EFBFBD>蝟? |
| 皛𡁜𢆡<EFBFBD>? | 憿菟𢒰蝥批<EFBFBD>嚗䔶<EFBFBD>撉<EFBFBD>榆 |
靽桀<EFBFBD><EFBFBD>?<3F>?
| <EFBFBD><EFBFBD><EFBFBD> | <EFBFBD>寡<EFBFBD> |
|---|---|
| 銵冽聢 | 甇<EFBFBD>虜<EFBFBD>曄內嚗?px 颲寞<E9A2B2>嚗屸狍敶? |
| <EFBFBD>厰僼 | 撠誩概嚗?4px嚗㚁<E59A97><E39A81>𥪜<EFBFBD>嚗𣬚<E59A97>颲寞<E9A2B2> |
| AI 撖寡<E69296>獢? | <EFBFBD>游捐嚗?80px嚗㚁<E59A97><E39A81>㗇洽餈舘祗 |
| 颲寞<EFBFBD> | 2px嚗峕<EFBFBD><EFBFBD>啣<EFBFBD><EFBFBD>? |
| <EFBFBD>港<EFBFBD> | 皜𣂼<EFBFBD><EFBFBD><EFBFBD>狍敶晞<EFBFBD><EFBFBD><EFBFBD>甈⊥<EFBFBD> |
| 皛𡁜𢆡<EFBFBD>? | 隞<EFBFBD>”<EFBFBD>澆<EFBFBD><EFBFBD>剁<EFBFBD>雿㯄<EFBFBD>憟? |
<EFBFBD>㴓 <20>蠘<EFBFBD>撖寞<E69296>
靽桀<EFBFBD><EFBFBD>?<3F>?
| <EFBFBD>蠘<EFBFBD> | <EFBFBD>桅<EFBFBD> |
|---|---|
| 隞<EFBFBD><EFBFBD><EFBFBD>扯<EFBFBD> | <EFBFBD>芸𢆡<EFBFBD>扯<EFBFBD>嚗峕<EFBFBD>瘜閙綉<EFBFBD>? |
| 颲枏<EFBFBD>獢? | <EFBFBD>煾<EFBFBD><EFBFBD><EFBFBD>銝齿<EFBFBD>蝛? |
| AI <20>拇<EFBFBD> | <EFBFBD>喲𡡒<EFBFBD>擧<EFBFBD>瘜閙<EFBFBD>撘<EFBFBD> |
| 蝞<EFBFBD><EFBFBD>閖䔮蝑? | 銝齿𣈲<EFBFBD>? |
靽桀<EFBFBD><EFBFBD>?<3F>?
| <EFBFBD>蠘<EFBFBD> | <EFBFBD>寡<EFBFBD> |
|---|---|
| 隞<EFBFBD><EFBFBD><EFBFBD>扯<EFBFBD> | <EFBFBD>见𢆡<EFBFBD>孵稬"餈鞱<E9A488>隞<EFBFBD><E99A9E>"<22>厰僼 |
| 颲枏<EFBFBD>獢? | <EFBFBD>煾<EFBFBD><EFBFBD><EFBFBD><EFBFBD>芸𢆡皜<EFBFBD>征 |
| AI <20>拇<EFBFBD> | <EFBFBD>舫<EFBFBD><EFBFBD>嗅<EFBFBD><EFBFBD>W<EFBFBD><EFBFBD>? |
| 蝞<EFBFBD><EFBFBD>閖䔮蝑? | <EFBFBD>舀<EFBFBD>嚗<EFBFBD>鰵憓?/ai/chat API嚗? |
<EFBFBD><EFBFBD> <20>啣<EFBFBD> API
POST /api/v1/dc/tool-c/ai/chat
**<2A>券<EFBFBD>?*嚗𡁶<E59A97><F0A181B6>閖䔮蝑䈑<E89D91>銝滨<E98A9D><E6BBA8>𣂷誨<F0A382B7>?
**霂瑟<E99C82>**嚗?
{
"sessionId": "xxx",
"message": "<22>唾<EFBFBD>蝐餃<E89D90><E9A483>埈<EFBFBD>憭𡁜<E686AD>蝻箏仃<E7AE8F>潘<EFBFBD>"
}
**<2A>滚<EFBFBD>**嚗?
{
"success": true,
"data": {
"messageId": "xxx",
"content": "<22>寞旿敶枏<E695B6><E69E8F>唳旿<E594B3><E697BF><EFBFBD><EFBFBD>唾<EFBFBD>蝐餃<E89D90><E9A483>埈<EFBFBD> 15 銝芰撩憭勗<E686AD>潦<EFBFBD>?,
"explanation": "<EFBFBD>寞旿敶枏<EFBFBD><EFBFBD>唳旿<EFBFBD><EFBFBD><EFBFBD><EFBFBD>唾<EFBFBD>蝐餃<EFBFBD><EFBFBD>埈<EFBFBD> 15 銝芰撩憭勗<EFBFBD>潦<EFBFBD>?
}
}
<EFBFBD>?撉諹<E69289>蝏𤘪<E89D8F>
Linter 璉<><E79289>?
- <EFBFBD>?<EFBFBD>滨垢嚗? <20>躰秤嚗? 霅血<E99C85>
- <EFBFBD>?<EFBFBD>𡒊垢嚗? <20>躰秤嚗? 霅血<E99C85>
瘚讛<EFBFBD><EFBFBD>冽綉<EFBFBD>嗅蝱
- <EFBFBD>?AG Grid <20>躰秤嚗𡁜歇靽桀<EFBFBD>
- <EFBFBD>?**Spin 霅血<E99C85>**嚗𡁜歇靽桀<E99DBD>
- <EFBFBD>?0 <20>躰秤嚗? 霅血<E99C85>
<EFBFBD>蠘<EFBFBD>瘚贝<EFBFBD>
| <EFBFBD>蠘<EFBFBD> | 瘚贝<EFBFBD>蝏𤘪<EFBFBD> |
|---|---|
| 銵冽聢<EFBFBD>㰘蝸 | <EFBFBD>?甇<>虜<EFBFBD>曄內 |
| AI 甈Z<E79488>霂? | <EFBFBD>?<3F>芸𢆡<E88AB8>曄內 |
| 颲枏<EFBFBD>獢<EFBFBD><EFBFBD>蝛? | <EFBFBD>?<3F>煾<EFBFBD><E785BE><EFBFBD>皜<EFBFBD>征 |
| 隞<EFBFBD><EFBFBD><EFBFBD>见𢆡<EFBFBD>扯<EFBFBD> | <EFBFBD>?<3F>孵稬<E5ADB5>厰僼<E58EB0>扯<EFBFBD> |
| AI <20>拇<EFBFBD><E68B87><EFBFBD>揢 | <EFBFBD>?<3F>臬<EFBFBD><E887AC>? |
| 憿菟𢒰皛𡁜𢆡 | <EFBFBD>?隞<>”<EFBFBD>澆<EFBFBD><E6BE86>? |
| <EFBFBD>屸𢒰蝎曇稲摨? | <EFBFBD>?<3F>亥<EFBFBD><E4BAA5>笔<EFBFBD><E7AC94>? |
<EFBFBD><EFBFBD> <20>冽<EFBFBD>雿㯄<E99BBF><E3AF84>𣂼<EFBFBD>
靽桀<EFBFBD><EFBFBD>?
- <EFBFBD>?銵冽聢銝齿遬蝷綽<E89DB7><E7B6BD>冽<EFBFBD><E586BD>唳<EFBFBD>
- <EFBFBD>?<3F>屸𢒰蝎㛖<E89D8E>嚗𣬚撩銋譍<E98A8B>銝𡁏<E98A9D>
- <EFBFBD>?AI 撖寡<E69296>獢<EFBFBD>征<EFBFBD>踝<EFBFBD>銝滨䰻<E6BBA8>枏<EFBFBD>雿蓥蝙<E893A5>?
- <EFBFBD>?颲枏<E9A2B2>獢<EFBFBD><E78DA2>皜<EFBFBD>征嚗䔶<E59A97>撉<EFBFBD>榆
- <EFBFBD>?隞<><E99A9E><EFBFBD>芸𢆡<E88AB8>扯<EFBFBD>嚗峕<E59A97>瘜閙綉<E99699>?
- <EFBFBD>?憿菟𢒰皛𡁜𢆡瘛瑚僚
靽桀<EFBFBD><EFBFBD>?
- <EFBFBD>?銵冽聢蝡见朖<E8A781>曄內嚗峕㺭<E5B395>格<EFBFBD><E6A0BC>?
- <EFBFBD>?<3F>屸𢒰蝎曇稲嚗䔶<E59A97>銝𡁏<E98A9D>撘?
- <EFBFBD>?AI 甈Z<E79488>霂剖<E99C82>撖潘<E69296>雿輻鍂<E8BCBB>𡒊&
- <EFBFBD>?颲枏<E9A2B2>獢<EFBFBD>䌊<EFBFBD>冽<EFBFBD>蝛綽<E89D9B>雿㯄<E99BBF>瘚<EFBFBD><E7989A>
- <EFBFBD>?隞<><E99A9E><EFBFBD>见𢆡<E8A781>扯<EFBFBD>嚗𣬚鍂<F0A3AC9A>瑕虾<E79195>?
- <EFBFBD>?憿菟𢒰撣<F0A292B0><E692A3>摰𣬚<E691B0>嚗峕<E59A97>皛𡁜𢆡撟脫贋
<EFBFBD>冽<EFBFBD>雿㯄<EFBFBD>霂<EFBFBD><EFBFBD>嚗尠<EFBFBD>潃鐥<EFBFBD>潃鐥<EFBFBD>
<EFBFBD><EFBFBD> 瘚贝<E7989A><E8B49D><EFBFBD><EFBFBD>
1. <20>瑟鰵瘚讛<E7989A><E8AE9B>?
http://localhost:5173/data-cleaning/tool-c
2. 銝𠹺<E98A9D><F0A0B9BA><EFBFBD>辣
- <EFBFBD>孵稬"<22>㗇𥋘<E39787><F0A58B98>辣"
- 銝𠹺<EFBFBD> CSV <20>?Excel
- 摨磰砲<EFBFBD>见<EFBFBD>嚗?
- <EFBFBD>?銵冽聢甇<E881A2>虜<EFBFBD>曄內<E69B84>唳旿
- <EFBFBD>?AI 甈Z<E79488>霂剛䌊<E5899B>典枂<E585B8>?
- <EFBFBD>?<3F>屸𢒰蝎曇稲蝢舘<E89DA2>
3. 瘚贝<E7989A> AI 撖寡<E69296>
**<2A>唳旿憭<E697BF><E686AD><EFBFBD><EFBFBD>瘙?*嚗<><E59A97><EFBFBD>𣂷誨<F0A382B7><E8AAA8><EFBFBD>嚗?
- "<22>𠰴僑樴<E58391>之鈭?0<><30>挽銝箄<E98A9D><E7AE84>僑蝏?
- "<22>𣳇膄<F0A3B387>滚<EFBFBD>銵?
- "憛怨‘蝻箏仃<E7AE8F>?
**蝞<><E89D9E>閖䔮蝑?*嚗<><E59A97><EFBFBD><EFBFBD><EFBFBD>隞<EFBFBD><E99A9E>嚗㚁<E59A97>
- "<22>唾<EFBFBD>蝐餃<E89D90><E9A483>埈<EFBFBD>憭𡁜<E686AD>蝻箏仃<E7AE8F>潘<EFBFBD>"
- "<22>唳旿<E594B3><E697BF><EFBFBD>憭𡁜<E686AD>銵䕘<E98AB5>"
- "<22>匧𪑛鈭𥕦<E988AD>嚗?
4. 撉諹<E69289><E8ABB9>蠘<EFBFBD>
- <EFBFBD>?颲枏<E9A2B2>瘨<EFBFBD><E798A8><EFBFBD>𠬍<EFBFBD>颲枏<E9A2B2>獢<EFBFBD>䌊<EFBFBD>冽<EFBFBD>蝛?
- <EFBFBD>?AI <20><><EFBFBD>隞<EFBFBD><E99A9E>嚗峕遬蝷?餈鞱<E9A488>隞<EFBFBD><E99A9E>"<22>厰僼
- <EFBFBD>?<3F>孵稬<E5ADB5>厰僼<E58EB0>𠬍<EFBFBD>銵冽聢<E586BD>湔鰵
- <EFBFBD>?<3F>臭誑<E887AD>喲𡡒撟園<E6929F><E59C92>唳<EFBFBD>撘<EFBFBD> AI <20>拇<EFBFBD>
- <EFBFBD>?憿菟𢒰<E88F9F>䭾<EFBFBD><E4ADBE>冽辺嚗<E8BEBA>蘨<EFBFBD>㕑”<E39591>澆<EFBFBD><E6BE86>典虾皛𡁜𢆡
<EFBFBD><EFBFBD> <20>喲睸<E596B2>寡<EFBFBD><E5AFA1>?
1. 閫<EFBFBD><EFBFBD>霈曇恣
- <EFBFBD>?颲寞<E9A2B2>隞?1px <20>?2px
- <EFBFBD>?<3F>游蔣隞?sm <20>?lg
- <EFBFBD>?<3F><><EFBFBD>隞?xl <20>?2xl
- <EFBFBD>?瘛餃<E7989B>皜𣂼<E79A9C><F0A382BC>峕艶
- <EFBFBD>?<3F>厰僼<E58EB0>游<EFBFBD>撌扳<E6928C><E689B3>?
2. 鈭支<EFBFBD>雿㯄<EFBFBD>
- <EFBFBD>?颲枏<E9A2B2>獢<EFBFBD>䌊<EFBFBD>冽<EFBFBD>蝛?
- <EFBFBD>?AI <20>拇<EFBFBD><E68B87>臬<EFBFBD><E887AC>?
- <EFBFBD>?隞<><E99A9E><EFBFBD>见𢆡<E8A781>扯<EFBFBD>
- <EFBFBD>?甈Z<E79488>霂剖<E99C82>撖?
3. 撣<EFBFBD><EFBFBD>隡睃<EFBFBD>
- <EFBFBD>?蝘駁膄憿菟𢒰皛𡁜𢆡
- <EFBFBD>?撖寡<E69296>獢<EFBFBD>凒摰踝<E691B0>480px嚗?
- <EFBFBD>?撅<>活皜<E6B4BB>苊
4. <EFBFBD>蠘<EFBFBD>憓𧼮撩
- <EFBFBD>?<3F>舀<EFBFBD>蝞<EFBFBD><E89D9E>閖䔮蝑?
- <EFBFBD>?<3F>舀<EFBFBD>隞<EFBFBD><E99A9E><EFBFBD><EFBFBD><EFBFBD>
- <EFBFBD>?<3F>冽<EFBFBD><E586BD>舀綉<E88880>扯<EFBFBD>
<EFBFBD><EFBFBD> <20>餌<EFBFBD>
*<EFBFBD>?<3F><><EFBFBD>?7 銝芷䔮憸睃歇摰𣬚<E691B0>靽桀<E99DBD>嚗?
- <EFBFBD>?AG Grid 銵冽聢甇<E881A2>虜<EFBFBD>㰘蝸
- <EFBFBD>?<3F>屸𢒰蝎曇稲蝢舘<E89DA2>嚗峕𦻖餈穃<E9A488><E7A983>见㦛
- <EFBFBD>?AI 甈Z<E79488>霂剛䌊<E5899B>冽遬蝷?
- <EFBFBD>?颲枏<E9A2B2>獢<EFBFBD>䌊<EFBFBD>冽<EFBFBD>蝛?
- <EFBFBD>?憿菟𢒰<E88F9F>䭾<EFBFBD><E4ADBE>冽辺
- <EFBFBD>?隞<><E99A9E><EFBFBD>见𢆡<E8A781>扯<EFBFBD>
- <EFBFBD>?<3F>舀<EFBFBD>蝞<EFBFBD><E89D9E>閖䔮蝑?
**隞<><E99A9E>韐券<E99F90>**嚗?
- <EFBFBD>?0 <20>躰秤嚗? 霅血<E99C85>
- <EFBFBD>?摰峕㟲<E5B395><E39FB2>掩<EFBFBD>见<EFBFBD><E8A781>?
- <EFBFBD>?隡㗛<E99AA1><E3979B><EFBFBD>誨<EFBFBD><E8AAA8><EFBFBD><EFBFBD>?
**<2A>冽<EFBFBD>雿㯄<E99BBF>**嚗?
- <EFBFBD>?<3F>屸𢒰蝎曇稲銝㮖<E98A9D>
- <EFBFBD>?鈭支<E988AD>瘚<EFBFBD><E7989A><EFBFBD>芰<EFBFBD>
- <EFBFBD>?<3F>蠘<EFBFBD>摰峕㟲<E5B395>舀綉
*<EFBFBD><EFBFBD> Tool C MVP 摰峕㟲<E5B395><E39FB2>歇撠梁貌嚗? <20><>
**靽桀<E99DBD><E6A180>?*嚗鋫I Assistant
**<2A>交<EFBFBD>**嚗?025-12-07
<EFBFBD><EFBFBD>𧋦嚗鯝1.2嚗<EFBFBD><EFBFBD><EFBFBD>港<EFBFBD><EFBFBD>𣇉<EFBFBD>嚗?