THREE_PAGES_DATA_ISSUE.md 12 KB

三个页面数据获取和审批状态问题分析

🎯 问题概述

您描述的问题:

  1. ❌ 项目从列表进入时,跳转到错误的阶段页面
  2. ❌ 经过组长审批的项目,审批状态依旧显示"待审批"
  3. ❌ 审批信息没有正确传递和同步

📊 三个页面的数据获取分析

1️⃣ 管理端项目管理 (project-management.ts)

数据来源Project

关键代码

// 第196行:查询Project表
const projects = await this.projectService.findProjects({ limit: 100 });

// 第220行:获取阶段
const rawStage = json.currentStage || json.stage || '订单分配';

// 第223行:规范化阶段名称
const normalizedStage = normalizeStage(rawStage);

// 第226行:根据阶段自动判断状态
const autoStatus = getProjectStatusByStage(rawStage, json.status);

// 第248行:使用规范化后的阶段
currentStage: normalizedStage

字段映射

  • currentStage → 规范化后的阶段名称
  • status → 根据阶段自动判断的状态

2️⃣ 客服端项目列表 (project-list.ts)

数据来源Project

关键代码

// 第435行:查询Project表
const ProjectQuery = new Parse.Query('Project');
const projectObjects = await ProjectQuery.find();

// 第479行:获取阶段(优先currentStage)
let rawStage = obj.get('currentStage') || obj.get('stage') || '订单分配';

// 第486-490行:统一交付执行子阶段
if (this.isDeliveryExecutionStage(rawStage)) {
  finalStage = '交付执行';
}

// 第494行:根据阶段自动判断状态
const autoStatus = getProjectStatusByStage(rawStage, projectStatus);

// 第508行:使用统一后的阶段
currentStage: finalStage as ProjectStage

跳转逻辑 (第894-924行):

navigateToProject(project, columnId) {
  // ❌ 问题:使用columnId而不是project.currentStage
  const stagePath = stagePathMapping[columnId];
  this.router.navigate(['/wxwork', cid, 'project', project.id, stagePath]);
}

3️⃣ 组长端看板 (dashboard.ts)

数据来源Project 表(通过DesignerService)

关键代码

// 第551行:加载项目
const realProjects = await this.designerService.getProjects();

// 第428, 520行:获取阶段
currentStage: project.get('currentStage') || '未知阶段'

跳转逻辑 (第850-876行):

viewProjectDetails(projectId: string) {
  const project = this.projects.find(p => p.id === projectId);
  const currentStage = project?.currentStage || '订单分配';
  
  // ✅ 正确:使用project.currentStage
  const stagePath = stageRouteMap[currentStage] || 'order';
  this.router.navigate(['/wxwork', cid, 'project', projectId, stagePath]);
}

❌ 发现的核心问题

问题1:客服端跳转使用错误的阶段

错误代码 (project-list.ts 第894-924行):

navigateToProject(project: ProjectListItem, columnId: 'order' | 'requirements' | 'delivery' | 'aftercare') {
  //  ❌ 使用columnId(看板列ID),而不是project.currentStage
  const stagePath = stagePathMapping[columnId];
  this.router.navigate(['/wxwork', cid, 'project', project.id, stagePath]);
}

问题

  • 项目实际阶段是 "确认需求"
  • 但如果项目在"订单分配"看板列,columnId = 'order'
  • 导致跳转到 /project/{id}/order 而不是 /project/{id}/requirements

正确方式

navigateToProject(project: ProjectListItem) {
  // ✅ 应该根据project.currentStage决定路由
  const stageRouteMap = {
    '订单分配': 'order',
    '确认需求': 'requirements',
    '交付执行': 'delivery',
    '售后归档': 'aftercare'
  };
  const stagePath = stageRouteMap[project.currentStage] || 'order';
  this.router.navigate(['/wxwork', cid, 'project', project.id, stagePath]);
}

问题2:自动回退机制可能过度回退

代码位置 (project-detail.component.ts 第462-548行)

问题分析

// 第492行:检查审批状态
const notApproved = approvalStatus !== 'approved';

