agkan 2.14.3 → 3.0.1
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/README.ja.md +62 -238
- package/README.md +48 -241
- package/dist/board/boardFavicon.d.ts +2 -0
- package/dist/board/boardFavicon.d.ts.map +1 -0
- package/dist/board/boardFavicon.js +5 -0
- package/dist/board/boardFavicon.js.map +1 -0
- package/dist/board/boardRenderer.d.ts +22 -6
- package/dist/board/boardRenderer.d.ts.map +1 -1
- package/dist/board/boardRenderer.js +67 -26
- package/dist/board/boardRenderer.js.map +1 -1
- package/dist/board/boardRoutes.d.ts +4 -2
- package/dist/board/boardRoutes.d.ts.map +1 -1
- package/dist/board/boardRoutes.js +140 -13
- package/dist/board/boardRoutes.js.map +1 -1
- package/dist/board/boardStyles.d.ts +1 -1
- package/dist/board/boardStyles.d.ts.map +1 -1
- package/dist/board/boardStyles.js +62 -8
- package/dist/board/boardStyles.js.map +1 -1
- package/dist/board/client/board.js +1007 -29
- package/dist/board/server.d.ts +3 -2
- package/dist/board/server.d.ts.map +1 -1
- package/dist/board/server.js +9 -7
- package/dist/board/server.js.map +1 -1
- package/dist/cli/commands/agent-guide.d.ts.map +1 -1
- package/dist/cli/commands/agent-guide.js +6 -0
- package/dist/cli/commands/agent-guide.js.map +1 -1
- package/dist/cli/commands/board.d.ts.map +1 -1
- package/dist/cli/commands/board.js +202 -15
- package/dist/cli/commands/board.js.map +1 -1
- package/dist/cli/commands/ps.d.ts +7 -0
- package/dist/cli/commands/ps.d.ts.map +1 -0
- package/dist/cli/commands/ps.js +83 -0
- package/dist/cli/commands/ps.js.map +1 -0
- package/dist/cli/commands/tag/add.d.ts.map +1 -1
- package/dist/cli/commands/tag/add.js +10 -11
- package/dist/cli/commands/tag/add.js.map +1 -1
- package/dist/cli/commands/tag/attach.d.ts.map +1 -1
- package/dist/cli/commands/tag/attach.js +10 -11
- package/dist/cli/commands/tag/attach.js.map +1 -1
- package/dist/cli/commands/tag/rename.d.ts.map +1 -1
- package/dist/cli/commands/tag/rename.js +10 -11
- package/dist/cli/commands/tag/rename.js.map +1 -1
- package/dist/cli/commands/task/add.js +1 -1
- package/dist/cli/commands/task/add.js.map +1 -1
- package/dist/cli/commands/task/copy.d.ts +6 -0
- package/dist/cli/commands/task/copy.d.ts.map +1 -0
- package/dist/cli/commands/task/copy.js +118 -0
- package/dist/cli/commands/task/copy.js.map +1 -0
- package/dist/cli/commands/task/list.d.ts.map +1 -1
- package/dist/cli/commands/task/list.js +37 -17
- package/dist/cli/commands/task/list.js.map +1 -1
- package/dist/cli/commands/task/update-parent.d.ts.map +1 -1
- package/dist/cli/commands/task/update-parent.js +10 -11
- package/dist/cli/commands/task/update-parent.js.map +1 -1
- package/dist/cli/index.js +6 -0
- package/dist/cli/index.js.map +1 -1
- package/dist/cli/utils/board-daemon.d.ts +7 -0
- package/dist/cli/utils/board-daemon.d.ts.map +1 -0
- package/dist/cli/utils/board-daemon.js +83 -0
- package/dist/cli/utils/board-daemon.js.map +1 -0
- package/dist/db/adapters/sqlite-storage-backend.d.ts +27 -0
- package/dist/db/adapters/sqlite-storage-backend.d.ts.map +1 -0
- package/dist/db/adapters/sqlite-storage-backend.js +498 -0
- package/dist/db/adapters/sqlite-storage-backend.js.map +1 -0
- package/dist/db/connection.d.ts +19 -0
- package/dist/db/connection.d.ts.map +1 -1
- package/dist/db/connection.js +37 -2
- package/dist/db/connection.js.map +1 -1
- package/dist/db/migrations/20260328000000_initial_schema.d.ts +3 -0
- package/dist/db/migrations/20260328000000_initial_schema.d.ts.map +1 -0
- package/dist/db/migrations/20260328000000_initial_schema.js +218 -0
- package/dist/db/migrations/20260328000000_initial_schema.js.map +1 -0
- package/dist/db/migrations/20260329000000_add_session_id_to_task_run_logs.d.ts +3 -0
- package/dist/db/migrations/20260329000000_add_session_id_to_task_run_logs.d.ts.map +1 -0
- package/dist/db/migrations/20260329000000_add_session_id_to_task_run_logs.js +7 -0
- package/dist/db/migrations/20260329000000_add_session_id_to_task_run_logs.js.map +1 -0
- package/dist/db/migrations/index.d.ts +4 -0
- package/dist/db/migrations/index.d.ts.map +1 -0
- package/dist/db/migrations/index.js +18 -0
- package/dist/db/migrations/index.js.map +1 -0
- package/dist/db/migrations/types.d.ts +17 -0
- package/dist/db/migrations/types.d.ts.map +1 -0
- package/dist/{board/client → db/migrations}/types.js +0 -1
- package/dist/db/migrations/types.js.map +1 -0
- package/dist/db/reset.d.ts.map +1 -1
- package/dist/db/reset.js +8 -3
- package/dist/db/reset.js.map +1 -1
- package/dist/db/schema.d.ts +4 -4
- package/dist/db/schema.d.ts.map +1 -1
- package/dist/db/schema.js +22 -207
- package/dist/db/schema.js.map +1 -1
- package/dist/db/types/repository.d.ts +226 -0
- package/dist/db/types/repository.d.ts.map +1 -0
- package/dist/db/types/repository.js +15 -0
- package/dist/db/types/repository.js.map +1 -0
- package/dist/errors.d.ts +27 -0
- package/dist/errors.d.ts.map +1 -0
- package/dist/errors.js +51 -0
- package/dist/errors.js.map +1 -0
- package/dist/models/Task.d.ts +2 -0
- package/dist/models/Task.d.ts.map +1 -1
- package/dist/services/ClaudeProcessService.d.ts +100 -0
- package/dist/services/ClaudeProcessService.d.ts.map +1 -0
- package/dist/services/ClaudeProcessService.js +279 -0
- package/dist/services/ClaudeProcessService.js.map +1 -0
- package/dist/services/CommentService.d.ts +3 -3
- package/dist/services/CommentService.d.ts.map +1 -1
- package/dist/services/CommentService.js +13 -72
- package/dist/services/CommentService.js.map +1 -1
- package/dist/services/ExportImportService.d.ts +3 -3
- package/dist/services/ExportImportService.d.ts.map +1 -1
- package/dist/services/ExportImportService.js +29 -31
- package/dist/services/ExportImportService.js.map +1 -1
- package/dist/services/MetadataService.d.ts +3 -3
- package/dist/services/MetadataService.d.ts.map +1 -1
- package/dist/services/MetadataService.js +9 -69
- package/dist/services/MetadataService.js.map +1 -1
- package/dist/services/ProcessService.d.ts +54 -0
- package/dist/services/ProcessService.d.ts.map +1 -0
- package/dist/services/ProcessService.js +147 -0
- package/dist/services/ProcessService.js.map +1 -0
- package/dist/services/TagService.d.ts +3 -3
- package/dist/services/TagService.d.ts.map +1 -1
- package/dist/services/TagService.js +16 -41
- package/dist/services/TagService.js.map +1 -1
- package/dist/services/TaskBlockService.d.ts +3 -3
- package/dist/services/TaskBlockService.d.ts.map +1 -1
- package/dist/services/TaskBlockService.js +14 -40
- package/dist/services/TaskBlockService.js.map +1 -1
- package/dist/services/TaskService.d.ts +5 -23
- package/dist/services/TaskService.d.ts.map +1 -1
- package/dist/services/TaskService.js +57 -191
- package/dist/services/TaskService.js.map +1 -1
- package/dist/services/TaskTagService.d.ts +3 -3
- package/dist/services/TaskTagService.d.ts.map +1 -1
- package/dist/services/TaskTagService.js +23 -86
- package/dist/services/TaskTagService.js.map +1 -1
- package/dist/services/TmuxService.d.ts +2 -0
- package/dist/services/TmuxService.d.ts.map +1 -0
- package/dist/services/TmuxService.js +7 -0
- package/dist/services/TmuxService.js.map +1 -0
- package/dist/services/index.d.ts +2 -0
- package/dist/services/index.d.ts.map +1 -1
- package/dist/services/index.js +3 -1
- package/dist/services/index.js.map +1 -1
- package/dist/utils/logger.d.ts +7 -0
- package/dist/utils/logger.d.ts.map +1 -0
- package/dist/utils/logger.js +18 -0
- package/dist/utils/logger.js.map +1 -0
- package/package.json +12 -5
- package/dist/board/client/addTaskModal.d.ts +0 -2
- package/dist/board/client/addTaskModal.d.ts.map +0 -1
- package/dist/board/client/addTaskModal.js +0 -64
- package/dist/board/client/addTaskModal.js.map +0 -1
- package/dist/board/client/autoScroll.d.ts +0 -4
- package/dist/board/client/autoScroll.d.ts.map +0 -1
- package/dist/board/client/autoScroll.js +0 -59
- package/dist/board/client/autoScroll.js.map +0 -1
- package/dist/board/client/boardPolling.d.ts +0 -15
- package/dist/board/client/boardPolling.d.ts.map +0 -1
- package/dist/board/client/boardPolling.js +0 -144
- package/dist/board/client/boardPolling.js.map +0 -1
- package/dist/board/client/burgerMenu.d.ts +0 -2
- package/dist/board/client/burgerMenu.d.ts.map +0 -1
- package/dist/board/client/burgerMenu.js +0 -80
- package/dist/board/client/burgerMenu.js.map +0 -1
- package/dist/board/client/contextMenu.d.ts +0 -2
- package/dist/board/client/contextMenu.d.ts.map +0 -1
- package/dist/board/client/contextMenu.js +0 -52
- package/dist/board/client/contextMenu.js.map +0 -1
- package/dist/board/client/detailPanel.d.ts +0 -8
- package/dist/board/client/detailPanel.d.ts.map +0 -1
- package/dist/board/client/detailPanel.js +0 -565
- package/dist/board/client/detailPanel.js.map +0 -1
- package/dist/board/client/dragDrop.d.ts +0 -6
- package/dist/board/client/dragDrop.d.ts.map +0 -1
- package/dist/board/client/dragDrop.js +0 -82
- package/dist/board/client/dragDrop.js.map +0 -1
- package/dist/board/client/filters.d.ts +0 -6
- package/dist/board/client/filters.d.ts.map +0 -1
- package/dist/board/client/filters.js +0 -167
- package/dist/board/client/filters.js.map +0 -1
- package/dist/board/client/main.d.ts +0 -2
- package/dist/board/client/main.d.ts.map +0 -1
- package/dist/board/client/main.js +0 -20
- package/dist/board/client/main.js.map +0 -1
- package/dist/board/client/tags.d.ts +0 -6
- package/dist/board/client/tags.d.ts.map +0 -1
- package/dist/board/client/tags.js +0 -198
- package/dist/board/client/tags.js.map +0 -1
- package/dist/board/client/types.d.ts +0 -48
- package/dist/board/client/types.d.ts.map +0 -1
- package/dist/board/client/types.js.map +0 -1
- package/dist/board/client/utils.d.ts +0 -4
- package/dist/board/client/utils.d.ts.map +0 -1
- package/dist/board/client/utils.js +0 -44
- package/dist/board/client/utils.js.map +0 -1
|
@@ -13,21 +13,21 @@ const TaskBlockService_1 = require("./TaskBlockService");
|
|
|
13
13
|
* Handles JSON bulk export and import of tasks with all related data
|
|
14
14
|
*/
|
|
15
15
|
class ExportImportService {
|
|
16
|
-
|
|
16
|
+
backend;
|
|
17
17
|
taskService;
|
|
18
18
|
tagService;
|
|
19
19
|
taskTagService;
|
|
20
20
|
metadataService;
|
|
21
21
|
commentService;
|
|
22
22
|
taskBlockService;
|
|
23
|
-
constructor(
|
|
24
|
-
this.
|
|
25
|
-
this.taskService = new TaskService_1.TaskService(this.
|
|
26
|
-
this.tagService = new TagService_1.TagService(this.
|
|
27
|
-
this.taskTagService = new TaskTagService_1.TaskTagService(this.
|
|
28
|
-
this.metadataService = new MetadataService_1.MetadataService(this.
|
|
29
|
-
this.commentService = new CommentService_1.CommentService(this.
|
|
30
|
-
this.taskBlockService = new TaskBlockService_1.TaskBlockService(this.
|
|
23
|
+
constructor(backend) {
|
|
24
|
+
this.backend = backend ?? (0, connection_1.getStorageBackend)();
|
|
25
|
+
this.taskService = new TaskService_1.TaskService(this.backend);
|
|
26
|
+
this.tagService = new TagService_1.TagService(this.backend);
|
|
27
|
+
this.taskTagService = new TaskTagService_1.TaskTagService(this.backend);
|
|
28
|
+
this.metadataService = new MetadataService_1.MetadataService(this.backend);
|
|
29
|
+
this.commentService = new CommentService_1.CommentService(this.backend);
|
|
30
|
+
this.taskBlockService = new TaskBlockService_1.TaskBlockService(this.backend);
|
|
31
31
|
}
|
|
32
32
|
/**
|
|
33
33
|
* Build a map from task_id to list of blocker task IDs
|
|
@@ -103,10 +103,8 @@ class ExportImportService {
|
|
|
103
103
|
status: exportedTask.status,
|
|
104
104
|
parent_id: newParentId,
|
|
105
105
|
});
|
|
106
|
-
// Restore original timestamps via
|
|
107
|
-
this.
|
|
108
|
-
.prepare('UPDATE tasks SET created_at = ?, updated_at = ? WHERE id = ?')
|
|
109
|
-
.run(exportedTask.created_at, exportedTask.updated_at, newTask.id);
|
|
106
|
+
// Restore original timestamps via the backend
|
|
107
|
+
this.backend.updateTaskTimestamps(newTask.id, exportedTask.created_at, exportedTask.updated_at);
|
|
110
108
|
return newTask.id;
|
|
111
109
|
}
|
|
112
110
|
/**
|
|
@@ -136,9 +134,7 @@ class ExportImportService {
|
|
|
136
134
|
author: comment.author || undefined,
|
|
137
135
|
content: comment.content,
|
|
138
136
|
});
|
|
139
|
-
this.
|
|
140
|
-
.prepare('UPDATE task_comments SET created_at = ?, updated_at = ? WHERE id = ?')
|
|
141
|
-
.run(comment.created_at, comment.updated_at, newComment.id);
|
|
137
|
+
this.backend.comments.updateTimestamps(newComment.id, comment.created_at, comment.updated_at);
|
|
142
138
|
}
|
|
143
139
|
}
|
|
144
140
|
/**
|
|
@@ -174,22 +170,24 @@ class ExportImportService {
|
|
|
174
170
|
* @returns Import result with count and ID mapping
|
|
175
171
|
*/
|
|
176
172
|
importData(data) {
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
const
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
173
|
+
return this.backend.transaction(() => {
|
|
174
|
+
const idMapping = new Map();
|
|
175
|
+
const sortedTasks = this.sortTasksByParent(data.tasks);
|
|
176
|
+
for (const exportedTask of sortedTasks) {
|
|
177
|
+
const newTaskId = this.importTask(exportedTask, idMapping);
|
|
178
|
+
idMapping.set(exportedTask.id, newTaskId);
|
|
179
|
+
this.importTaskTags(newTaskId, exportedTask.tags);
|
|
180
|
+
for (const [key, value] of Object.entries(exportedTask.metadata)) {
|
|
181
|
+
this.metadataService.setMetadata({ task_id: newTaskId, key, value });
|
|
182
|
+
}
|
|
183
|
+
this.importTaskComments(newTaskId, exportedTask.comments);
|
|
185
184
|
}
|
|
186
|
-
this.
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
};
|
|
185
|
+
this.importBlockRelationships(data.tasks, idMapping);
|
|
186
|
+
return {
|
|
187
|
+
importedCount: sortedTasks.length,
|
|
188
|
+
idMapping,
|
|
189
|
+
};
|
|
190
|
+
});
|
|
193
191
|
}
|
|
194
192
|
/**
|
|
195
193
|
* Sort tasks so parents come before children (topological sort)
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ExportImportService.js","sourceRoot":"","sources":["../../src/services/ExportImportService.ts"],"names":[],"mappings":";;;AAAA,
|
|
1
|
+
{"version":3,"file":"ExportImportService.js","sourceRoot":"","sources":["../../src/services/ExportImportService.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
import { TaskMetadata, CreateTaskMetadataInput } from '../models';
|
|
2
|
-
import {
|
|
2
|
+
import { StorageBackend } from '../db/types/repository';
|
|
3
3
|
/**
|
|
4
4
|
* Metadata Service
|
|
5
5
|
* Manages creation, retrieval, update, and deletion of task metadata
|
|
6
6
|
*/
|
|
7
7
|
export declare class MetadataService {
|
|
8
|
-
private
|
|
9
|
-
constructor(
|
|
8
|
+
private backend;
|
|
9
|
+
constructor(backend?: StorageBackend);
|
|
10
10
|
/**
|
|
11
11
|
* Set metadata for a task (create or update)
|
|
12
12
|
* @param input - Metadata creation input
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MetadataService.d.ts","sourceRoot":"","sources":["../../src/services/MetadataService.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,uBAAuB,EAAE,MAAM,WAAW,CAAC;AAElE,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"MetadataService.d.ts","sourceRoot":"","sources":["../../src/services/MetadataService.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,uBAAuB,EAAE,MAAM,WAAW,CAAC;AAElE,OAAO,EAAE,cAAc,EAAE,MAAM,wBAAwB,CAAC;AAExD;;;GAGG;AACH,qBAAa,eAAe;IAC1B,OAAO,CAAC,OAAO,CAAiB;gBAEpB,OAAO,CAAC,EAAE,cAAc;IAIpC;;;;OAIG;IACH,WAAW,CAAC,KAAK,EAAE,uBAAuB,GAAG,YAAY;IAKzD;;;;;OAKG;IACH,gBAAgB,CAAC,MAAM,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,YAAY,GAAG,IAAI;IAIlE;;;;OAIG;IACH,YAAY,CAAC,MAAM,EAAE,MAAM,GAAG,YAAY,EAAE;IAI5C;;;;;OAKG;IACH,cAAc,CAAC,MAAM,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO;IAIpD;;;;OAIG;IACH,mBAAmB,IAAI,GAAG,CAAC,MAAM,EAAE,YAAY,EAAE,CAAC;IAIlD;;;;OAIG;IACH,iBAAiB,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM;CAG1C"}
|
|
@@ -7,9 +7,9 @@ const connection_1 = require("../db/connection");
|
|
|
7
7
|
* Manages creation, retrieval, update, and deletion of task metadata
|
|
8
8
|
*/
|
|
9
9
|
class MetadataService {
|
|
10
|
-
|
|
11
|
-
constructor(
|
|
12
|
-
this.
|
|
10
|
+
backend;
|
|
11
|
+
constructor(backend) {
|
|
12
|
+
this.backend = backend ?? (0, connection_1.getStorageBackend)();
|
|
13
13
|
}
|
|
14
14
|
/**
|
|
15
15
|
* Set metadata for a task (create or update)
|
|
@@ -17,29 +17,8 @@ class MetadataService {
|
|
|
17
17
|
* @returns Metadata object
|
|
18
18
|
*/
|
|
19
19
|
setMetadata(input) {
|
|
20
|
-
const db = this.db;
|
|
21
|
-
// Check if metadata already exists
|
|
22
|
-
const existing = this.getMetadataByKey(input.task_id, input.key);
|
|
23
20
|
const now = new Date().toISOString();
|
|
24
|
-
|
|
25
|
-
// Update existing metadata
|
|
26
|
-
const stmt = db.prepare(`
|
|
27
|
-
UPDATE task_metadata
|
|
28
|
-
SET value = ?, updated_at = ?
|
|
29
|
-
WHERE task_id = ? AND key = ?
|
|
30
|
-
`);
|
|
31
|
-
stmt.run(input.value, now, input.task_id, input.key);
|
|
32
|
-
return this.getMetadataByKey(input.task_id, input.key);
|
|
33
|
-
}
|
|
34
|
-
else {
|
|
35
|
-
// Create new metadata
|
|
36
|
-
const stmt = db.prepare(`
|
|
37
|
-
INSERT INTO task_metadata (task_id, key, value, created_at, updated_at)
|
|
38
|
-
VALUES (?, ?, ?, ?, ?)
|
|
39
|
-
`);
|
|
40
|
-
stmt.run(input.task_id, input.key, input.value, now, now);
|
|
41
|
-
return this.getMetadataByKey(input.task_id, input.key);
|
|
42
|
-
}
|
|
21
|
+
return this.backend.metadata.set({ ...input, created_at: now, updated_at: now });
|
|
43
22
|
}
|
|
44
23
|
/**
|
|
45
24
|
* Get metadata by task ID and key
|
|
@@ -48,13 +27,7 @@ class MetadataService {
|
|
|
48
27
|
* @returns Metadata object or null if not found
|
|
49
28
|
*/
|
|
50
29
|
getMetadataByKey(taskId, key) {
|
|
51
|
-
|
|
52
|
-
const stmt = db.prepare(`
|
|
53
|
-
SELECT * FROM task_metadata
|
|
54
|
-
WHERE task_id = ? AND key = ?
|
|
55
|
-
`);
|
|
56
|
-
const result = stmt.get(taskId, key);
|
|
57
|
-
return result ? result : null;
|
|
30
|
+
return this.backend.metadata.findByKey(taskId, key);
|
|
58
31
|
}
|
|
59
32
|
/**
|
|
60
33
|
* List metadata for a task
|
|
@@ -62,14 +35,7 @@ class MetadataService {
|
|
|
62
35
|
* @returns Array of metadata objects
|
|
63
36
|
*/
|
|
64
37
|
listMetadata(taskId) {
|
|
65
|
-
|
|
66
|
-
const stmt = db.prepare(`
|
|
67
|
-
SELECT * FROM task_metadata
|
|
68
|
-
WHERE task_id = ?
|
|
69
|
-
ORDER BY created_at DESC
|
|
70
|
-
`);
|
|
71
|
-
const results = stmt.all(taskId);
|
|
72
|
-
return results;
|
|
38
|
+
return this.backend.metadata.findByTaskId(taskId);
|
|
73
39
|
}
|
|
74
40
|
/**
|
|
75
41
|
* Delete metadata by task ID and key
|
|
@@ -78,13 +44,7 @@ class MetadataService {
|
|
|
78
44
|
* @returns True if deletion succeeded, false if metadata not found
|
|
79
45
|
*/
|
|
80
46
|
deleteMetadata(taskId, key) {
|
|
81
|
-
|
|
82
|
-
const stmt = db.prepare(`
|
|
83
|
-
DELETE FROM task_metadata
|
|
84
|
-
WHERE task_id = ? AND key = ?
|
|
85
|
-
`);
|
|
86
|
-
const result = stmt.run(taskId, key);
|
|
87
|
-
return result.changes > 0;
|
|
47
|
+
return this.backend.metadata.delete(taskId, key);
|
|
88
48
|
}
|
|
89
49
|
/**
|
|
90
50
|
* Get all metadata for multiple tasks at once
|
|
@@ -92,21 +52,7 @@ class MetadataService {
|
|
|
92
52
|
* @returns Map<task_id, TaskMetadata[]>
|
|
93
53
|
*/
|
|
94
54
|
getAllTasksMetadata() {
|
|
95
|
-
|
|
96
|
-
const stmt = db.prepare(`
|
|
97
|
-
SELECT * FROM task_metadata
|
|
98
|
-
ORDER BY task_id, created_at DESC
|
|
99
|
-
`);
|
|
100
|
-
const results = stmt.all();
|
|
101
|
-
const metadataMap = new Map();
|
|
102
|
-
for (const row of results) {
|
|
103
|
-
const taskId = row.task_id;
|
|
104
|
-
if (!metadataMap.has(taskId)) {
|
|
105
|
-
metadataMap.set(taskId, []);
|
|
106
|
-
}
|
|
107
|
-
metadataMap.get(taskId).push(row);
|
|
108
|
-
}
|
|
109
|
-
return metadataMap;
|
|
55
|
+
return this.backend.metadata.findAllGroupedByTaskId();
|
|
110
56
|
}
|
|
111
57
|
/**
|
|
112
58
|
* Delete all metadata for a task
|
|
@@ -114,13 +60,7 @@ class MetadataService {
|
|
|
114
60
|
* @returns Number of deleted metadata entries
|
|
115
61
|
*/
|
|
116
62
|
deleteAllMetadata(taskId) {
|
|
117
|
-
|
|
118
|
-
const stmt = db.prepare(`
|
|
119
|
-
DELETE FROM task_metadata
|
|
120
|
-
WHERE task_id = ?
|
|
121
|
-
`);
|
|
122
|
-
const result = stmt.run(taskId);
|
|
123
|
-
return result.changes;
|
|
63
|
+
return this.backend.metadata.deleteAllForTask(taskId);
|
|
124
64
|
}
|
|
125
65
|
}
|
|
126
66
|
exports.MetadataService = MetadataService;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MetadataService.js","sourceRoot":"","sources":["../../src/services/MetadataService.ts"],"names":[],"mappings":";;;AACA,
|
|
1
|
+
{"version":3,"file":"MetadataService.js","sourceRoot":"","sources":["../../src/services/MetadataService.ts"],"names":[],"mappings":";;;AACA,iDAAqD;AAGrD;;;GAGG;AACH,MAAa,eAAe;IAClB,OAAO,CAAiB;IAEhC,YAAY,OAAwB;QAClC,IAAI,CAAC,OAAO,GAAG,OAAO,IAAI,IAAA,8BAAiB,GAAE,CAAC;IAChD,CAAC;IAED;;;;OAIG;IACH,WAAW,CAAC,KAA8B;QACxC,MAAM,GAAG,GAAG,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,CAAC;QACrC,OAAO,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,GAAG,KAAK,EAAE,UAAU,EAAE,GAAG,EAAE,UAAU,EAAE,GAAG,EAAE,CAAC,CAAC;IACnF,CAAC;IAED;;;;;OAKG;IACH,gBAAgB,CAAC,MAAc,EAAE,GAAW;QAC1C,OAAO,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;IACtD,CAAC;IAED;;;;OAIG;IACH,YAAY,CAAC,MAAc;QACzB,OAAO,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC;IACpD,CAAC;IAED;;;;;OAKG;IACH,cAAc,CAAC,MAAc,EAAE,GAAW;QACxC,OAAO,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;IACnD,CAAC;IAED;;;;OAIG;IACH,mBAAmB;QACjB,OAAO,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,sBAAsB,EAAE,CAAC;IACxD,CAAC;IAED;;;;OAIG;IACH,iBAAiB,CAAC,MAAc;QAC9B,OAAO,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,gBAAgB,CAAC,MAAM,CAAC,CAAC;IACxD,CAAC;CACF;AA/DD,0CA+DC"}
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
export interface TmuxSessionInfo {
|
|
2
|
+
name: string;
|
|
3
|
+
created: string;
|
|
4
|
+
windows: string;
|
|
5
|
+
attached: string;
|
|
6
|
+
}
|
|
7
|
+
/**
|
|
8
|
+
* Service for managing tmux sessions using child_process.spawn.
|
|
9
|
+
* Avoids zombie processes by using native Node.js APIs with spawn for tmux sessions.
|
|
10
|
+
* Properly handles process reaping in Docker containers by using:
|
|
11
|
+
* - spawn with detached=true for session creation (allows proper signal handling)
|
|
12
|
+
* - execSync for query operations (tmux commands that don't spawn long-lived processes)
|
|
13
|
+
*
|
|
14
|
+
* The key fix: tmux new-session is spawned with detached=true so it becomes
|
|
15
|
+
* a child of init, preventing zombie processes when the Node.js container doesn't
|
|
16
|
+
* have a proper init system.
|
|
17
|
+
*/
|
|
18
|
+
export declare class ProcessService {
|
|
19
|
+
/**
|
|
20
|
+
* Start a new tmux session running the given command.
|
|
21
|
+
* Uses spawn with detached=true to prevent zombie processes in Docker.
|
|
22
|
+
* Throws if a session with the same name already exists (double-start prevention).
|
|
23
|
+
*/
|
|
24
|
+
startSession(sessionName: string, command: string): void;
|
|
25
|
+
/**
|
|
26
|
+
* Kill an existing tmux session.
|
|
27
|
+
*/
|
|
28
|
+
killSession(sessionName: string): void;
|
|
29
|
+
/**
|
|
30
|
+
* List all tmux sessions.
|
|
31
|
+
* Returns an empty array when no tmux server is running.
|
|
32
|
+
*/
|
|
33
|
+
listSessions(): TmuxSessionInfo[];
|
|
34
|
+
/**
|
|
35
|
+
* Check whether a session with the given name currently exists.
|
|
36
|
+
*/
|
|
37
|
+
sessionExists(sessionName: string): boolean;
|
|
38
|
+
/**
|
|
39
|
+
* Capture the visible pane content of a tmux session.
|
|
40
|
+
* Returns the captured text, or null when the session does not exist.
|
|
41
|
+
*/
|
|
42
|
+
capturePane(sessionName: string, lines?: number): string | null;
|
|
43
|
+
/**
|
|
44
|
+
* Asynchronously stream pane content at regular intervals.
|
|
45
|
+
* Calls onData with each captured snapshot and onEnd when the session exits.
|
|
46
|
+
* Returns a stop function to cancel polling.
|
|
47
|
+
*/
|
|
48
|
+
streamPane(sessionName: string, onData: (chunk: string) => void, onEnd: () => void, intervalMs?: number): () => void;
|
|
49
|
+
/**
|
|
50
|
+
* Send a key sequence to a tmux session pane.
|
|
51
|
+
*/
|
|
52
|
+
sendKeys(sessionName: string, keys: string): void;
|
|
53
|
+
}
|
|
54
|
+
//# sourceMappingURL=ProcessService.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ProcessService.d.ts","sourceRoot":"","sources":["../../src/services/ProcessService.ts"],"names":[],"mappings":"AAEA,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED;;;;;;;;;;GAUG;AACH,qBAAa,cAAc;IACzB;;;;OAIG;IACH,YAAY,CAAC,WAAW,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,IAAI;IAiBxD;;OAEG;IACH,WAAW,CAAC,WAAW,EAAE,MAAM,GAAG,IAAI;IAQtC;;;OAGG;IACH,YAAY,IAAI,eAAe,EAAE;IAoBjC;;OAEG;IACH,aAAa,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO;IAS3C;;;OAGG;IACH,WAAW,CAAC,WAAW,EAAE,MAAM,EAAE,KAAK,GAAE,MAAY,GAAG,MAAM,GAAG,IAAI;IAcpE;;;;OAIG;IACH,UAAU,CACR,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,EAC/B,KAAK,EAAE,MAAM,IAAI,EACjB,UAAU,GAAE,MAAY,GACvB,MAAM,IAAI;IA4Bb;;OAEG;IACH,QAAQ,CAAC,WAAW,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,IAAI;CASlD"}
|
|
@@ -0,0 +1,147 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.ProcessService = void 0;
|
|
4
|
+
const child_process_1 = require("child_process");
|
|
5
|
+
/**
|
|
6
|
+
* Service for managing tmux sessions using child_process.spawn.
|
|
7
|
+
* Avoids zombie processes by using native Node.js APIs with spawn for tmux sessions.
|
|
8
|
+
* Properly handles process reaping in Docker containers by using:
|
|
9
|
+
* - spawn with detached=true for session creation (allows proper signal handling)
|
|
10
|
+
* - execSync for query operations (tmux commands that don't spawn long-lived processes)
|
|
11
|
+
*
|
|
12
|
+
* The key fix: tmux new-session is spawned with detached=true so it becomes
|
|
13
|
+
* a child of init, preventing zombie processes when the Node.js container doesn't
|
|
14
|
+
* have a proper init system.
|
|
15
|
+
*/
|
|
16
|
+
class ProcessService {
|
|
17
|
+
/**
|
|
18
|
+
* Start a new tmux session running the given command.
|
|
19
|
+
* Uses spawn with detached=true to prevent zombie processes in Docker.
|
|
20
|
+
* Throws if a session with the same name already exists (double-start prevention).
|
|
21
|
+
*/
|
|
22
|
+
startSession(sessionName, command) {
|
|
23
|
+
if (this.sessionExists(sessionName)) {
|
|
24
|
+
throw new Error(`Session '${sessionName}' already exists`);
|
|
25
|
+
}
|
|
26
|
+
// Use spawn with detached=true and stdio 'ignore' for proper process management
|
|
27
|
+
// This allows the tmux server to become a child of init rather than Node.js,
|
|
28
|
+
// preventing zombie processes when Node.js doesn't reap children
|
|
29
|
+
const child = (0, child_process_1.spawn)('tmux', ['new-session', '-d', '-s', sessionName, command], {
|
|
30
|
+
stdio: 'ignore',
|
|
31
|
+
detached: true,
|
|
32
|
+
});
|
|
33
|
+
// Immediately unref so Node.js doesn't wait for this process
|
|
34
|
+
child.unref();
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Kill an existing tmux session.
|
|
38
|
+
*/
|
|
39
|
+
killSession(sessionName) {
|
|
40
|
+
try {
|
|
41
|
+
(0, child_process_1.execSync)(`tmux kill-session -t ${shellEscape(sessionName)}`, { stdio: 'pipe' });
|
|
42
|
+
}
|
|
43
|
+
catch {
|
|
44
|
+
// Session might not exist, that's fine
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
/**
|
|
48
|
+
* List all tmux sessions.
|
|
49
|
+
* Returns an empty array when no tmux server is running.
|
|
50
|
+
*/
|
|
51
|
+
listSessions() {
|
|
52
|
+
try {
|
|
53
|
+
const output = (0, child_process_1.execSync)("tmux list-sessions -F '#{session_name}|#{session_created_string}|#{session_windows}|#{session_attached}'", { stdio: 'pipe' })
|
|
54
|
+
.toString()
|
|
55
|
+
.trim();
|
|
56
|
+
if (!output)
|
|
57
|
+
return [];
|
|
58
|
+
return output.split('\n').map((line) => {
|
|
59
|
+
const [name, created, windows, attached] = line.split('|');
|
|
60
|
+
return { name, created, windows, attached };
|
|
61
|
+
});
|
|
62
|
+
}
|
|
63
|
+
catch {
|
|
64
|
+
// No server running or no sessions
|
|
65
|
+
return [];
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
/**
|
|
69
|
+
* Check whether a session with the given name currently exists.
|
|
70
|
+
*/
|
|
71
|
+
sessionExists(sessionName) {
|
|
72
|
+
try {
|
|
73
|
+
(0, child_process_1.execSync)(`tmux has-session -t ${shellEscape(sessionName)}`, { stdio: 'pipe' });
|
|
74
|
+
return true;
|
|
75
|
+
}
|
|
76
|
+
catch {
|
|
77
|
+
return false;
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
/**
|
|
81
|
+
* Capture the visible pane content of a tmux session.
|
|
82
|
+
* Returns the captured text, or null when the session does not exist.
|
|
83
|
+
*/
|
|
84
|
+
capturePane(sessionName, lines = 500) {
|
|
85
|
+
if (!this.sessionExists(sessionName)) {
|
|
86
|
+
return null;
|
|
87
|
+
}
|
|
88
|
+
try {
|
|
89
|
+
const output = (0, child_process_1.execSync)(`tmux capture-pane -pt ${shellEscape(sessionName)} -S -${lines}`, {
|
|
90
|
+
stdio: 'pipe',
|
|
91
|
+
}).toString();
|
|
92
|
+
return output;
|
|
93
|
+
}
|
|
94
|
+
catch {
|
|
95
|
+
return null;
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
/**
|
|
99
|
+
* Asynchronously stream pane content at regular intervals.
|
|
100
|
+
* Calls onData with each captured snapshot and onEnd when the session exits.
|
|
101
|
+
* Returns a stop function to cancel polling.
|
|
102
|
+
*/
|
|
103
|
+
streamPane(sessionName, onData, onEnd, intervalMs = 500) {
|
|
104
|
+
let lastContent = '';
|
|
105
|
+
let stopped = false;
|
|
106
|
+
const poll = () => {
|
|
107
|
+
if (stopped)
|
|
108
|
+
return;
|
|
109
|
+
if (!this.sessionExists(sessionName)) {
|
|
110
|
+
onEnd();
|
|
111
|
+
return;
|
|
112
|
+
}
|
|
113
|
+
const content = this.capturePane(sessionName);
|
|
114
|
+
if (content !== null && content !== lastContent) {
|
|
115
|
+
lastContent = content;
|
|
116
|
+
onData(content);
|
|
117
|
+
}
|
|
118
|
+
setTimeout(poll, intervalMs);
|
|
119
|
+
};
|
|
120
|
+
setTimeout(poll, 0);
|
|
121
|
+
return () => {
|
|
122
|
+
stopped = true;
|
|
123
|
+
};
|
|
124
|
+
}
|
|
125
|
+
/**
|
|
126
|
+
* Send a key sequence to a tmux session pane.
|
|
127
|
+
*/
|
|
128
|
+
sendKeys(sessionName, keys) {
|
|
129
|
+
try {
|
|
130
|
+
(0, child_process_1.execSync)(`tmux send-keys -t ${shellEscape(sessionName)} ${shellEscape(keys)} Enter`, {
|
|
131
|
+
stdio: 'pipe',
|
|
132
|
+
});
|
|
133
|
+
}
|
|
134
|
+
catch {
|
|
135
|
+
// Session might have ended
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
exports.ProcessService = ProcessService;
|
|
140
|
+
/**
|
|
141
|
+
* Minimal shell escaping: wraps value in single quotes and escapes embedded single quotes.
|
|
142
|
+
* Suitable for passing arguments to tmux commands.
|
|
143
|
+
*/
|
|
144
|
+
function shellEscape(value) {
|
|
145
|
+
return "'" + value.replace(/'/g, "'\\''") + "'";
|
|
146
|
+
}
|
|
147
|
+
//# sourceMappingURL=ProcessService.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ProcessService.js","sourceRoot":"","sources":["../../src/services/ProcessService.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
import { Tag, CreateTagInput, UpdateTagInput } from '../models';
|
|
2
|
-
import {
|
|
2
|
+
import { StorageBackend } from '../db/types/repository';
|
|
3
3
|
/**
|
|
4
4
|
* Tag Service
|
|
5
5
|
* Manages creation, retrieval, update, and deletion of tags
|
|
6
6
|
*/
|
|
7
7
|
export declare class TagService {
|
|
8
|
-
private
|
|
9
|
-
constructor(
|
|
8
|
+
private backend;
|
|
9
|
+
constructor(backend?: StorageBackend);
|
|
10
10
|
/**
|
|
11
11
|
* Create a new tag
|
|
12
12
|
* @param input - Tag creation input
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TagService.d.ts","sourceRoot":"","sources":["../../src/services/TagService.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,cAAc,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAGhE,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"TagService.d.ts","sourceRoot":"","sources":["../../src/services/TagService.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,cAAc,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAGhE,OAAO,EAAE,cAAc,EAAE,MAAM,wBAAwB,CAAC;AAGxD;;;GAGG;AACH,qBAAa,UAAU;IACrB,OAAO,CAAC,OAAO,CAAiB;gBAEpB,OAAO,CAAC,EAAE,cAAc;IAIpC;;;;;OAKG;IACH,SAAS,CAAC,KAAK,EAAE,cAAc,GAAG,GAAG;IAiBrC;;;;OAIG;IACH,MAAM,CAAC,EAAE,EAAE,MAAM,GAAG,GAAG,GAAG,IAAI;IAI9B;;;;OAIG;IACH,YAAY,CAAC,IAAI,EAAE,MAAM,GAAG,GAAG,GAAG,IAAI;IAItC;;;OAGG;IACH,QAAQ,IAAI,GAAG,EAAE;IAIjB;;;;;;OAMG;IACH,SAAS,CAAC,EAAE,EAAE,MAAM,EAAE,KAAK,EAAE,cAAc,GAAG,GAAG,GAAG,IAAI;IA+BxD;;;;OAIG;IACH,SAAS,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO;CAG/B"}
|