停滞期和改图期的数据保存在 Parse 数据库的 Project 表的 data 字段中:
Project 表
├── id (字符串)
├── title (字符串) - 项目标题
├── currentStage (字符串) - 当前阶段(如"订单分配"、"确认需求"、"交付执行"等)
├── stage (字符串) - 兼容旧字段,与 currentStage 类似
└── data (JSON 对象) ⬅️ 停滞期和改图期数据在这里
├── isStalled (布尔值) - 是否处于停滞期
├── isModification (布尔值) - 是否处于改图期
├── stagnationReasonType (字符串) - 停滞原因类型
├── stagnationCustomReason (字符串) - 自定义停滞原因
├── modificationReasonType (字符串) - 改图原因类型
├── modificationCustomReason (字符串) - 自定义改图原因
├── estimatedResumeDate (日期) - 预计恢复时间
├── reasonNotes (字符串) - 备注说明
├── markedAt (日期) - 标记时间
├── markedBy (字符串) - 标记人
└── ... (其他项目数据)
Project.stage 字段中Project.currentStage 字段中ProjectFile 表中currentStage 字段用途:存储项目当前所处的工作流阶段
可能的值:
"订单分配" - 订单分配阶段"确认需求" - 确认需求阶段"方案深化" - 方案深化阶段"交付执行" / "白模" / "软装" / "渲染" / "后期" - 交付执行阶段"尾款结算" - 售后归档阶段示例:
{
"currentStage": "交付执行"
}
stage 字段用途:兼容旧版本的阶段字段,功能与 currentStage 类似
说明:在新代码中主要使用 currentStage,但保留 stage 以兼容旧数据
data 字段用途:存储项目的扩展数据,包括停滞期、改图期等状态信息
完整结构示例:
{
"data": {
// 停滞期相关
"isStalled": true,
"stagnationReasonType": "customer",
"stagnationCustomReason": "",
"estimatedResumeDate": "2024-12-15T00:00:00.000Z",
"reasonNotes": "客户出差暂时无法沟通",
"markedAt": "2024-12-07T13:42:00.000Z",
"markedBy": "张组长",
// 改图期相关(互斥,同时只能有一个为 true)
"isModification": false,
"modificationReasonType": "",
"modificationCustomReason": "",
// 其他扩展数据
"phaseDeadlines": { ... },
"approvalStatus": "approved",
"requirementsAnalysis": { ... },
// ...
}
}
private async updateProjectMarkStatus(
projectId: string,
type: 'stagnation' | 'modification',
reason: any
): Promise<void> {
const Parse = (window as any).Parse;
const query = new Parse.Query('Project');
const project = await query.get(projectId);
// ✅ 获取 data 字段
const projectData = project.get('data') || {};
// ✅ 设置停滞期/改图期字段
if (type === 'stagnation') {
projectData.isStalled = true;
projectData.isModification = false;
projectData.stagnationReasonType = reason.reasonType;
projectData.stagnationCustomReason = reason.customReason;
projectData.estimatedResumeDate = reason.estimatedResumeDate;
projectData.reasonNotes = reason.notes;
projectData.markedAt = new Date();
projectData.markedBy = this.currentUser.name;
} else {
projectData.isModification = true;
projectData.isStalled = false;
projectData.modificationReasonType = reason.reasonType;
projectData.modificationCustomReason = reason.customReason;
projectData.reasonNotes = reason.notes;
projectData.markedAt = new Date();
projectData.markedBy = this.currentUser.name;
}
// ✅ 保存回 data 字段
project.set('data', projectData);
await project.save();
}
// ✅ 从 data 字段读取停滞期状态
get isStalled(): boolean {
const data = this.project?.get('data') || {};
return data.isStalled === true;
}
// ✅ 从 data 字段读取改图期状态
get isModification(): boolean {
const data = this.project?.get('data') || {};
return data.isModification === true;
}
// ✅ 从 data 字段读取停滞期详情
get stagnationInfo() {
const data = this.project?.get('data') || {};
return {
reasonType: data.stagnationReasonType,
customReason: data.stagnationCustomReason,
estimatedResumeDate: data.estimatedResumeDate,
notes: data.reasonNotes,
markedAt: data.markedAt,
markedBy: data.markedBy
};
}
const Parse = require('parse/node');
const query = new Parse.Query('Project');
// 注意:Parse 不支持直接查询嵌套 JSON 字段
// 需要使用特殊语法或在代码中过滤
// 获取所有项目后过滤
const projects = await query.find();
const stalledProjects = projects.filter(p => {
const data = p.get('data') || {};
return data.isStalled === true;
});
console.log('停滞期项目数量:', stalledProjects.length);
const query = new Parse.Query('Project');
const projects = await query.find();
const modificationProjects = projects.filter(p => {
const data = p.get('data') || {};
return data.isModification === true;
});
console.log('改图期项目数量:', modificationProjects.length);
const query = new Parse.Query('Project');
const project = await query.get('项目ID');
const data = project.get('data') || {};
data.isStalled = true;
data.stagnationReasonType = 'customer';
data.markedAt = new Date();
project.set('data', data);
await project.save();
要验证停滞期/改图期数据是否正确保存,可以检查:
Project 类data 列(JSON 格式)isStalled 或 isModification 字段// 在浏览器控制台运行
const Parse = window.Parse;
const query = new Parse.Query('Project');
query.get('你的项目ID').then(project => {
const data = project.get('data');
console.log('停滞期:', data.isStalled);
console.log('改图期:', data.isModification);
console.log('完整data:', data);
});
标记项目后,控制台应该显示:
✅ [数据库] 停滞期标记已保存到数据库 项目ID
currentStage 字段中?A: currentStage 表示项目的工作流阶段(如"订单分配"、"交付执行"),与停滞期/改图期的状态标记是不同的概念。一个项目可以同时处于"交付执行"阶段和"停滞期"状态。
ProjectFile 表中?A: ProjectFile 表用于存储项目文件(图片、文档等),而停滞期/改图期是项目级别的状态,应该保存在 Project 表中。
A: 由于 Parse 限制,无法直接查询嵌套 JSON 字段。建议:
data.isStalled === true 的项目Project 表添加顶层字段 isStalled(需要同步更新)A: 不会。所有标记操作都会调用 project.save() 保存到 Parse 数据库。只要保存成功(有日志确认),数据就会持久化。
✅ 停滞期和改图期数据保存在:Project.data.isStalled / Project.data.isModification
❌ 不在:Project.currentStage 或 Project.stage
❌ 不在:ProjectFile 表
如需查看实际数据库内容,请访问 Parse Dashboard 查看 Project 表的 data 字段。