@dalmasonto/taskflow-mcp 1.0.2 → 1.0.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +14 -6
- package/dist/tools/timer.js +17 -6
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -3,21 +3,29 @@ import { startSSEServer } from './sse.js';
|
|
|
3
3
|
import { getDb } from './db.js';
|
|
4
4
|
import { broadcast } from './sse.js';
|
|
5
5
|
const httpOnly = process.argv.includes('--http-only');
|
|
6
|
-
// Close
|
|
7
|
-
//
|
|
6
|
+
// Close orphaned sessions left from a previous crash.
|
|
7
|
+
// Uses a grace period so that sessions from the current conversation
|
|
8
|
+
// (stdio transport restarts the server on each tool call) are preserved.
|
|
9
|
+
const ORPHAN_GRACE_MS = 5 * 60 * 1000; // 5 minutes
|
|
8
10
|
function cleanupOrphanedSessions() {
|
|
9
11
|
const db = getDb();
|
|
10
|
-
const
|
|
11
|
-
const
|
|
12
|
+
const nowMs = Date.now();
|
|
13
|
+
const nowIso = new Date(nowMs).toISOString();
|
|
14
|
+
const cutoff = new Date(nowMs - ORPHAN_GRACE_MS).toISOString();
|
|
15
|
+
// Only close sessions that started more than ORPHAN_GRACE_MS ago
|
|
16
|
+
const orphaned = db.prepare('SELECT * FROM sessions WHERE end IS NULL AND start < ?').all(cutoff);
|
|
12
17
|
if (orphaned.length === 0)
|
|
13
18
|
return;
|
|
14
|
-
|
|
19
|
+
// Close each orphaned session with end = now (preserves the real elapsed time)
|
|
20
|
+
for (const session of orphaned) {
|
|
21
|
+
db.prepare('UPDATE sessions SET end = ? WHERE id = ?').run(nowIso, session.id);
|
|
22
|
+
}
|
|
15
23
|
// Set orphaned in_progress tasks back to paused
|
|
16
24
|
const taskIds = [...new Set(orphaned.map(s => s.task_id))];
|
|
17
25
|
for (const taskId of taskIds) {
|
|
18
26
|
const task = db.prepare('SELECT status FROM tasks WHERE id = ?').get(taskId);
|
|
19
27
|
if (task?.status === 'in_progress') {
|
|
20
|
-
db.prepare("UPDATE tasks SET status = 'paused', updated_at = ? WHERE id = ?").run(
|
|
28
|
+
db.prepare("UPDATE tasks SET status = 'paused', updated_at = ? WHERE id = ?").run(nowIso, taskId);
|
|
21
29
|
broadcast('task_updated', { entity: 'task', action: 'task_status_changed', payload: db.prepare('SELECT * FROM tasks WHERE id = ?').get(taskId) });
|
|
22
30
|
}
|
|
23
31
|
}
|
package/dist/tools/timer.js
CHANGED
|
@@ -35,12 +35,23 @@ export async function pauseTimer(params) {
|
|
|
35
35
|
return errorResponse('Task not found', 'NOT_FOUND');
|
|
36
36
|
// Find open session
|
|
37
37
|
const session = db.prepare('SELECT * FROM sessions WHERE task_id = ? AND end IS NULL').get(params.task_id);
|
|
38
|
-
if (!session)
|
|
39
|
-
return errorResponse('No active timer session for this task', 'NO_ACTIVE_SESSION');
|
|
40
38
|
const endTime = now();
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
39
|
+
let duration;
|
|
40
|
+
let closedSession;
|
|
41
|
+
if (session) {
|
|
42
|
+
// Normal path — close the active session
|
|
43
|
+
duration = new Date(endTime).getTime() - new Date(session.start).getTime();
|
|
44
|
+
db.prepare('UPDATE sessions SET end = ? WHERE id = ?').run(endTime, session.id);
|
|
45
|
+
closedSession = { ...session, end: endTime };
|
|
46
|
+
}
|
|
47
|
+
else {
|
|
48
|
+
// Fallback — session already closed (orphan cleanup, auto-close)
|
|
49
|
+
const lastSession = db.prepare('SELECT * FROM sessions WHERE task_id = ? ORDER BY start DESC LIMIT 1').get(params.task_id);
|
|
50
|
+
if (!lastSession)
|
|
51
|
+
return errorResponse('No timer sessions found for this task', 'NO_ACTIVE_SESSION');
|
|
52
|
+
duration = new Date(lastSession.end).getTime() - new Date(lastSession.start).getTime();
|
|
53
|
+
closedSession = lastSession;
|
|
54
|
+
}
|
|
44
55
|
// Update task to paused
|
|
45
56
|
db.prepare('UPDATE tasks SET status = ?, updated_at = ? WHERE id = ?').run('paused', endTime, params.task_id);
|
|
46
57
|
logActivity('timer_paused', task.title, {
|
|
@@ -48,7 +59,7 @@ export async function pauseTimer(params) {
|
|
|
48
59
|
entityType: 'task',
|
|
49
60
|
entityId: params.task_id,
|
|
50
61
|
});
|
|
51
|
-
const pausedSession = { ...
|
|
62
|
+
const pausedSession = { ...closedSession, duration };
|
|
52
63
|
broadcastChange('timer', 'timer_paused', { task_id: params.task_id, session: pausedSession, task_status: 'paused' });
|
|
53
64
|
return successResponse(pausedSession);
|
|
54
65
|
}
|