2025102211-data-loading-fix.md 6.3 KB

数据加载与甘特图显示问题修复

日期: 2025-10-22 11:00 问题: 控制台报错 TypeError: deadline.getTime is not a function,甘特图无法显示真实数据


问题分析

1. 主要错误

TypeError: deadline.getTime is not a function
  at DesignerService.transformProject (designer.service.ts:219:42)

2. 根本原因

transformProject 中直接调用 deadline.getTime(),但未验证 deadline 是否为 Date 对象。Parse 查询可能返回:

  • Date 对象(正常)
  • null/undefined(字段不存在)
  • 字符串(类型不匹配)

3. 甘特图显示说明

甘特图设计是正确的

  • ✅ Y轴显示设计师名字(按负载排序)
  • ✅ X轴显示时间轴(周/月视图)
  • ✅ 条形图显示每个设计师负责的项目及其时间线
  • ✅ 颜色标识项目紧急度(红色=高,橙色=中,绿色=低)
  • ✅ 背景色标识设计师负载状态(绿色=空闲,红色=超负荷)

这就是"设计师排版时间轴"的正确呈现方式。用户看到的"项目数据"是指条形图中的项目名称和截止日期,这是预期行为


修复内容

1. 修复 Date 类型处理(designer.service.ts)

calculateProjectWeight (Line 164-188)

// 修复前
const deadline = project.get?.('deadline') || project.deadline;
const daysLeft = deadline ? Math.ceil((deadline.getTime() - now.getTime()) / ...) : 30;

// 修复后
const deadlineRaw = project.get?.('deadline') || project.deadline;
const deadline = deadlineRaw instanceof Date ? deadlineRaw : (deadlineRaw ? new Date(deadlineRaw) : null);
const daysLeft = deadline ? Math.ceil((deadline.getTime() - now.getTime()) / ...) : 30;

transformProject (Line 216-221)

// 修复前
const deadline = project.get('deadline') || new Date();

// 修复后
const deadlineRaw = project.get('deadline');
const deadline = deadlineRaw instanceof Date ? deadlineRaw : (deadlineRaw ? new Date(deadlineRaw) : new Date());

2. 添加调试日志

constructor (Line 36-40):

constructor() {
  this.cid = localStorage.getItem('company') || '';
  console.log('🏢 DesignerService初始化,当前公司ID:', this.cid || '(未设置)');
  this.initParse();
}

getProjects (Line 193-227):

async getProjects(): Promise<any[]> {
  const Parse = await this.ensureParse();
  if (!Parse) {
    console.error('❌ Parse未初始化,无法查询项目');
    return [];
  }
  
  if (!this.cid) {
    console.error('❌ 未找到公司ID(localStorage的company字段为空),无法查询项目');
    return [];
  }
  
  console.log('🔍 开始查询项目,company:', this.cid);
  const query = new Parse.Query('Project');
  // ... 查询逻辑
  
  console.log(`✅ Parse查询成功,找到 ${projects.length} 个项目`);
  
  if (projects.length === 0) {
    console.warn('⚠️ 数据库中没有符合条件的项目数据');
    console.warn('💡 提示:请确保Project表中有数据,且company字段=', this.cid);
  }
  
  return projects.map((p: any) => this.transformProject(p));
}

验证步骤

1. 检查控制台日志

刷新页面后,应该看到以下日志:

🏢 DesignerService初始化,当前公司ID: <你的company ID>
✅ DesignerService: FmodeParse 初始化成功
🔍 开始查询项目,company: <你的company ID>
✅ Parse查询成功,找到 X 个项目

2. 如果看到"未找到公司ID"

说明 localStorage.getItem('company') 为空,需要:

  • 确认是否已登录
  • 检查登录流程是否正确设置了 localStorage.company

3. 如果看到"找到 0 个项目"

说明数据库中没有符合条件的Project数据,需要:

  • 确认Project表中有数据
  • 确认Project.company字段与当前company ID匹配
  • 确认Project.isDeleted字段不为true

4. 检查甘特图显示

如果有真实数据,甘特图应该显示:

  • Y轴:设计师名字列表
  • X轴:时间轴(默认显示"周"视图,未来7天)
  • 条形图:每个设计师负责的项目
  • 颜色:红色(高紧急度)、橙色(中)、绿色(低)
  • 背景:绿色背景=设计师空闲可接单,红色背景=超负荷

数据准备

确保Project表有测试数据

// 在Parse Dashboard或云函数中执行:
const Project = Parse.Object.extend("Project");
const project = new Project();

project.set("title", "测试项目-现代客厅设计");
project.set("company", "<你的company objectId>");
project.set("status", "进行中");
project.set("currentStage", "modeling");
project.set("deadline", new Date(Date.now() + 7 * 24 * 60 * 60 * 1000)); // 7天后

// 可选:关联设计师
const Profile = Parse.Object.extend("Profile");
const designer = Profile.createWithoutData("<设计师objectId>");
project.set("assignee", designer);

// 可选:设置扩展数据
project.set("data", {
  projectType: "soft", // soft=软装, hard=硬装
  urgency: "high",     // high/medium/low
  style: "现代简约"
});

await project.save();

确保Profile表有设计师数据

const Profile = Parse.Object.extend("Profile");
const profile = new Profile();

profile.set("name", "张三");
profile.set("company", "<你的company objectId>");
profile.set("roleName", "组员"); // 重要:必须是"组员"角色
profile.set("data", {
  tags: {
    expertise: {
      styles: ["现代简约", "北欧风格"],
      skills: ["建模", "渲染"],
      spaceTypes: ["客厅", "卧室"]
    },
    capacity: {
      weeklyProjects: 3,
      maxConcurrent: 5,
      avgDaysPerProject: 10
    },
    emergency: {
      willing: true,
      premium: 20,
      maxPerWeek: 2
    },
    history: {
      totalProjects: 15,
      completionRate: 90,
      avgRating: 4.5,
      onTimeRate: 85,
      excellentCount: 5
    },
    portfolio: []
  }
});

await profile.save();

下一步

如果数据库中确实没有数据,系统会自动使用模拟数据(fallback机制),甘特图仍然可以正常显示和测试。

等数据准备好后,刷新页面即可看到真实数据。


相关文件

  • src/app/pages/team-leader/services/designer.service.ts - 修复Date处理,添加调试日志
  • src/app/pages/team-leader/dashboard/dashboard.ts - 调用数据服务
  • rules/schemas.md - YSS项目的数据表结构