import React, { useState, useEffect, useRef } from 'react'; import { Search, MessageSquare, FileText, Clock, ChevronRight, ChevronDown, Send, BookOpen, HelpCircle, Presentation, Briefcase, FileSignature, CreditCard, AlertCircle, CheckCircle2, Sparkles, ArrowDown, Download, File, FileBarChart2, ListTodo, X, Loader2 } from 'lucide-react'; // --- 配置区域 --- const apiKey = ""; // Gemini API Key will be injected by the environment // --- 数据源 (保留原有数据作为 AI 的上下文) --- // 1. 知识库数据 const KNOWLEDGE_BASE = [ { keywords: ["code", "申请", "project code", "材料"], answer: "申请 Project Code 一般分为常规 Code 和 Special Code。常规 Code 需要提交:1. Code Request Form;2. Budget Plan。如果是 Special Code,还需要额外增加 Lob Leader 的批复。如果没有模板,请在建议书苑查找或询问中台同事。", source: "常见问题.pdf" }, { keywords: ["时间", "多久", "时长", "code"], answer: "申请 Code 的时间取决于客户类型:\n1. 现有客户(有 Customer Code):通常 1-2 天。\n2. 新客户或更名客户:需要先走 KYC 流程和申请 Customer Code,通常需要 1-2 周。", source: "常见问题.pdf" }, { keywords: ["开票", "流程", "发票", "税票"], answer: "开票流程如下:\n1. 向中台申请 FN (Fee Note);\n2. 联系客户获得确认开票的邮件;\n3. 财务开出税票后,将税票发送给客户(抄送中台)。\n注意:Fee Note 申请通常需要 2-3 天。", source: "常见问题.pdf" }, { keywords: ["盖章", "合同", "用印"], answer: "合同盖章申请材料包括:\n1. 最终版 PDF 文件;\n2. 所有审批邮件(报价批复+法务批复必选);\n3. 《合同盖章申请表》。\n如果是法人签,需中台审批后找 Wise 或 Raymond 签字。", source: "常见问题.pdf" }, { keywords: ["投标", "保证金", "流程"], answer: "投标保证金流程:需填写申请模板,写清英文邮件正文给 July Mao。如果涉及合同条款,必须先提供法务审核意见。请务必预留充足时间。", source: "2025项目管理.pptx" }, { keywords: ["供应商", "付款", "vendor"], answer: "2026新规(1月1日起执行):\n1. 必须收到客户服务费后,原则上才能支付供应商费用;\n2. 支付比例不可一次性支付;\n3. 支付需 PD 和 Lob Leader 审批;\n4. 必须在供应商合同有效期内启动支付。", source: "项目财务管理--20260106.pptx" }, { keywords: ["2026", "新规", "财务"], answer: "2026年1月1日起执行的新规重点:\n1. Fee note 要和正式税票同时开出;\n2. 当年开具的税票争取当年追回 AR;\n3. Special code 合同尽量在当年 12.31 前签署回来。", source: "项目财务管理--20260106.pptx" } ]; // 2. FAQ 数据 const FAQ_DATA = [ { category: "Project Code 相关", questions: [ { q: "申请 Project code 需要什么材料?", a: "常规 code 申请需要: 1. Code Request Form, 2. Budget Plan。\nSpecial Code 则需要在常规 code 基础上增加 Lob Leader 的批复。" }, { q: "申请 code 需要多长时间?", a: "情况一(老客户):通常 1-2 天。\n情况二(新客户/更名):需要 KYC 及 Customer Code,通常 1-2 周。" } ] }, { category: "开票与财务", questions: [ { q: "每月可开票的时间是?", a: "系统一般在每月第三个工作日之后开启。Billing Deadline 一般为系统开启后一周。具体时间留意中台每月邮件。" }, { q: "开票有哪些注意事项?", a: "注意每月具体时间;申请 FN 前确定好合同金额;如需拆分需提前沟通;客户确认邮件需符合规范。" } ] }, { category: "合同盖章", questions: [ { q: "合同盖章申请需要哪些材料?", a: "1. 最终版 PDF 文件;\n2. 审批邮件(报价+法务);\n3. 《合同盖章申请表》。" }, { q: "合同需要法人/代表签字怎么办?", a: "如需 Raymond 或 Wise 签字,请在获取中台盖章审批后,向对应领导申请电子签,并抄送 Angela Han 用印。" } ] } ]; // 3. PPT 时间轴数据 (按时间正序存储,渲染时倒序) const TIMELINE_SLIDES = [ { id: 1, phase: "BD Phase", title: "投标与招标文件", date: "July 2025", color: "bg-blue-500", icon: , content: [ { type: "subtitle", text: "招标文件获取" }, { type: "list", items: ["线上购买:确认 CA 证书有效期,联系 July Mao。", "线下购买:准备法人授权书、身份证复印件。"] }, { type: "subtitle", text: "关键授权文件审批" }, { type: "table", rows: [ ["公司授权书", "Raymond Lu -> Wise Xu (CC Angela)"], ["业绩证明", "Raymond Lu -> July Mao 提供"], ["资信/社保", "发给 July Mao 协助获取 (提前2-3天)"] ]} ] }, { id: 2, phase: "Contracting Phase", title: "报价审批与 Budget Plan", date: "2025 Standard", color: "bg-indigo-500", icon: , content: [ { type: "text", text: "《Budget Plan》是报价计算工具,也是项目资源管理依据。" }, { type: "subtitle", text: "报价审批流程" }, { type: "list", items: [ "投标报价审批:发给 BD 成员、Resource Manager (Sindy)、中台 (Louisa/July)。", "合同报价审批:包含项目总报价、付款比例、交付内容。", "首/尾款比例:尾款比例不得高于 10%,否则需特别审批。" ]} ] }, { id: 3, phase: "Project Delivery", title: "Project Code 申请体系", date: "Ongoing", color: "bg-purple-500", icon: , content: [ { type: "subtitle", text: "Code 类型判断" }, { type: "list", items: [ "常规 Code (有合同):Code Request Form + Budget Plan -> 系统申请", "Special Code (无合同):上述材料 + Lob Leader 批复 -> 提交 Ticket" ]}, { type: "subtitle", text: "Mavenlink ID" }, { type: "text", text: "创建 Project Name 格式:客户名称-项目名称。生成 4 开头的 8 位 ID。" } ] }, { id: 4, phase: "Finance Rules", title: "财务管理新规 (重点)", date: "Effective Jan 1, 2026", tag: "NEW", color: "bg-red-500", icon: , content: [ { type: "subtitle", text: "AR 与 Special Code 管理" }, { type: "list", items: [ "Fee note 需与正式税票同时开出。", "Special code 合同必须在当年 12 月 31 日前签署拿回。", "跨年 AR 需 PD 准备 Business Justification。" ]}, { type: "subtitle", text: "供应商管理 (严控)" }, { type: "list", items: [ "原则:收到客户款项后,再支付供应商。", "流程:PD Approval -> Lob Leader Approval。", "禁止:一次性支付供应商费用。" ]} ] } ]; // 4. 下载中心文件数据 const DOWNLOAD_RESOURCES = [ { id: 1, name: "项目财务管理--20260106.pptx", type: "PPT", size: "2.4 MB", date: "2026-01-06", desc: "2026年最新财务新规,包含 Special Code 管理及供应商付款流程变更。", color: "text-red-600", bgColor: "bg-red-50" }, { id: 2, name: "2025项目管理.pptx", type: "PPT", size: "5.8 MB", date: "2025-07-01", desc: "项目全生命周期管理指引,涵盖 BD、合同及交付阶段标准动作。", color: "text-orange-600", bgColor: "bg-orange-50" }, { id: 3, name: "常见问题.pdf", type: "PDF", size: "1.2 MB", date: "2025-07-15", desc: "Project Code 申请、开票、盖章等日常高频问题解答。", color: "text-blue-600", bgColor: "bg-blue-50" } ]; // --- Gemini API 集成逻辑 --- // 1. 构建全量知识库上下文字符串 const MANUAL_CONTEXT = JSON.stringify({ knowledge_base: KNOWLEDGE_BASE, faq: FAQ_DATA, timeline_rules: TIMELINE_SLIDES }, null, 2); // 2. API 调用函数 const callGemini = async (prompt, systemInstruction = "") => { try { const response = await fetch( `https://generativelanguage.googleapis.com/v1beta/models/gemini-2.5-flash-preview-09-2025:generateContent?key=${apiKey}`, { method: 'POST', headers: { 'Content-Type': 'application/json', }, body: JSON.stringify({ contents: [{ parts: [{ text: prompt }] }], systemInstruction: { parts: [{ text: systemInstruction }] }, }), } ); if (!response.ok) { throw new Error(`API Error: ${response.status}`); } const data = await response.json(); let text = data.candidates?.[0]?.content?.parts?.[0]?.text || "抱歉,我暂时无法回答这个问题。"; // 清理 markdown 代码块标记,以便直接渲染 HTML text = text.replace(/^```html\s*/, '').replace(/```$/, ''); return text; } catch (error) { console.error("Gemini API Call Failed:", error); return "