if (orderStageIncomplete || notApproved) {
  // ❌ 即使项目已经正常推进到确认需求,如果某些字段缺失也会回退
  needRollback = true;
  correctStage = '订单分配';
}

可能导致

  • 组长已审批通过的项目
  • currentStage 已经是 "确认需求"
  • 但如果 approvalStatus 字段丢失或未同步
  • 会被错误地回退到"订单分配"

问题3:审批状态同步可能不完整

审批通过代码 (stage-order.component.ts 第546-602行):

async approveOrder(): Promise<void> {
  // 第570行:设置审批状态
  data.approvalStatus = 'approved';
  
  // 第576行:推进到确认需求
  this.project.set('currentStage', '确认需求');
  
  // 第585行:保存
  await this.project.save();
  
  // 第596-600行:刷新验证
  this.project = await query.get(this.project.id);
}

可能的问题

  1. ⚠️ 保存后没有通知其他页面刷新
  2. ⚠️ 其他端可能缓存了旧数据
  3. ⚠️ 自动回退机制可能覆盖了审批结果

🔧 完整修复方案

修复1:客服端跳转逻辑

文件project-list.ts 第894-924行

// 修改前
navigateToProject(project: ProjectListItem, columnId: 'order' | 'requirements' | 'delivery' | 'aftercare') {
  const stagePath = stagePathMapping[columnId];  // ❌ 错误
  this.router.navigate(['/wxwork', cid, 'project', project.id, stagePath]);
}

// 修改后
navigateToProject(project: ProjectListItem) {
  const cid = localStorage.getItem('company') || '';
  if (!cid) {
    console.error('未找到公司ID');
    return;
  }
  
  // ✅ 根据项目实际阶段决定路由
  const stageRouteMap: Record<string, string> = {
    '订单分配': 'order',
    '确认需求': 'requirements',
    '方案确认': 'requirements',
    '方案深化': 'requirements',
    '交付执行': 'delivery',
    '建模': 'delivery',
    '软装': 'delivery',
    '渲染': 'delivery',
    '后期': 'delivery',
    '白模': 'delivery',
    '售后归档': 'aftercare',
    '尾款结算': 'aftercare',
    '客户评价': 'aftercare'
  };
  
  const currentStage = project.currentStage || '订单分配';
  const stagePath = stageRouteMap[currentStage] || 'order';
  
  console.log(`🎯 项目"${project.name}"当前阶段: ${currentStage}, 跳转到: ${stagePath}`);
  
  localStorage.setItem('enterFromCustomerService', '1');
  localStorage.setItem('customerServiceMode', 'true');
  
  this.router.navigate(['/wxwork', cid, 'project', project.id, stagePath]);
}

修复2:优化自动回退检查

文件project-detail.component.ts 第462-548行

// 修改检查逻辑,增加智能判断
if (projectStage && ['确认需求', '交付执行', '售后归档', ...].includes(projectStage)) {
  const title = this.project.get('title');
  const projectType = this.project.get('projectType');
  const demoday = this.project.get('demoday');
  const quotationTotal = data.quotation?.total || 0;
  const approvalStatus = data.approvalStatus;
  
  // 检查订单分配阶段是否完成
  const orderStageIncomplete = !title || !projectType || !demoday || quotationTotal <= 0;
  
  // ✅ 智能判断:如果有审批历史且最后一次是通过,认为已审批
  const hasApprovedHistory = data.approvalHistory?.some((h: any) => 
    h.stage === '订单分配' && h.status === 'approved'
  );
  
  // ⚠️ 只有在明确未审批且阶段未完成时才回退
  const notApproved = approvalStatus !== 'approved' && !hasApprovedHistory;
  
  if (orderStageIncomplete || notApproved) {
    // 只有当两个条件都满足时才回退
    if (orderStageIncomplete && notApproved) {
      needRollback = true;
      correctStage = '订单分配';
      rollbackReason = `订单分配阶段未完成`;
    } else {
      console.warn('⚠️ 项目数据不完整但已审批,不回退');
    }
  }
}

修复3:组长审批后强制刷新

文件stage-order.component.ts 第546-602行

