-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathscheduleTree.js
162 lines (162 loc) · 5.6 KB
/
scheduleTree.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
// Serves the schedule-state report page.
const serveScheduleReport = op => {
const {
err,
fs,
globals,
reportPrep,
reportScriptPrep,
servePage
} = op;
fs.readFile('scheduleReport.html', 'utf8')
.then(
htmlContent => {
fs.readFile('report.js', 'utf8')
.then(
jsContent => {
const newJSContent = reportScriptPrep(
jsContent,
'/scheduletally',
['total', 'changes', 'storyTotal', 'storyChanges', 'taskTotal', 'taskChanges', 'error']
);
const newContent = reportPrep(htmlContent, newJSContent)
.replace('__scheduleState__', globals.state.story);
servePage(newContent, true);
},
error => err(error, 'reading scheduleReport script')
);
},
error => err(error, 'reading scheduleReport page')
);
};
// Handles project change requests.
const scheduleHandle = (op, bodyObject) => {
const {setState} = op;
// Set the global state variable.
setState(bodyObject.scheduleState);
// Serve a report.
serveScheduleReport(op);
};
// Recursively sets the states of an array of tasks.
const scheduleTasks = (op, tasks) => {
const {globals, err, shorten, report} = op;
if (tasks.length && ! globals.isError) {
const firstTask = tasks[0];
const firstRef = shorten('task', 'task', firstTask.ref);
if (! globals.isError) {
// If the task’s state needs to be changed:
if (firstTask.state !== globals.state.task) {
// Change it.
return globals.restAPI.update({
ref: firstRef,
data: {
State: globals.state.task
}
})
.then(
// When it has been changed:
() => {
report([['total'], ['taskTotal'], ['changes'], ['taskChanges']]);
// Process the remaining tasks.
return scheduleTasks(op, tasks.slice(1));
},
error => err(error, 'changing state of task')
);
}
// Otherwise, i.e. if the task’s state does not need to be changed:
else {
report([['total'], ['taskTotal']]);
// Process the remaining tasks.
return scheduleTasks(op, tasks.slice(1));
}
}
else {
return Promise.resolve('');
}
}
else {
return Promise.resolve('');
}
};
// Recursively sets the schedule state in a tree or subtree of user stories.
const scheduleTree = (op, storyRefs) => {
const {globals, err, shorten, report, getItemData, getCollectionData} = op;
if (storyRefs.length && ! globals.isError) {
const firstRef = shorten('userstory', 'hierarchicalrequirement', storyRefs[0]);
if (! globals.isError) {
// Get data on the first user story.
return getItemData(firstRef, ['FormattedID', 'ScheduleState'], ['Children', 'Tasks'])
.then(
// When the data arrive:
data => {
report([['total'], ['storyTotal']]);
// Report progress in the console if requested.
if (globals.debug) {
console.log(`Processing ${data.formattedID}`);
}
// Change the schedule state of the user story if necessary.
const changeNeeded = ! data.children.count
&& ! data.tasks.count
&& data.scheduleState !== globals.state.story;
return (changeNeeded ? globals.restAPI.update({
ref: firstRef,
data: {
ScheduleState: globals.state.story
}
}) : Promise.resolve(''))
.then(
// When the change, if any, has been made:
() => {
changeNeeded && report([['changes'], ['storyChanges']]);
// Get data on the tasks of the user story, if any.
return getCollectionData(data.tasks.ref, ['State'], [])
.then(
// When the data arrive:
tasks => {
// Change the states of any tasks, if necessary.
return scheduleTasks(op, tasks)
.then(
// When the changes, if any, have been made:
() => {
// Get data on the child user stories of the user story, if any.
return getCollectionData(data.children.ref, [], [])
.then(
// When the data arrive:
children => {
// Process the child user stories.
return scheduleTree(
op, children.length ? children.map(child => child.ref) : []
)
.then(
/*
When the child user stories, if any, have been processed, process
the remaining user stories.
*/
() => scheduleTree(op, storyRefs.slice(1)),
error => err(error, 'changing schedule states of child user stories')
);
},
error => err(error, 'getting data on child user stories')
);
},
error => err(error, 'changing states of tasks')
);
},
error => err(error, 'getting data on tasks')
);
}
);
},
error => err(error, 'getting data on user story')
);
}
else {
return Promise.resolve('');
}
}
else {
return Promise.resolve('');
}
};
exports.scheduleHandle = scheduleHandle;
exports.scheduleTree = scheduleTree;