AI 服务暂时不可用,请稍后再试。

"; } }; // --- Modal Component (用于展示 AI 生成的内容) --- const AIModal = ({ isOpen, onClose, title, content, isLoading }) => { if (!isOpen) return null; return (

{title}

{isLoading ? (

Gemini 正在为您绘制可视化的执行清单...

) : ( // 使用 dangerouslySetInnerHTML 渲染 AI 生成的 HTML 结构
)}
); }; // --- 组件部分 --- const SlideCard = ({ slide, onGenerateChecklist }) => (
{slide.icon}

{slide.title}

{slide.phase}

{slide.tag && {slide.tag}}

{slide.date}

{slide.content.map((block, idx) => { if (block.type === 'subtitle') return

{block.text}

; if (block.type === 'text') return

{block.text}

; if (block.type === 'list') return (
    {block.items.map((item, i) =>
  • {item}
  • )}
); if (block.type === 'table') return (
{block.rows.map((row, rIdx) => ( ))}
{row[0]} {row[1]}
); return null; })}
{/* AI 功能按钮 */}
); const ChatMessage = ({ msg }) => (
{msg.isBot && (
)}
{msg.text}
); const FAQItem = ({ q, a }) => { const [isOpen, setIsOpen] = useState(false); return (
{isOpen && (
{a}
)}
); }; const ResourceCard = ({ resource }) => (
{resource.type === 'PPT' ? ( ) : ( )}

{resource.name}

{resource.type}

{resource.desc}

{resource.size} 更新于 {resource.date}
); export default function ProjectManualApp() { const [activeTab, setActiveTab] = useState('chat'); const [input, setInput] = useState(''); const [isTyping, setIsTyping] = useState(false); // AI Modal State const [modalOpen, setModalOpen] = useState(false); const [modalTitle, setModalTitle] = useState(''); const [modalContent, setModalContent] = useState(''); const [isModalLoading, setIsModalLoading] = useState(false); const [chatHistory, setChatHistory] = useState([ { id: 1, isBot: true, text: "你好!我是升级版的项目管理 AI 助手。\n\n我不止会关键词匹配,现在我可以基于手册内容,理解您的复杂问题。\n\n您可以问我:\n- “如果是老客户,申请 Code 一般要几天?”\n- “2026年关于供应商付款有哪些严厉的新规?”" } ]); const chatEndRef = useRef(null); const scrollToBottom = () => { chatEndRef.current?.scrollIntoView({ behavior: "smooth" }); }; useEffect(() => { scrollToBottom(); }, [chatHistory, isTyping]); // --- AI Handlers --- const handleSend = async () => { if (!input.trim()) return; const userMsg = { id: Date.now(), isBot: false, text: input }; setChatHistory(prev => [...prev, userMsg]); setInput(''); setIsTyping(true); const systemInstruction = ` 你是一个专业的项目管理手册咨询顾问。请根据以下提供的知识库内容回答用户的问题。 知识库内容 (包含2025/2026新规, 常见问题, 流程): ${MANUAL_CONTEXT} 回答原则: 1. 必须基于知识库内容回答。如果知识库没有提及,请礼貌地说明“手册中未找到相关规定,建议咨询中台”。 2. 2026年的新规(如财务部分)优先级高于旧规则,请特别提示用户。 3. 回答要清晰、分点陈述,语气专业亲切。 `; try { const aiResponseText = await callGemini(input, systemInstruction); setChatHistory(prev => [...prev, { id: Date.now() + 1, isBot: true, text: aiResponseText }]); } catch (error) { setChatHistory(prev => [...prev, { id: Date.now()+1, isBot: true, text: "抱歉,AI 服务连接失败。" }]); } finally { setIsTyping(false); } }; const handleGenerateChecklist = async (slide) => { setModalTitle(`智能执行清单: ${slide.title}`); setModalContent(''); setIsModalLoading(true); setModalOpen(true); const prompt = ` 请根据项目管理手册中 "${slide.title}" (${slide.phase}) 的内容,生成一个非常直观、可视化的 HTML 执行清单。 该阶段内容参考: ${JSON.stringify(slide.content)} 要求: 1. **不要**返回 Markdown 代码,直接返回一段完整的
HTML 代码。 2. 使用 **Tailwind CSS** 类名来美化界面,风格要求现代、清爽、商务。 3. **呈现形式(必须生动,选一种最适合的)**: - 如果内容是流程(如审批流),请设计成一个带有箭头图标的“流程图”样式(横向或纵向 Flex 布局)。 - 如果内容是待办事项,请设计成一个“卡片矩阵”或“表格”,包含“责任人”、“动作”、“关键点”等列。 - 使用 Emoji 图标(如 👤, 📝, ⚠️, ✅)来增强视觉效果。 - 关键的审批节点(如 Raymond Lu, Wise Xu)请用醒目的颜色(如 bg-red-100 text-red-700)高亮显示。 4. 结构清晰,包含一个简短的总结性标题。 `; const system = `你是一个前端专家和项目经理助理。你的任务是将枯燥的文本转化为精美的 HTML/Tailwind CSS 可视化图表。不要使用 Markdown 格式,直接输出 HTML 字符串。`; try { const text = await callGemini(prompt, system); setModalContent(text); } catch (e) { setModalContent("
生成失败,请稍后再试。
"); } finally { setIsModalLoading(false); } }; const handleKeyPress = (e) => { if (e.key === 'Enter') handleSend(); }; return (
setModalOpen(false)} title={modalTitle} content={modalContent} isLoading={isModalLoading} /> {/* 顶部导航 */}

Project Manual Hub AI Powered

项目管理手册 & 智能办公平台

{/* 主内容区域 */}
{/* 1. 智能聊天界面 */} {activeTab === 'chat' && (
{chatHistory.map(msg => ( ))} {isTyping && (
AI 正在思考中...
)}
setInput(e.target.value)} onKeyPress={handleKeyPress} placeholder="请输入您的问题... (支持复杂语义,例如:如何处理跨年签署的 Special Code?)" className="w-full pl-4 pr-12 py-4 bg-gray-50 border border-gray-200 rounded-xl focus:outline-none focus:ring-2 focus:ring-indigo-500 focus:bg-white transition-all shadow-sm" disabled={isTyping} />

Powered by Gemini 2.5 Flash

)} {/* 2. PPT 时间轴界面 (带生成清单功能) */} {activeTab === 'timeline' && (
{[...TIMELINE_SLIDES].reverse().map((slide, index) => (
{index < TIMELINE_SLIDES.length - 1 && (
)}
))}

持续更新中...

管理员将根据项目进展,随时补充新的 PPT 页面至此时间轴。

)} {/* 3. 资料下载界面 (无 AI 摘要) */} {activeTab === 'downloads' && (

资料下载中心

一键获取最新的项目管理手册、PPT 及财务规范文件。

{DOWNLOAD_RESOURCES.map((resource) => ( ))}
)} {/* 4. FAQ 界面 */} {activeTab === 'faq' && (

常见问题清单

汇集大家最关心的流程与财务问题

{FAQ_DATA.map((category, idx) => (

{category.category}

{category.questions.map((q, qIdx) => ( ))}
))}
)}
); }