async approveOrder(): Promise<void> {
  if (!this.project || !this.currentUser) return;

  try {
    const data = this.project.get('data') || {};
    const approvalHistory = data.approvalHistory || [];

    approvalHistory.push({
      stage: '订单分配',
      status: 'approved',
      approver: this.currentUser.id,
      approverName: this.currentUser.get('name'),
      timestamp: new Date(),
      comment: '组长审批通过'
    });

    data.approvalHistory = approvalHistory;
    data.approvalStatus = 'approved';  // ✅ 明确设置
    delete data.lastRejectionReason;
    delete data.pendingApprovalBy;

    this.project.set('data', data);
    this.project.set('currentStage', '确认需求');  // ✅ 推进阶段
    this.project.set('pendingApproval', false);
    
    console.log('📝 [审批通过] 准备保存:', {
      approvalStatus: data.approvalStatus,
      currentStage: '确认需求'
    });

    await this.project.save();
    
    // ✅ 强制刷新验证
    const query = new Parse.Query('Project');
    query.include('contact', 'assignee', 'customer', 'department');
    this.project = await query.get(this.project.id);
    
    const savedData = this.project.get('data') || {};
    console.log('✅ [审批通过] 保存后验证:', {
      approvalStatus: savedData.approvalStatus,  // 应该是 'approved'
      currentStage: this.project.get('currentStage')  // 应该是 '确认需求'
    });
    
    // ✅ 确保前端状态同步
    if (savedData.approvalStatus !== 'approved') {
      console.error('❌ 审批状态未正确保存!');
    }
    if (this.project.get('currentStage') !== '确认需求') {
      console.error('❌ 项目阶段未正确推进!');
    }
    
    window?.fmode?.alert('审批通过,项目已进入确认需求阶段');
    
    // ✅ 派发事件通知父组件刷新
    document.dispatchEvent(new CustomEvent('stage:completed', {
      detail: { stage: 'order', nextStage: 'requirements' }
    }));
    
  } catch (error) {
    console.error('审批通过失败:', error);
    window?.fmode?.alert('审批失败: ' + (error as any).message);
  }
}

📋 验证步骤

测试1:组长审批后检查数据

  1. 组长端审批通过项目
  2. 打开浏览器控制台,查看日志:

    ✅ [审批通过] 保存后验证:
     approvalStatus: "approved"
     currentStage: "确认需求"
    
  3. 刷新客服端项目列表,检查:

    • 项目是否显示在"确认需求"列
    • 点击项目是否跳转到 /project/{id}/requirements

测试2:从客服端进入项目

  1. 客服端点击项目
  2. 查看控制台日志

    🎯 项目"xxx"当前阶段: 确认需求, 跳转到: requirements
    
  3. 验证跳转

    • URL应该是 /wxwork/{cid}/project/{id}/requirements
    • 页面应该显示确认需求阶段的内容

测试3:检查自动回退是否正常

  1. 创建一个已审批的项目
  2. 删除部分必填字段(模拟数据不完整)
  3. 打开项目
  4. 查看是否错误回退
    • 如果有审批历史,应该不回退
    • 控制台显示:"⚠️ 项目数据不完整但已审批,不回退"

📂 需要修改的文件

  1. project-list.ts - 修复客服端跳转逻辑
  2. project-detail.component.ts - 优化自动回退检查
  3. stage-order.component.ts - 增强审批通过后的验证

🎯 修复后的效果

正确的流程

1. 组长审批通过
   ├─ approvalStatus = 'approved'
   ├─ currentStage = '确认需求'
   └─ 保存并验证

2. 客服端看到项目更新
   ├─ 项目显示在"确认需求"列
   └─ currentStage = '确认需求'

3. 客服端点击项目
   ├─ 读取 project.currentStage = '确认需求'
   ├─ 映射路由: stageRouteMap['确认需求'] = 'requirements'
   └─ 跳转: /wxwork/{cid}/project/{id}/requirements

4. 进入项目详情
   ├─ 自动回退检查
   ├─ 发现有审批历史且已通过
   ├─ 不回退
   └─ 显示确认需求页面

🚀 立即执行

让我现在就修复这些问题!