@nickmeriano/task 0.4.2 → 0.6.0
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.md +77 -9
- package/dist/cli.js +290 -19
- package/dist/cli.js.map +1 -1
- package/dist/file-store.d.ts +113 -0
- package/dist/file-store.d.ts.map +1 -0
- package/dist/file-store.js +604 -0
- package/dist/file-store.js.map +1 -0
- package/dist/index.d.ts +6 -4
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +3 -1
- package/dist/index.js.map +1 -1
- package/dist/server.d.ts.map +1 -1
- package/dist/server.js +30 -7
- package/dist/server.js.map +1 -1
- package/dist/store.d.ts +69 -16
- package/dist/store.d.ts.map +1 -1
- package/dist/store.js +169 -39
- package/dist/store.js.map +1 -1
- package/dist/store.test.d.ts +12 -0
- package/dist/store.test.d.ts.map +1 -0
- package/dist/store.test.js +252 -0
- package/dist/store.test.js.map +1 -0
- package/dist/ticket-doc.d.ts +57 -0
- package/dist/ticket-doc.d.ts.map +1 -0
- package/dist/ticket-doc.js +197 -0
- package/dist/ticket-doc.js.map +1 -0
- package/dist/types.d.ts +35 -3
- package/dist/types.d.ts.map +1 -1
- package/dist/types.js.map +1 -1
- package/package.json +4 -4
- package/skill/SKILL.md +40 -9
- package/src/cli.ts +304 -22
- package/src/file-store.ts +693 -0
- package/src/index.ts +30 -4
- package/src/server.ts +31 -11
- package/src/store.test.ts +305 -0
- package/src/store.ts +210 -49
- package/src/ticket-doc.ts +226 -0
- package/src/types.ts +35 -3
- package/ui/dist/assets/index-CXW8uT5f.css +1 -0
- package/ui/dist/assets/{index-Dm3ToURf.js → index-oJzomUDL.js} +67 -67
- package/ui/dist/index.html +2 -2
- package/ui/dist/assets/index-DXFbw9bM.css +0 -1
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAEA,OAAO,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAEA,OAAO,EACL,SAAS,EACT,WAAW,EACX,YAAY,EACZ,UAAU,EACV,kBAAkB,EAClB,QAAQ,EACR,aAAa,EACb,KAAK,QAAQ,EACb,KAAK,KAAK,GACX,MAAM,YAAY,CAAA;AACnB,OAAO,EACL,WAAW,EACX,SAAS,EACT,WAAW,EACX,WAAW,EACX,YAAY,EACZ,SAAS,GACV,MAAM,iBAAiB,CAAA;AACxB,OAAO,EACL,WAAW,EACX,eAAe,EACf,YAAY,EACZ,gBAAgB,EAChB,KAAK,SAAS,EACd,KAAK,UAAU,GAChB,MAAM,iBAAiB,CAAA;AACxB,OAAO,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAA;AAC9C,OAAO,EAAE,aAAa,EAAE,SAAS,EAAE,KAAK,MAAM,EAAE,KAAK,YAAY,EAAE,MAAM,aAAa,CAAA;AACtF,cAAc,YAAY,CAAA"}
|
package/dist/index.js
CHANGED
|
@@ -1,6 +1,8 @@
|
|
|
1
1
|
// Programmatic access to the same store the CLI and `task serve` use — for
|
|
2
2
|
// scripts that want to read or write .task/ without shelling out.
|
|
3
|
-
export { TaskStore,
|
|
3
|
+
export { TaskStore, boardConfig, derivePrefix, findBoards, findBoardsByPrefix, findRoot, findScopeRoot, } from "./store.js";
|
|
4
|
+
export { ARCHIVE_DIR, FileStore, TICKETS_DIR, initProject, migrateBoard, openBoard, } from "./file-store.js";
|
|
5
|
+
export { parseTicket, serializeTicket, parseComment, serializeComment, } from "./ticket-doc.js";
|
|
4
6
|
export { createTaskServer } from "./server.js";
|
|
5
7
|
export { resolveAuthor, ANONYMOUS } from "./author.js";
|
|
6
8
|
export * from "./types.js";
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,2EAA2E;AAC3E,kEAAkE;AAClE,OAAO,
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,2EAA2E;AAC3E,kEAAkE;AAClE,OAAO,EACL,SAAS,EACT,WAAW,EACX,YAAY,EACZ,UAAU,EACV,kBAAkB,EAClB,QAAQ,EACR,aAAa,GAGd,MAAM,YAAY,CAAA;AACnB,OAAO,EACL,WAAW,EACX,SAAS,EACT,WAAW,EACX,WAAW,EACX,YAAY,EACZ,SAAS,GACV,MAAM,iBAAiB,CAAA;AACxB,OAAO,EACL,WAAW,EACX,eAAe,EACf,YAAY,EACZ,gBAAgB,GAGjB,MAAM,iBAAiB,CAAA;AACxB,OAAO,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAA;AAC9C,OAAO,EAAE,aAAa,EAAE,SAAS,EAAkC,MAAM,aAAa,CAAA;AACtF,cAAc,YAAY,CAAA"}
|
package/dist/server.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA,OAAO,EAAsC,KAAK,MAAM,EAAuB,MAAM,WAAW,CAAA;
|
|
1
|
+
{"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA,OAAO,EAAsC,KAAK,MAAM,EAAuB,MAAM,WAAW,CAAA;AAuEhG;;;;;;;;;;GAUG;AACH,wBAAgB,gBAAgB,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,CAwP1D"}
|
package/dist/server.js
CHANGED
|
@@ -3,7 +3,8 @@ import { watch, existsSync, readFileSync, statSync } from "node:fs";
|
|
|
3
3
|
import { extname, join, normalize } from "node:path";
|
|
4
4
|
import { fileURLToPath } from "node:url";
|
|
5
5
|
import { resolveAuthor } from "./author.js";
|
|
6
|
-
import {
|
|
6
|
+
import { openBoard } from "./file-store.js";
|
|
7
|
+
import { findBoards } from "./store.js";
|
|
7
8
|
import { STATUSES, isStatus } from "./types.js";
|
|
8
9
|
/** The prebuilt SPA, shipped inside the package next to dist/. */
|
|
9
10
|
const UI_DIR = fileURLToPath(new URL("../ui/dist", import.meta.url));
|
|
@@ -50,10 +51,29 @@ function parsePatch(body) {
|
|
|
50
51
|
}
|
|
51
52
|
if (typeof body.needsHuman === "boolean")
|
|
52
53
|
patch.needsHuman = body.needsHuman;
|
|
54
|
+
if (Array.isArray(body.blocks))
|
|
55
|
+
patch.blocks = body.blocks.map(taskNumber);
|
|
56
|
+
if (Array.isArray(body.blockedBy))
|
|
57
|
+
patch.blockedBy = body.blockedBy.map(taskNumber);
|
|
58
|
+
if (Array.isArray(body.prs)) {
|
|
59
|
+
patch.prs = body.prs.map((pr) => {
|
|
60
|
+
const url = String(pr).trim();
|
|
61
|
+
// Anything the UI would render as a clickable link has to be a link.
|
|
62
|
+
if (!/^https?:\/\//.test(url))
|
|
63
|
+
throw new Error(`not a PR url: ${url}`);
|
|
64
|
+
return url;
|
|
65
|
+
});
|
|
66
|
+
}
|
|
53
67
|
if (typeof body.position === "number")
|
|
54
68
|
patch.position = body.position;
|
|
55
69
|
return patch;
|
|
56
70
|
}
|
|
71
|
+
function taskNumber(value) {
|
|
72
|
+
const n = Number(value);
|
|
73
|
+
if (!Number.isInteger(n) || n <= 0)
|
|
74
|
+
throw new Error(`invalid task number: ${String(value)}`);
|
|
75
|
+
return n;
|
|
76
|
+
}
|
|
57
77
|
/**
|
|
58
78
|
* `task serve` — one plain node:http server for the static UI, the JSON API,
|
|
59
79
|
* and an SSE stream that pings whenever anything writes to a `.task/` (the UI
|
|
@@ -91,9 +111,12 @@ export function createTaskServer(serveRoot) {
|
|
|
91
111
|
};
|
|
92
112
|
const boards = new Map();
|
|
93
113
|
let ordered = [];
|
|
94
|
-
const
|
|
95
|
-
const store =
|
|
96
|
-
|
|
114
|
+
const attachBoard = (ref) => {
|
|
115
|
+
const store = openBoard(ref.root);
|
|
116
|
+
// Recursive: text-canonical state is a tree (tickets/<n>/comments/…), and
|
|
117
|
+
// a write anywhere in it is a board change. Node supports this on Linux,
|
|
118
|
+
// macOS and Windows for the versions this package requires.
|
|
119
|
+
const watcher = watch(store.taskDir, { recursive: true }, () => noteChange(ref.id));
|
|
97
120
|
// A deleted board dir can make fs.watch emit; the next rescan cleans up.
|
|
98
121
|
watcher.on("error", () => { });
|
|
99
122
|
boards.set(ref.id, { store, watcher });
|
|
@@ -111,7 +134,7 @@ export function createTaskServer(serveRoot) {
|
|
|
111
134
|
}
|
|
112
135
|
for (const ref of found)
|
|
113
136
|
if (!boards.has(ref.id))
|
|
114
|
-
|
|
137
|
+
attachBoard(ref);
|
|
115
138
|
ordered = found.map((ref) => ref.id);
|
|
116
139
|
return found;
|
|
117
140
|
};
|
|
@@ -209,11 +232,11 @@ export function createTaskServer(serveRoot) {
|
|
|
209
232
|
.catch((error) => json(res, 400, { error: error.message }));
|
|
210
233
|
return;
|
|
211
234
|
}
|
|
212
|
-
const taskMatch = /^\/api\/tasks\/([^/]+)(\/comments(?:\/(
|
|
235
|
+
const taskMatch = /^\/api\/tasks\/([^/]+)(\/comments(?:\/([^/]+))?)?$/.exec(path);
|
|
213
236
|
if (taskMatch) {
|
|
214
237
|
const number = store.parseId(decodeURIComponent(taskMatch[1]));
|
|
215
238
|
if (taskMatch[3] && req.method === "DELETE") {
|
|
216
|
-
const commentId =
|
|
239
|
+
const commentId = decodeURIComponent(taskMatch[3]);
|
|
217
240
|
const existing = store.comments(number).find((c) => c.id === commentId);
|
|
218
241
|
if (!existing) {
|
|
219
242
|
json(res, 404, { error: `no such comment: ${commentId}` });
|
package/dist/server.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAA0D,MAAM,WAAW,CAAA;AAChG,OAAO,EAAE,KAAK,EAAE,UAAU,EAAE,YAAY,EAAE,QAAQ,EAAkB,MAAM,SAAS,CAAA;AACnF,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,SAAS,EAAE,MAAM,WAAW,CAAA;AACpD,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAA;AACxC,OAAO,EAAE,aAAa,EAAE,MAAM,aAAa,CAAA;AAC3C,OAAO,EAAE,SAAS,EAAE,MAAM,iBAAiB,CAAA;AAC3C,OAAO,EAAE,UAAU,EAA6B,MAAM,YAAY,CAAA;AAClE,OAAO,EAAE,QAAQ,EAAE,QAAQ,EAAkB,MAAM,YAAY,CAAA;AAE/D,kEAAkE;AAClE,MAAM,MAAM,GAAG,aAAa,CAAC,IAAI,GAAG,CAAC,YAAY,EAAE,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAA;AAEpE,MAAM,IAAI,GAA2B;IACnC,OAAO,EAAE,0BAA0B;IACnC,KAAK,EAAE,iBAAiB;IACxB,MAAM,EAAE,UAAU;IAClB,MAAM,EAAE,eAAe;IACvB,OAAO,EAAE,kBAAkB;IAC3B,MAAM,EAAE,WAAW;IACnB,MAAM,EAAE,cAAc;IACtB,QAAQ,EAAE,YAAY;IACtB,MAAM,EAAE,kBAAkB;CAC3B,CAAA;AAED,SAAS,IAAI,CAAC,GAAmB,EAAE,MAAc,EAAE,IAAa;IAC9D,MAAM,IAAI,GAAG,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,CAAA;IACjC,GAAG,CAAC,SAAS,CAAC,MAAM,EAAE,EAAE,cAAc,EAAE,kBAAkB,EAAE,CAAC,CAAA;IAC7D,GAAG,CAAC,GAAG,CAAC,IAAI,CAAC,CAAA;AACf,CAAC;AAED,KAAK,UAAU,QAAQ,CAAC,GAAoB;IAC1C,MAAM,MAAM,GAAa,EAAE,CAAA;IAC3B,IAAI,KAAK,EAAE,MAAM,KAAK,IAAI,GAAG;QAAE,MAAM,CAAC,IAAI,CAAC,KAAe,CAAC,CAAA;IAC3D,MAAM,IAAI,GAAG,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAA;IACnD,IAAI,CAAC,IAAI;QAAE,OAAO,EAAE,CAAA;IACpB,OAAO,IAAI,CAAC,KAAK,CAAC,IAAI,CAA4B,CAAA;AACpD,CAAC;AAED,SAAS,UAAU,CAAC,IAA6B;IAC/C,MAAM,KAAK,GAAc,EAAE,CAAA;IAC3B,IAAI,OAAO,IAAI,CAAC,KAAK,KAAK,QAAQ;QAAE,KAAK,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,CAAA;IAC5D,IAAI,OAAO,IAAI,CAAC,WAAW,KAAK,QAAQ;QAAE,KAAK,CAAC,WAAW,GAAG,IAAI,CAAC,WAAW,CAAA;IAC9E,IAAI,OAAO,IAAI,CAAC,MAAM,KAAK,QAAQ,EAAE,CAAC;QACpC,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,MAAM,CAAC;YAAE,MAAM,IAAI,KAAK,CAAC,mBAAmB,IAAI,CAAC,MAAM,EAAE,CAAC,CAAA;QAC7E,KAAK,CAAC,MAAM,GAAG,IAAI,CAAC,MAAM,CAAA;IAC5B,CAAC;IACD,IAAI,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC;QAAE,KAAK,CAAC,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,MAAM,CAAC,CAAA;IAChE,IAAI,OAAO,IAAI,CAAC,SAAS,KAAK,QAAQ,IAAI,IAAI,CAAC,SAAS,KAAK,IAAI,EAAE,CAAC;QAClE,KAAK,CAAC,SAAS,GAAG,IAAI,CAAC,SAAS,KAAK,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,SAAS,CAAA;IACjE,CAAC;IACD,IAAI,OAAO,IAAI,CAAC,UAAU,KAAK,SAAS;QAAE,KAAK,CAAC,UAAU,GAAG,IAAI,CAAC,UAAU,CAAA;IAC5E,IAAI,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,MAAM,CAAC;QAAE,KAAK,CAAC,MAAM,GAAG,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,UAAU,CAAC,CAAA;IAC1E,IAAI,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,SAAS,CAAC;QAAE,KAAK,CAAC,SAAS,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,UAAU,CAAC,CAAA;IACnF,IAAI,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC;QAC5B,KAAK,CAAC,GAAG,GAAG,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,EAAE;YAC9B,MAAM,GAAG,GAAG,MAAM,CAAC,EAAE,CAAC,CAAC,IAAI,EAAE,CAAA;YAC7B,qEAAqE;YACrE,IAAI,CAAC,cAAc,CAAC,IAAI,CAAC,GAAG,CAAC;gBAAE,MAAM,IAAI,KAAK,CAAC,iBAAiB,GAAG,EAAE,CAAC,CAAA;YACtE,OAAO,GAAG,CAAA;QACZ,CAAC,CAAC,CAAA;IACJ,CAAC;IACD,IAAI,OAAO,IAAI,CAAC,QAAQ,KAAK,QAAQ;QAAE,KAAK,CAAC,QAAQ,GAAG,IAAI,CAAC,QAAQ,CAAA;IACrE,OAAO,KAAK,CAAA;AACd,CAAC;AAED,SAAS,UAAU,CAAC,KAAc;IAChC,MAAM,CAAC,GAAG,MAAM,CAAC,KAAK,CAAC,CAAA;IACvB,IAAI,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC;QAAE,MAAM,IAAI,KAAK,CAAC,wBAAwB,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC,CAAA;IAC5F,OAAO,CAAC,CAAA;AACV,CAAC;AAED;;;;;;;;;;GAUG;AACH,MAAM,UAAU,gBAAgB,CAAC,SAAiB;IAChD,MAAM,OAAO,GAAG,IAAI,GAAG,EAAkB,CAAA;IAEzC,2EAA2E;IAC3E,2EAA2E;IAC3E,wEAAwE;IACxE,oDAAoD;IACpD,MAAM,MAAM,GAAG,aAAa,CAAC,SAAS,EAAE,SAAS,CAAC,CAAC,IAAI,CAAA;IAEvD,MAAM,OAAO,GAAG,IAAI,GAAG,EAAU,CAAA;IACjC,IAAI,OAAO,GAA0B,IAAI,CAAA;IACzC,MAAM,UAAU,GAAG,CAAC,EAAU,EAAE,EAAE;QAChC,OAAO,CAAC,GAAG,CAAC,EAAE,CAAC,CAAA;QACf,IAAI,OAAO;YAAE,OAAM;QACnB,OAAO,GAAG,UAAU,CAAC,GAAG,EAAE;YACxB,OAAO,GAAG,IAAI,CAAA;YACd,MAAM,GAAG,GAAG,CAAC,GAAG,OAAO,CAAC,CAAA;YACxB,OAAO,CAAC,KAAK,EAAE,CAAA;YACf,KAAK,MAAM,EAAE,IAAI,GAAG,EAAE,CAAC;gBACrB,MAAM,OAAO,GAAG,SAAS,IAAI,CAAC,SAAS,CAAC,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,EAAE,EAAE,CAAC,MAAM,CAAA;gBAC5E,KAAK,MAAM,MAAM,IAAI,OAAO;oBAAE,MAAM,CAAC,KAAK,CAAC,OAAO,CAAC,CAAA;YACrD,CAAC;QACH,CAAC,EAAE,EAAE,CAAC,CAAA;IACR,CAAC,CAAA;IAMD,MAAM,MAAM,GAAG,IAAI,GAAG,EAAiB,CAAA;IACvC,IAAI,OAAO,GAAa,EAAE,CAAA;IAE1B,MAAM,WAAW,GAAG,CAAC,GAAa,EAAQ,EAAE;QAC1C,MAAM,KAAK,GAAG,SAAS,CAAC,GAAG,CAAC,IAAI,CAAC,CAAA;QACjC,0EAA0E;QAC1E,yEAAyE;QACzE,4DAA4D;QAC5D,MAAM,OAAO,GAAG,KAAK,CAAC,KAAK,CAAC,OAAO,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,EAAE,GAAG,EAAE,CAAC,UAAU,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,CAAA;QACnF,yEAAyE;QACzE,OAAO,CAAC,EAAE,CAAC,OAAO,EAAE,GAAG,EAAE,GAAE,CAAC,CAAC,CAAA;QAC7B,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE,EAAE,EAAE,KAAK,EAAE,OAAO,EAAE,CAAC,CAAA;IACxC,CAAC,CAAA;IAED,kFAAkF;IAClF,MAAM,UAAU,GAAG,GAAe,EAAE;QAClC,MAAM,KAAK,GAAG,UAAU,CAAC,SAAS,CAAC,CAAA;QACnC,MAAM,GAAG,GAAG,IAAI,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,CAAA;QAC/C,KAAK,MAAM,CAAC,EAAE,EAAE,KAAK,CAAC,IAAI,MAAM,EAAE,CAAC;YACjC,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE,CAAC,EAAE,CAAC;gBACjB,KAAK,CAAC,OAAO,CAAC,KAAK,EAAE,CAAA;gBACrB,KAAK,CAAC,KAAK,CAAC,KAAK,EAAE,CAAA;gBACnB,MAAM,CAAC,MAAM,CAAC,EAAE,CAAC,CAAA;YACnB,CAAC;QACH,CAAC;QACD,KAAK,MAAM,GAAG,IAAI,KAAK;YAAE,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE,CAAC;gBAAE,WAAW,CAAC,GAAG,CAAC,CAAA;QAClE,OAAO,GAAG,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,GAAG,CAAC,EAAE,CAAC,CAAA;QACpC,OAAO,KAAK,CAAA;IACd,CAAC,CAAA;IAED,UAAU,EAAE,CAAA;IACZ,IAAI,MAAM,CAAC,IAAI,KAAK,CAAC,EAAE,CAAC;QACtB,MAAM,IAAI,KAAK,CAAC,wCAAwC,SAAS,4BAA4B,CAAC,CAAA;IAChG,CAAC;IAED,MAAM,SAAS,GAAG,WAAW,CAAC,GAAG,EAAE;QACjC,KAAK,MAAM,MAAM,IAAI,OAAO;YAAE,MAAM,CAAC,KAAK,CAAC,YAAY,CAAC,CAAA;IAC1D,CAAC,EAAE,MAAM,CAAC,CAAA;IAEV,MAAM,MAAM,GAAG,YAAY,CAAC,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE;QACvC,IAAI,CAAC;YACH,KAAK,CAAC,GAAG,EAAE,GAAG,CAAC,CAAA;QACjB,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC,CAAA;QACnF,CAAC;IACH,CAAC,CAAC,CAAA;IAEF,MAAM,CAAC,EAAE,CAAC,OAAO,EAAE,GAAG,EAAE;QACtB,IAAI,OAAO;YAAE,YAAY,CAAC,OAAO,CAAC,CAAA;QAClC,aAAa,CAAC,SAAS,CAAC,CAAA;QACxB,KAAK,MAAM,KAAK,IAAI,MAAM,CAAC,MAAM,EAAE,EAAE,CAAC;YACpC,KAAK,CAAC,OAAO,CAAC,KAAK,EAAE,CAAA;YACrB,KAAK,CAAC,KAAK,CAAC,KAAK,EAAE,CAAA;QACrB,CAAC;QACD,KAAK,MAAM,MAAM,IAAI,OAAO;YAAE,MAAM,CAAC,GAAG,EAAE,CAAA;IAC5C,CAAC,CAAC,CAAA;IAEF,SAAS,KAAK,CAAC,GAAoB,EAAE,GAAmB;QACtD,MAAM,GAAG,GAAG,IAAI,GAAG,CAAC,GAAG,CAAC,GAAG,IAAI,GAAG,EAAE,kBAAkB,CAAC,CAAA;QACvD,MAAM,IAAI,GAAG,GAAG,CAAC,QAAQ,CAAA;QAEzB,IAAI,IAAI,KAAK,aAAa,EAAE,CAAC;YAC3B,GAAG,CAAC,SAAS,CAAC,GAAG,EAAE;gBACjB,cAAc,EAAE,mBAAmB;gBACnC,eAAe,EAAE,UAAU;gBAC3B,UAAU,EAAE,YAAY;aACzB,CAAC,CAAA;YACF,GAAG,CAAC,KAAK,CAAC,iBAAiB,CAAC,CAAA;YAC5B,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC,CAAA;YAChB,GAAG,CAAC,EAAE,CAAC,OAAO,EAAE,GAAG,EAAE,CAAC,OAAO,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,CAAA;YAC1C,OAAM;QACR,CAAC;QAED,IAAI,IAAI,KAAK,aAAa,EAAE,CAAC;YAC3B,MAAM,KAAK,GAAG,UAAU,EAAE,CAAA;YAC1B,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE;gBACb,MAAM,EAAE,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE;oBACxB,MAAM,EAAE,MAAM,EAAE,GAAG,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE,CAAE,CAAC,KAAK,CAAA;oBAC5C,OAAO,EAAE,EAAE,EAAE,GAAG,CAAC,EAAE,EAAE,IAAI,EAAE,MAAM,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,CAAA;gBACjE,CAAC,CAAC;aACH,CAAC,CAAA;YACF,OAAM;QACR,CAAC;QAED,IAAI,IAAI,CAAC,UAAU,CAAC,OAAO,CAAC,EAAE,CAAC;YAC7B,MAAM,EAAE,GAAG,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,OAAO,CAAC,IAAI,OAAO,CAAC,CAAC,CAAC,CAAA;YACtD,MAAM,KAAK,GAAG,MAAM,CAAC,GAAG,CAAC,EAAE,CAAC,CAAA;YAC5B,IAAI,CAAC,KAAK,EAAE,CAAC;gBACX,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,kBAAkB,EAAE,EAAE,EAAE,CAAC,CAAA;gBACjD,OAAM;YACR,CAAC;YACD,QAAQ,CAAC,KAAK,CAAC,KAAK,EAAE,GAAG,EAAE,GAAG,EAAE,IAAI,CAAC,CAAA;YACrC,OAAM;QACR,CAAC;QAED,WAAW,CAAC,IAAI,EAAE,GAAG,CAAC,CAAA;IACxB,CAAC;IAED,SAAS,QAAQ,CACf,KAAY,EACZ,GAAoB,EACpB,GAAmB,EACnB,IAAY;QAEZ,IAAI,IAAI,KAAK,cAAc,EAAE,CAAC;YAC5B,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE;gBACb,IAAI,EAAE,KAAK,CAAC,MAAM,CAAC,IAAI;gBACvB,MAAM,EAAE,KAAK,CAAC,MAAM,CAAC,MAAM;gBAC3B,QAAQ,EAAE,QAAQ;gBAClB,MAAM;aACP,CAAC,CAAA;YACF,OAAM;QACR,CAAC;QAED,IAAI,IAAI,KAAK,YAAY,IAAI,GAAG,CAAC,MAAM,KAAK,KAAK,EAAE,CAAC;YAClD,MAAM,MAAM,GAAG,KAAK,CAAC,aAAa,EAAE,CAAA;YACpC,MAAM,KAAK,GAAG,KAAK;iBAChB,IAAI,EAAE;iBACN,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,GAAG,CAAC,EAAE,YAAY,EAAE,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAA;YAClE,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,CAAC,CAAA;YACzB,OAAM;QACR,CAAC;QAED,IAAI,IAAI,KAAK,YAAY,IAAI,GAAG,CAAC,MAAM,KAAK,MAAM,EAAE,CAAC;YACnD,KAAK,QAAQ,CAAC,GAAG,CAAC;iBACf,IAAI,CAAC,CAAC,IAAI,EAAE,EAAE;gBACb,IAAI,OAAO,IAAI,CAAC,KAAK,KAAK,QAAQ,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,EAAE,EAAE,CAAC;oBACzD,MAAM,IAAI,KAAK,CAAC,mBAAmB,CAAC,CAAA;gBACtC,CAAC;gBACD,MAAM,KAAK,GAAG,UAAU,CAAC,IAAI,CAAC,CAAA;gBAC9B,MAAM,IAAI,GAAG,KAAK,CAAC,MAAM,CAAC,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,CAAC,IAAI,EAAE,EAAE,GAAG,KAAK,EAAE,CAAC,CAAA;gBACjE,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,IAAI,EAAE,CAAC,CAAA;YAC1B,CAAC,CAAC;iBACD,KAAK,CAAC,CAAC,KAAY,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC,CAAA;YACpE,OAAM;QACR,CAAC;QAED,MAAM,SAAS,GAAG,oDAAoD,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA;QACjF,IAAI,SAAS,EAAE,CAAC;YACd,MAAM,MAAM,GAAG,KAAK,CAAC,OAAO,CAAC,kBAAkB,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC,CAAA;YAC9D,IAAI,SAAS,CAAC,CAAC,CAAC,IAAI,GAAG,CAAC,MAAM,KAAK,QAAQ,EAAE,CAAC;gBAC5C,MAAM,SAAS,GAAG,kBAAkB,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAA;gBAClD,MAAM,QAAQ,GAAG,KAAK,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,KAAK,SAAS,CAAC,CAAA;gBACvE,IAAI,CAAC,QAAQ,EAAE,CAAC;oBACd,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,oBAAoB,SAAS,EAAE,EAAE,CAAC,CAAA;oBAC1D,OAAM;gBACR,CAAC;gBACD,qEAAqE;gBACrE,uEAAuE;gBACvE,IAAI,QAAQ,CAAC,MAAM,KAAK,MAAM,EAAE,CAAC;oBAC/B,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,uCAAuC,EAAE,CAAC,CAAA;oBAClE,OAAM;gBACR,CAAC;gBACD,KAAK,CAAC,aAAa,CAAC,MAAM,EAAE,SAAS,CAAC,CAAA;gBACtC,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,EAAE,EAAE,IAAI,EAAE,CAAC,CAAA;gBAC5B,OAAM;YACR,CAAC;YACD,IAAI,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,IAAI,GAAG,CAAC,MAAM,KAAK,MAAM,EAAE,CAAC;gBAC3D,KAAK,QAAQ,CAAC,GAAG,CAAC;qBACf,IAAI,CAAC,CAAC,IAAI,EAAE,EAAE;oBACb,IAAI,OAAO,IAAI,CAAC,IAAI,KAAK,QAAQ,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,EAAE,CAAC;wBACvD,MAAM,IAAI,KAAK,CAAC,kBAAkB,CAAC,CAAA;oBACrC,CAAC;oBACD,+DAA+D;oBAC/D,MAAM,OAAO,GAAG,KAAK,CAAC,UAAU,CAAC,MAAM,EAAE,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,EAAE,MAAM,CAAC,CAAA;oBAClE,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,OAAO,EAAE,CAAC,CAAA;gBAC7B,CAAC,CAAC;qBACD,KAAK,CAAC,CAAC,KAAY,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC,CAAA;gBACpE,OAAM;YACR,CAAC;YACD,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC;gBAClB,IAAI,GAAG,CAAC,MAAM,KAAK,KAAK,EAAE,CAAC;oBACzB,MAAM,IAAI,GAAG,KAAK,CAAC,GAAG,CAAC,MAAM,CAAC,CAAA;oBAC9B,IAAI,CAAC,IAAI,EAAE,CAAC;wBACV,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,iBAAiB,KAAK,CAAC,SAAS,CAAC,MAAM,CAAC,EAAE,EAAE,CAAC,CAAA;wBACrE,OAAM;oBACR,CAAC;oBACD,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,CAAC,QAAQ,CAAC,MAAM,CAAC,EAAE,CAAC,CAAA;oBAC1D,OAAM;gBACR,CAAC;gBACD,IAAI,GAAG,CAAC,MAAM,KAAK,OAAO,EAAE,CAAC;oBAC3B,KAAK,QAAQ,CAAC,GAAG,CAAC;yBACf,IAAI,CAAC,CAAC,IAAI,EAAE,EAAE;wBACb,MAAM,IAAI,GAAG,KAAK,CAAC,MAAM,CAAC,MAAM,EAAE,UAAU,CAAC,IAAI,CAAC,CAAC,CAAA;wBACnD,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,IAAI,EAAE,CAAC,CAAA;oBAC1B,CAAC,CAAC;yBACD,KAAK,CAAC,CAAC,KAAY,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC,CAAA;oBACpE,OAAM;gBACR,CAAC;gBACD,IAAI,GAAG,CAAC,MAAM,KAAK,QAAQ,EAAE,CAAC;oBAC5B,KAAK,CAAC,MAAM,CAAC,MAAM,CAAC,CAAA;oBACpB,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,EAAE,EAAE,IAAI,EAAE,CAAC,CAAA;oBAC5B,OAAM;gBACR,CAAC;YACH,CAAC;QACH,CAAC;QAED,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,KAAK,EAAE,WAAW,EAAE,CAAC,CAAA;IACxC,CAAC;IAED,SAAS,WAAW,CAAC,IAAY,EAAE,GAAmB;QACpD,MAAM,IAAI,GAAG,SAAS,CAAC,IAAI,CAAC,CAAC,OAAO,CAAC,eAAe,EAAE,EAAE,CAAC,CAAA;QACzD,IAAI,IAAI,GAAG,IAAI,CAAC,MAAM,EAAE,IAAI,CAAC,CAAA;QAC7B,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,QAAQ,CAAC,IAAI,CAAC,CAAC,WAAW,EAAE,EAAE,CAAC;YACtD,IAAI,GAAG,IAAI,CAAC,MAAM,EAAE,YAAY,CAAC,CAAA,CAAC,eAAe;QACnD,CAAC;QACD,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC,EAAE,CAAC;YACtB,GAAG,CAAC,SAAS,CAAC,GAAG,EAAE,EAAE,cAAc,EAAE,YAAY,EAAE,CAAC,CAAA;YACpD,GAAG,CAAC,GAAG,CAAC,6DAA6D,CAAC,CAAA;YACtE,OAAM;QACR,CAAC;QACD,GAAG,CAAC,SAAS,CAAC,GAAG,EAAE;YACjB,cAAc,EAAE,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,IAAI,0BAA0B;YACjE,eAAe,EAAE,UAAU;SAC5B,CAAC,CAAA;QACF,GAAG,CAAC,GAAG,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC,CAAA;IAC7B,CAAC;IAED,OAAO,MAAM,CAAA;AACf,CAAC"}
|
package/dist/store.d.ts
CHANGED
|
@@ -1,7 +1,37 @@
|
|
|
1
|
-
import type { Comment, ProjectConfig, Task, TaskFilter, TaskInput, TaskPatch } from "./types.
|
|
1
|
+
import type { Comment, ProjectConfig, Task, TaskFilter, TaskInput, TaskPatch } from "./types.ts";
|
|
2
2
|
export declare const TASK_DIR = ".task";
|
|
3
3
|
export declare const DB_FILE = "tasks.db";
|
|
4
4
|
export declare const CONFIG_FILE = "config.json";
|
|
5
|
+
/** Spacing between adjacent board positions — leaves room to drop between. */
|
|
6
|
+
export declare const POSITION_GAP = 1024;
|
|
7
|
+
/**
|
|
8
|
+
* What a board's persistence layer looks like, whichever representation backs
|
|
9
|
+
* it. Two implementations: `FileStore` (text files in `.task/tickets/`, the
|
|
10
|
+
* canonical format) and the legacy `TaskStore` (a committed SQLite database),
|
|
11
|
+
* which survives so un-migrated boards keep working. `openBoard` picks.
|
|
12
|
+
*/
|
|
13
|
+
export interface Store {
|
|
14
|
+
readonly root: string;
|
|
15
|
+
readonly taskDir: string;
|
|
16
|
+
readonly config: ProjectConfig;
|
|
17
|
+
close(): void;
|
|
18
|
+
displayId(number: number): string;
|
|
19
|
+
parseId(ref: string): number;
|
|
20
|
+
list(filter?: TaskFilter): Task[];
|
|
21
|
+
get(number: number): Task | null;
|
|
22
|
+
create(input: TaskInput): Task;
|
|
23
|
+
update(number: number, patch: TaskPatch): Task;
|
|
24
|
+
link(number: number, relation: "blocks" | "blocked_by", target: number): Task;
|
|
25
|
+
unlink(number: number, relation: "blocks" | "blocked_by", target: number): Task;
|
|
26
|
+
delete(number: number): void;
|
|
27
|
+
/** Move a done/canceled ticket to `.task/archive/`, out of the board's hot path. */
|
|
28
|
+
archive(number: number): Task;
|
|
29
|
+
unarchive(number: number): Task;
|
|
30
|
+
comments(number: number): Comment[];
|
|
31
|
+
addComment(number: number, body: string, author?: string): Comment;
|
|
32
|
+
deleteComment(number: number, commentId: string): Comment;
|
|
33
|
+
commentCounts(): Map<number, number>;
|
|
34
|
+
}
|
|
5
35
|
/**
|
|
6
36
|
* Walk up from `from` looking for a `.task/config.json`, the way git finds its
|
|
7
37
|
* `.git`. Returns the directory that *contains* `.task`, or null.
|
|
@@ -13,6 +43,22 @@ export interface BoardRef {
|
|
|
13
43
|
/** Absolute directory containing `.task/`. */
|
|
14
44
|
root: string;
|
|
15
45
|
}
|
|
46
|
+
/**
|
|
47
|
+
* The widest board scope `from` belongs to: the *outermost* ancestor holding a
|
|
48
|
+
* `.task/` (a monorepo's root board), or `from` itself when no ancestor has
|
|
49
|
+
* one. Where `findRoot` answers "which board am I on", this answers "which
|
|
50
|
+
* repo of boards am I in" — the anchor for anything cross-board: prefix
|
|
51
|
+
* routing and `task boards`.
|
|
52
|
+
*/
|
|
53
|
+
export declare function findScopeRoot(from: string): string;
|
|
54
|
+
/** A board's config, read without opening a store. Throws on a broken file. */
|
|
55
|
+
export declare function boardConfig(root: string): ProjectConfig;
|
|
56
|
+
/**
|
|
57
|
+
* Every board in scope whose prefix is `prefix` (case-insensitive). Normally
|
|
58
|
+
* zero or one — two boards sharing a prefix is a repo mistake this surfaces
|
|
59
|
+
* rather than resolves. Boards with unreadable configs can't match.
|
|
60
|
+
*/
|
|
61
|
+
export declare function findBoardsByPrefix(scopeRoot: string, prefix: string): BoardRef[];
|
|
16
62
|
/**
|
|
17
63
|
* The multi-board complement of `findRoot`: walk *down* from `serveRoot`
|
|
18
64
|
* collecting every directory that holds a `.task/config.json`, so one
|
|
@@ -21,14 +67,15 @@ export interface BoardRef {
|
|
|
21
67
|
* dependency/build dirs and symlinks are skipped; unreadable dirs are ignored.
|
|
22
68
|
*/
|
|
23
69
|
export declare function findBoards(serveRoot: string, maxDepth?: number): BoardRef[];
|
|
24
|
-
/** Derive an id prefix from a project name: "phone agent" → "
|
|
70
|
+
/** Derive an id prefix from a project name: "phone agent" → "PHO". */
|
|
25
71
|
export declare function derivePrefix(name: string): string;
|
|
26
72
|
/**
|
|
27
|
-
* The
|
|
73
|
+
* The legacy persistence layer: one SQLite database inside `.task/`, opened
|
|
28
74
|
* synchronously via node:sqlite (built into Node ≥22.13 — zero dependencies,
|
|
29
|
-
* nothing to compile, safe for `npx`).
|
|
75
|
+
* nothing to compile, safe for `npx`). Boards created before the text format
|
|
76
|
+
* still run on this until `task migrate` moves them over.
|
|
30
77
|
*/
|
|
31
|
-
export declare class TaskStore {
|
|
78
|
+
export declare class TaskStore implements Store {
|
|
32
79
|
readonly root: string;
|
|
33
80
|
readonly taskDir: string;
|
|
34
81
|
readonly config: ProjectConfig;
|
|
@@ -39,25 +86,31 @@ export declare class TaskStore {
|
|
|
39
86
|
/** Accepts "PHONE-12", "phone-12" or "12". */
|
|
40
87
|
parseId(ref: string): number;
|
|
41
88
|
private toTask;
|
|
89
|
+
/** The other end of every link where `column` is this task. */
|
|
90
|
+
private linkedNumbers;
|
|
42
91
|
private toComment;
|
|
43
92
|
list(filter?: TaskFilter): Task[];
|
|
44
93
|
get(number: number): Task | null;
|
|
45
94
|
create(input: TaskInput): Task;
|
|
46
95
|
update(number: number, patch: TaskPatch): Task;
|
|
96
|
+
/**
|
|
97
|
+
* Make the link table agree with `targets` for one side of one task —
|
|
98
|
+
* `blocker_id` when setting what `number` blocks, `blocked_id` when setting
|
|
99
|
+
* what blocks it. The other task's view is the same row read from the other
|
|
100
|
+
* end, so there is no second write to keep consistent. Every task touched
|
|
101
|
+
* (both ends of every added or removed link) gets its `updated_at` bumped.
|
|
102
|
+
*/
|
|
103
|
+
private reconcileLinks;
|
|
104
|
+
/** `task link A --blocks B` and friends — additive, unlike the patch form. */
|
|
105
|
+
link(number: number, relation: "blocks" | "blocked_by", target: number): Task;
|
|
106
|
+
unlink(number: number, relation: "blocks" | "blocked_by", target: number): Task;
|
|
47
107
|
delete(number: number): void;
|
|
108
|
+
/** The archive is a text-format feature — a directory move, not a table. */
|
|
109
|
+
archive(_number: number): Task;
|
|
110
|
+
unarchive(_number: number): Task;
|
|
48
111
|
comments(number: number): Comment[];
|
|
49
112
|
addComment(number: number, body: string, author?: string): Comment;
|
|
50
|
-
deleteComment(number: number, commentId:
|
|
113
|
+
deleteComment(number: number, commentId: string): Comment;
|
|
51
114
|
commentCounts(): Map<number, number>;
|
|
52
115
|
}
|
|
53
|
-
export interface InitOptions {
|
|
54
|
-
name: string;
|
|
55
|
-
prefix?: string;
|
|
56
|
-
}
|
|
57
|
-
/**
|
|
58
|
-
* Create `.task/` in `root`: config, an empty database, and a .gitignore for
|
|
59
|
-
* SQLite's transient sidecar files (the database itself is meant to be
|
|
60
|
-
* committed — that's the point).
|
|
61
|
-
*/
|
|
62
|
-
export declare function initProject(root: string, options: InitOptions): TaskStore;
|
|
63
116
|
//# sourceMappingURL=store.d.ts.map
|
package/dist/store.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"store.d.ts","sourceRoot":"","sources":["../src/store.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EACV,OAAO,EACP,aAAa,EAEb,IAAI,EACJ,UAAU,EACV,SAAS,EACT,SAAS,EACV,MAAM,YAAY,CAAA;AAEnB,eAAO,MAAM,QAAQ,UAAU,CAAA;AAC/B,eAAO,MAAM,OAAO,aAAa,CAAA;AACjC,eAAO,MAAM,WAAW,gBAAgB,CAAA;
|
|
1
|
+
{"version":3,"file":"store.d.ts","sourceRoot":"","sources":["../src/store.ts"],"names":[],"mappings":"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"}
|
package/dist/store.js
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
import { DatabaseSync } from "node:sqlite";
|
|
2
|
-
import { existsSync,
|
|
2
|
+
import { existsSync, readdirSync, readFileSync } from "node:fs";
|
|
3
3
|
import { dirname, join, relative, sep } from "node:path";
|
|
4
4
|
export const TASK_DIR = ".task";
|
|
5
5
|
export const DB_FILE = "tasks.db";
|
|
6
6
|
export const CONFIG_FILE = "config.json";
|
|
7
7
|
/** Spacing between adjacent board positions — leaves room to drop between. */
|
|
8
|
-
const POSITION_GAP = 1024;
|
|
8
|
+
export const POSITION_GAP = 1024;
|
|
9
9
|
/**
|
|
10
10
|
* Walk up from `from` looking for a `.task/config.json`, the way git finds its
|
|
11
11
|
* `.git`. Returns the directory that *contains* `.task`, or null.
|
|
@@ -21,6 +21,46 @@ export function findRoot(from) {
|
|
|
21
21
|
dir = parent;
|
|
22
22
|
}
|
|
23
23
|
}
|
|
24
|
+
/**
|
|
25
|
+
* The widest board scope `from` belongs to: the *outermost* ancestor holding a
|
|
26
|
+
* `.task/` (a monorepo's root board), or `from` itself when no ancestor has
|
|
27
|
+
* one. Where `findRoot` answers "which board am I on", this answers "which
|
|
28
|
+
* repo of boards am I in" — the anchor for anything cross-board: prefix
|
|
29
|
+
* routing and `task boards`.
|
|
30
|
+
*/
|
|
31
|
+
export function findScopeRoot(from) {
|
|
32
|
+
let dir = from;
|
|
33
|
+
let top = null;
|
|
34
|
+
for (;;) {
|
|
35
|
+
if (existsSync(join(dir, TASK_DIR, CONFIG_FILE)))
|
|
36
|
+
top = dir;
|
|
37
|
+
const parent = dirname(dir);
|
|
38
|
+
if (parent === dir)
|
|
39
|
+
break;
|
|
40
|
+
dir = parent;
|
|
41
|
+
}
|
|
42
|
+
return top ?? from;
|
|
43
|
+
}
|
|
44
|
+
/** A board's config, read without opening a store. Throws on a broken file. */
|
|
45
|
+
export function boardConfig(root) {
|
|
46
|
+
return JSON.parse(readFileSync(join(root, TASK_DIR, CONFIG_FILE), "utf8"));
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* Every board in scope whose prefix is `prefix` (case-insensitive). Normally
|
|
50
|
+
* zero or one — two boards sharing a prefix is a repo mistake this surfaces
|
|
51
|
+
* rather than resolves. Boards with unreadable configs can't match.
|
|
52
|
+
*/
|
|
53
|
+
export function findBoardsByPrefix(scopeRoot, prefix) {
|
|
54
|
+
const wanted = prefix.toUpperCase();
|
|
55
|
+
return findBoards(scopeRoot).filter((ref) => {
|
|
56
|
+
try {
|
|
57
|
+
return boardConfig(ref.root).prefix.toUpperCase() === wanted;
|
|
58
|
+
}
|
|
59
|
+
catch {
|
|
60
|
+
return false;
|
|
61
|
+
}
|
|
62
|
+
});
|
|
63
|
+
}
|
|
24
64
|
/** Directories that never contain a board worth serving. */
|
|
25
65
|
const SKIP_DIRS = new Set(["node_modules", "dist", "build", "out", "coverage", "target"]);
|
|
26
66
|
/**
|
|
@@ -62,18 +102,19 @@ export function findBoards(serveRoot, maxDepth = 6) {
|
|
|
62
102
|
boards.sort((a, b) => (a.id === "." ? -1 : b.id === "." ? 1 : a.id < b.id ? -1 : 1));
|
|
63
103
|
return boards;
|
|
64
104
|
}
|
|
65
|
-
/** Derive an id prefix from a project name: "phone agent" → "
|
|
105
|
+
/** Derive an id prefix from a project name: "phone agent" → "PHO". */
|
|
66
106
|
export function derivePrefix(name) {
|
|
67
107
|
const word = name.toUpperCase().replace(/[^A-Z0-9]+/g, " ").trim().split(" ")[0];
|
|
68
|
-
return (word || "
|
|
108
|
+
return (word || "TAS").slice(0, 3);
|
|
69
109
|
}
|
|
70
110
|
function now() {
|
|
71
111
|
return new Date().toISOString();
|
|
72
112
|
}
|
|
73
113
|
/**
|
|
74
|
-
* The
|
|
114
|
+
* The legacy persistence layer: one SQLite database inside `.task/`, opened
|
|
75
115
|
* synchronously via node:sqlite (built into Node ≥22.13 — zero dependencies,
|
|
76
|
-
* nothing to compile, safe for `npx`).
|
|
116
|
+
* nothing to compile, safe for `npx`). Boards created before the text format
|
|
117
|
+
* still run on this until `task migrate` moves them over.
|
|
77
118
|
*/
|
|
78
119
|
export class TaskStore {
|
|
79
120
|
root;
|
|
@@ -114,14 +155,25 @@ export class TaskStore {
|
|
|
114
155
|
tags: JSON.parse(row.tags),
|
|
115
156
|
milestone: row.milestone,
|
|
116
157
|
needsHuman: row.needs_human !== 0,
|
|
158
|
+
blocks: this.linkedNumbers("blocker_id", row.id),
|
|
159
|
+
blockedBy: this.linkedNumbers("blocked_id", row.id),
|
|
160
|
+
prs: JSON.parse(row.prs),
|
|
117
161
|
position: row.position,
|
|
118
162
|
createdAt: row.created_at,
|
|
119
163
|
updatedAt: row.updated_at,
|
|
120
164
|
};
|
|
121
165
|
}
|
|
166
|
+
/** The other end of every link where `column` is this task. */
|
|
167
|
+
linkedNumbers(column, number) {
|
|
168
|
+
const other = column === "blocker_id" ? "blocked_id" : "blocker_id";
|
|
169
|
+
const rows = this.db
|
|
170
|
+
.prepare(`SELECT ${other} AS n FROM task_links WHERE ${column} = ? ORDER BY ${other}`)
|
|
171
|
+
.all(number);
|
|
172
|
+
return rows.map((r) => r.n);
|
|
173
|
+
}
|
|
122
174
|
toComment(row) {
|
|
123
175
|
return {
|
|
124
|
-
id: row.id,
|
|
176
|
+
id: String(row.id),
|
|
125
177
|
taskId: this.displayId(row.task_id),
|
|
126
178
|
author: row.author,
|
|
127
179
|
body: row.body,
|
|
@@ -129,6 +181,9 @@ export class TaskStore {
|
|
|
129
181
|
};
|
|
130
182
|
}
|
|
131
183
|
list(filter = {}) {
|
|
184
|
+
if (filter.archived) {
|
|
185
|
+
throw new Error("archiving needs a text-format board — run `task migrate` first");
|
|
186
|
+
}
|
|
132
187
|
const where = [];
|
|
133
188
|
const params = [];
|
|
134
189
|
if (filter.statuses?.length) {
|
|
@@ -164,15 +219,29 @@ export class TaskStore {
|
|
|
164
219
|
.get(status);
|
|
165
220
|
const timestamp = now();
|
|
166
221
|
const result = this.db
|
|
167
|
-
.prepare(`INSERT INTO tasks (title, description, status, tags, milestone, needs_human, position, created_at, updated_at)
|
|
168
|
-
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)`)
|
|
169
|
-
.run(input.title, input.description ?? "", status, JSON.stringify(input.tags ?? []), input.milestone ?? null, input.needsHuman ? 1 : 0, (max.max ?? 0) + POSITION_GAP, timestamp, timestamp);
|
|
170
|
-
|
|
222
|
+
.prepare(`INSERT INTO tasks (title, description, status, tags, milestone, needs_human, prs, position, created_at, updated_at)
|
|
223
|
+
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`)
|
|
224
|
+
.run(input.title, input.description ?? "", status, JSON.stringify(input.tags ?? []), input.milestone ?? null, input.needsHuman ? 1 : 0, JSON.stringify(input.prs ?? []), (max.max ?? 0) + POSITION_GAP, timestamp, timestamp);
|
|
225
|
+
const number = Number(result.lastInsertRowid);
|
|
226
|
+
if (input.blocks !== undefined)
|
|
227
|
+
this.reconcileLinks("blocker_id", number, input.blocks);
|
|
228
|
+
if (input.blockedBy !== undefined)
|
|
229
|
+
this.reconcileLinks("blocked_id", number, input.blockedBy);
|
|
230
|
+
return this.get(number);
|
|
171
231
|
}
|
|
172
232
|
update(number, patch) {
|
|
173
233
|
const existing = this.get(number);
|
|
174
234
|
if (!existing)
|
|
175
235
|
throw new Error(`no such task: ${this.displayId(number)}`);
|
|
236
|
+
// Reconciled outside the UPDATE — links live in their own table. Done
|
|
237
|
+
// first so a bad target rejects the whole patch before anything writes.
|
|
238
|
+
let linksChanged = false;
|
|
239
|
+
if (patch.blocks !== undefined) {
|
|
240
|
+
linksChanged = this.reconcileLinks("blocker_id", number, patch.blocks);
|
|
241
|
+
}
|
|
242
|
+
if (patch.blockedBy !== undefined) {
|
|
243
|
+
linksChanged = this.reconcileLinks("blocked_id", number, patch.blockedBy) || linksChanged;
|
|
244
|
+
}
|
|
176
245
|
const sets = [];
|
|
177
246
|
const params = [];
|
|
178
247
|
const set = (column, value) => {
|
|
@@ -189,6 +258,8 @@ export class TaskStore {
|
|
|
189
258
|
set("milestone", patch.milestone);
|
|
190
259
|
if (patch.needsHuman !== undefined)
|
|
191
260
|
set("needs_human", patch.needsHuman ? 1 : 0);
|
|
261
|
+
if (patch.prs !== undefined)
|
|
262
|
+
set("prs", JSON.stringify(patch.prs));
|
|
192
263
|
if (patch.status !== undefined) {
|
|
193
264
|
set("status", patch.status);
|
|
194
265
|
if (patch.position === undefined && patch.status !== existing.status) {
|
|
@@ -202,11 +273,70 @@ export class TaskStore {
|
|
|
202
273
|
}
|
|
203
274
|
if (patch.position !== undefined)
|
|
204
275
|
set("position", patch.position);
|
|
205
|
-
if (sets.length === 0)
|
|
276
|
+
if (sets.length === 0 && !linksChanged)
|
|
206
277
|
return existing;
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
278
|
+
if (sets.length > 0) {
|
|
279
|
+
set("updated_at", now());
|
|
280
|
+
params.push(number);
|
|
281
|
+
this.db.prepare(`UPDATE tasks SET ${sets.join(", ")} WHERE id = ?`).run(...params);
|
|
282
|
+
}
|
|
283
|
+
return this.get(number);
|
|
284
|
+
}
|
|
285
|
+
/**
|
|
286
|
+
* Make the link table agree with `targets` for one side of one task —
|
|
287
|
+
* `blocker_id` when setting what `number` blocks, `blocked_id` when setting
|
|
288
|
+
* what blocks it. The other task's view is the same row read from the other
|
|
289
|
+
* end, so there is no second write to keep consistent. Every task touched
|
|
290
|
+
* (both ends of every added or removed link) gets its `updated_at` bumped.
|
|
291
|
+
*/
|
|
292
|
+
reconcileLinks(column, number, targets) {
|
|
293
|
+
const other = column === "blocker_id" ? "blocked_id" : "blocker_id";
|
|
294
|
+
const wanted = [...new Set(targets)];
|
|
295
|
+
for (const target of wanted) {
|
|
296
|
+
if (target === number) {
|
|
297
|
+
throw new Error(`a task can't block itself: ${this.displayId(number)}`);
|
|
298
|
+
}
|
|
299
|
+
if (!this.db.prepare("SELECT id FROM tasks WHERE id = ?").get(target)) {
|
|
300
|
+
throw new Error(`no such task: ${this.displayId(target)}`);
|
|
301
|
+
}
|
|
302
|
+
}
|
|
303
|
+
const current = new Set(this.linkedNumbers(column, number));
|
|
304
|
+
const removed = [...current].filter((n) => !wanted.includes(n));
|
|
305
|
+
const added = wanted.filter((n) => !current.has(n));
|
|
306
|
+
for (const n of removed) {
|
|
307
|
+
this.db
|
|
308
|
+
.prepare(`DELETE FROM task_links WHERE ${column} = ? AND ${other} = ?`)
|
|
309
|
+
.run(number, n);
|
|
310
|
+
}
|
|
311
|
+
for (const n of added) {
|
|
312
|
+
this.db
|
|
313
|
+
.prepare(`INSERT OR IGNORE INTO task_links (${column}, ${other}) VALUES (?, ?)`)
|
|
314
|
+
.run(number, n);
|
|
315
|
+
}
|
|
316
|
+
const touched = [...removed, ...added];
|
|
317
|
+
if (touched.length > 0) {
|
|
318
|
+
const timestamp = now();
|
|
319
|
+
const bump = this.db.prepare("UPDATE tasks SET updated_at = ? WHERE id = ?");
|
|
320
|
+
for (const n of [...touched, number])
|
|
321
|
+
bump.run(timestamp, n);
|
|
322
|
+
}
|
|
323
|
+
return touched.length > 0;
|
|
324
|
+
}
|
|
325
|
+
/** `task link A --blocks B` and friends — additive, unlike the patch form. */
|
|
326
|
+
link(number, relation, target) {
|
|
327
|
+
if (!this.get(number))
|
|
328
|
+
throw new Error(`no such task: ${this.displayId(number)}`);
|
|
329
|
+
const column = relation === "blocks" ? "blocker_id" : "blocked_id";
|
|
330
|
+
const current = this.linkedNumbers(column, number);
|
|
331
|
+
this.reconcileLinks(column, number, [...current, target]);
|
|
332
|
+
return this.get(number);
|
|
333
|
+
}
|
|
334
|
+
unlink(number, relation, target) {
|
|
335
|
+
if (!this.get(number))
|
|
336
|
+
throw new Error(`no such task: ${this.displayId(number)}`);
|
|
337
|
+
const column = relation === "blocks" ? "blocker_id" : "blocked_id";
|
|
338
|
+
const current = this.linkedNumbers(column, number);
|
|
339
|
+
this.reconcileLinks(column, number, current.filter((n) => n !== target));
|
|
210
340
|
return this.get(number);
|
|
211
341
|
}
|
|
212
342
|
delete(number) {
|
|
@@ -214,6 +344,13 @@ export class TaskStore {
|
|
|
214
344
|
if (result.changes === 0)
|
|
215
345
|
throw new Error(`no such task: ${this.displayId(number)}`);
|
|
216
346
|
}
|
|
347
|
+
/** The archive is a text-format feature — a directory move, not a table. */
|
|
348
|
+
archive(_number) {
|
|
349
|
+
throw new Error("archiving needs a text-format board — run `task migrate` first");
|
|
350
|
+
}
|
|
351
|
+
unarchive(_number) {
|
|
352
|
+
throw new Error("archiving needs a text-format board — run `task migrate` first");
|
|
353
|
+
}
|
|
217
354
|
comments(number) {
|
|
218
355
|
const rows = this.db
|
|
219
356
|
.prepare("SELECT * FROM comments WHERE task_id = ? ORDER BY id")
|
|
@@ -232,12 +369,15 @@ export class TaskStore {
|
|
|
232
369
|
return this.toComment(row);
|
|
233
370
|
}
|
|
234
371
|
deleteComment(number, commentId) {
|
|
235
|
-
const
|
|
236
|
-
|
|
237
|
-
.
|
|
372
|
+
const rowid = Number(commentId);
|
|
373
|
+
const row = (Number.isInteger(rowid)
|
|
374
|
+
? this.db
|
|
375
|
+
.prepare("SELECT * FROM comments WHERE id = ? AND task_id = ?")
|
|
376
|
+
.get(rowid, number)
|
|
377
|
+
: undefined);
|
|
238
378
|
if (!row)
|
|
239
379
|
throw new Error(`no such comment on ${this.displayId(number)}: ${commentId}`);
|
|
240
|
-
this.db.prepare("DELETE FROM comments WHERE id = ?").run(
|
|
380
|
+
this.db.prepare("DELETE FROM comments WHERE id = ?").run(rowid);
|
|
241
381
|
return this.toComment(row);
|
|
242
382
|
}
|
|
243
383
|
commentCounts() {
|
|
@@ -301,6 +441,16 @@ const MIGRATIONS = [
|
|
|
301
441
|
ALTER TABLE tasks ADD COLUMN needs_human INTEGER NOT NULL DEFAULT 0;
|
|
302
442
|
ALTER TABLE tasks DROP COLUMN priority;
|
|
303
443
|
ALTER TABLE tasks DROP COLUMN assignee;`,
|
|
444
|
+
// v3 — dependencies and pull requests. One direction of "blocks" is the
|
|
445
|
+
// whole relation: (blocker, blocked) read from the blocked side is
|
|
446
|
+
// "blocked by", so the mirror is a query, not a second row. PRs are a JSON
|
|
447
|
+
// list of URLs, same shape as tags.
|
|
448
|
+
`CREATE TABLE task_links (
|
|
449
|
+
blocker_id INTEGER NOT NULL REFERENCES tasks(id) ON DELETE CASCADE,
|
|
450
|
+
blocked_id INTEGER NOT NULL REFERENCES tasks(id) ON DELETE CASCADE,
|
|
451
|
+
PRIMARY KEY (blocker_id, blocked_id)
|
|
452
|
+
);
|
|
453
|
+
ALTER TABLE tasks ADD COLUMN prs TEXT NOT NULL DEFAULT '[]';`,
|
|
304
454
|
];
|
|
305
455
|
/**
|
|
306
456
|
* Bring `db` up to the newest schema. DDL and `PRAGMA user_version` are both
|
|
@@ -323,24 +473,4 @@ function migrate(db) {
|
|
|
323
473
|
throw error;
|
|
324
474
|
}
|
|
325
475
|
}
|
|
326
|
-
/**
|
|
327
|
-
* Create `.task/` in `root`: config, an empty database, and a .gitignore for
|
|
328
|
-
* SQLite's transient sidecar files (the database itself is meant to be
|
|
329
|
-
* committed — that's the point).
|
|
330
|
-
*/
|
|
331
|
-
export function initProject(root, options) {
|
|
332
|
-
const taskDir = join(root, TASK_DIR);
|
|
333
|
-
if (existsSync(join(taskDir, CONFIG_FILE))) {
|
|
334
|
-
throw new Error(`already initialized: ${join(taskDir, CONFIG_FILE)} exists`);
|
|
335
|
-
}
|
|
336
|
-
mkdirSync(taskDir, { recursive: true });
|
|
337
|
-
const config = {
|
|
338
|
-
name: options.name,
|
|
339
|
-
prefix: options.prefix ?? derivePrefix(options.name),
|
|
340
|
-
version: 1,
|
|
341
|
-
};
|
|
342
|
-
writeFileSync(join(taskDir, CONFIG_FILE), `${JSON.stringify(config, null, 2)}\n`);
|
|
343
|
-
writeFileSync(join(taskDir, ".gitignore"), "# SQLite transients — tasks.db itself is committed.\n*.db-journal\n*.db-wal\n*.db-shm\n");
|
|
344
|
-
return new TaskStore(root);
|
|
345
|
-
}
|
|
346
476
|
//# sourceMappingURL=store.js.map
|