@a9n-shoji/rvw 0.2.1 → 0.2.2

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.
Files changed (97) hide show
  1. package/CHANGELOG.md +11 -0
  2. package/README.md +19 -2
  3. package/dist/cli.mjs +1 -1
  4. package/dist/cli.mjs.map +1 -1
  5. package/dist/web/assets/{DocumentViewer-DvrDlIpR.js → DocumentViewer-ADzspLC4.js} +17 -17
  6. package/dist/web/assets/{MarkdownTable-DbDc9VoP.js → MarkdownTable-DVJ0_MIC.js} +1 -1
  7. package/dist/web/assets/WalkthroughViewer-yQibj2tK.js +1 -0
  8. package/dist/web/assets/{abnfDiagram-N423BO3Z-fQDP4qYL.js → abnfDiagram-N423BO3Z-6dQzEuPV.js} +1 -1
  9. package/dist/web/assets/architecture-TIHT7OUA-DEoBuEnc.js +1 -0
  10. package/dist/web/assets/{architectureDiagram-T3A2C74G-D3Aon3Nd.js → architectureDiagram-T3A2C74G-DP7hHV7T.js} +1 -1
  11. package/dist/web/assets/{blockDiagram-VBNYF7ZC-DS1DcAqy.js → blockDiagram-VBNYF7ZC-ZbwzVKWP.js} +1 -1
  12. package/dist/web/assets/{c4Diagram-5PPSVZJV-BHQWz7l2.js → c4Diagram-5PPSVZJV-HVD9_uV4.js} +1 -1
  13. package/dist/web/assets/channel-DjgdV-zW.js +1 -0
  14. package/dist/web/assets/{chunk-2GRJ4B5K-CaahxDVT.js → chunk-2GRJ4B5K-Bkxs2d4J.js} +1 -1
  15. package/dist/web/assets/{chunk-4I5QYGJK-Bat5hdXD.js → chunk-4I5QYGJK-BJHE6zC_.js} +1 -1
  16. package/dist/web/assets/{chunk-5RXB4S5H-jyonN41f.js → chunk-5RXB4S5H-B-52dfCQ.js} +1 -1
  17. package/dist/web/assets/{chunk-6Q2QTUOP-BBo9TYzL.js → chunk-6Q2QTUOP-BpD0vQ66.js} +1 -1
  18. package/dist/web/assets/{chunk-7Z6QIM7H-CGSwsKhC.js → chunk-7Z6QIM7H-BTI1qgAO.js} +1 -1
  19. package/dist/web/assets/{chunk-GF5L2VYU-Cuca3bAY.js → chunk-GF5L2VYU-B8BxoCCx.js} +1 -1
  20. package/dist/web/assets/{chunk-I66GZJ75-DRdqLSyH.js → chunk-I66GZJ75-zwi-Xf01.js} +1 -1
  21. package/dist/web/assets/{chunk-JQJVKLGR-8xhLkhs2.js → chunk-JQJVKLGR-D9mKBWUz.js} +1 -1
  22. package/dist/web/assets/{chunk-KBJHAD2P-oOV-3e5-.js → chunk-KBJHAD2P-Qmtir3qc.js} +1 -1
  23. package/dist/web/assets/{chunk-NSK5VX7P-CXit1l3q.js → chunk-NSK5VX7P-SP2vZdAo.js} +1 -1
  24. package/dist/web/assets/{chunk-QR6OTTB3-DcdCU-01.js → chunk-QR6OTTB3-uVDCHurs.js} +1 -1
  25. package/dist/web/assets/{chunk-UBXNYLIW-i72Hgljr.js → chunk-UBXNYLIW-CtNzBWOU.js} +1 -1
  26. package/dist/web/assets/{chunk-W5SLKNZC-DetAQo7M.js → chunk-W5SLKNZC-BPfDqbmK.js} +1 -1
  27. package/dist/web/assets/{chunk-WRU74C26-DDUvJFNs.js → chunk-WRU74C26-BZkEOexq.js} +1 -1
  28. package/dist/web/assets/classDiagram-JCYQIIEL-B6Qjam7Y.js +1 -0
  29. package/dist/web/assets/classDiagram-v2-OCEON4UE-B6Qjam7Y.js +1 -0
  30. package/dist/web/assets/{cynefin-VYW2F7L2-fd-v6ani.js → cynefin-VYW2F7L2-BRisCyqC.js} +1 -1
  31. package/dist/web/assets/{cynefinDiagram-MW4NZA55-DRsVpAC3.js → cynefinDiagram-MW4NZA55-ClIrmCkB.js} +1 -1
  32. package/dist/web/assets/{dagre-VZM6K2ZE-BnRSs_fe.js → dagre-VZM6K2ZE-X31uC_JB.js} +1 -1
  33. package/dist/web/assets/{diagram-7IWD3JNH-D1g0PR4y.js → diagram-7IWD3JNH-DBQFjl0i.js} +1 -1
  34. package/dist/web/assets/{diagram-B4RE2ZJO-DuDKsQLp.js → diagram-B4RE2ZJO-BZ7934Wg.js} +1 -1
  35. package/dist/web/assets/{diagram-LBJQPF4R-COpzgGe7.js → diagram-LBJQPF4R-CcJqH9aY.js} +1 -1
  36. package/dist/web/assets/{diagram-Q27KOJAE-DR2vRbPE.js → diagram-Q27KOJAE-DzM7eiil.js} +1 -1
  37. package/dist/web/assets/{diagram-UB23O5K3-hs4VGPP7.js → diagram-UB23O5K3-CVCV-d3m.js} +1 -1
  38. package/dist/web/assets/{ebnfDiagram-BXEA7PRR-B_4NlK9q.js → ebnfDiagram-BXEA7PRR-D8xb9FBp.js} +1 -1
  39. package/dist/web/assets/{erDiagram-JOGREHBK-JyoZ3U-o.js → erDiagram-JOGREHBK-1l-G_PMG.js} +1 -1
  40. package/dist/web/assets/eventmodeling-45OFAUF4-ndNeUBOZ.js +1 -0
  41. package/dist/web/assets/flowDiagram-UKHOOZJN-BVxK_6Tu.js +1 -0
  42. package/dist/web/assets/{ganttDiagram-PKOTCBZU-f37I0Twm.js → ganttDiagram-PKOTCBZU-CDJ9a1tp.js} +1 -1
  43. package/dist/web/assets/{gitGraph-TEB2WS4Q-B_QWjr7j.js → gitGraph-TEB2WS4Q-DOeTh5wB.js} +1 -1
  44. package/dist/web/assets/{gitGraphDiagram-DS77QQ5N-AZsaC0hu.js → gitGraphDiagram-DS77QQ5N-DYLxc8Nz.js} +1 -1
  45. package/dist/web/assets/index-9cOaPesh.js +384 -0
  46. package/dist/web/assets/{info-DKCQHKI2-BRfisbEI.js → info-DKCQHKI2-B5u97QuQ.js} +1 -1
  47. package/dist/web/assets/{infoDiagram-6WML65LV-CaIb64N5.js → infoDiagram-6WML65LV-zosKW2OD.js} +1 -1
  48. package/dist/web/assets/{ishikawaDiagram-WSZJBQD7-BoJrcTja.js → ishikawaDiagram-WSZJBQD7-VYcc_au8.js} +1 -1
  49. package/dist/web/assets/{journeyDiagram-NVQOT4AX-CRR1dZy8.js → journeyDiagram-NVQOT4AX-C_nU8kP4.js} +1 -1
  50. package/dist/web/assets/{kanban-definition-27J2QSJJ-D5skDuP4.js → kanban-definition-27J2QSJJ-DybKaWfx.js} +1 -1
  51. package/dist/web/assets/{line-BKKx0vSh.js → line-DWsGplGj.js} +1 -1
  52. package/dist/web/assets/{mermaid-parser.core-DvZnIth0.js → mermaid-parser.core-D_T_3oIQ.js} +3 -3
  53. package/dist/web/assets/{mermaid.core-hykiOF_o.js → mermaid.core-BoLGzxB5.js} +4 -4
  54. package/dist/web/assets/{mindmap-definition-FAOFIHXS-BN2LQ4Yn.js → mindmap-definition-FAOFIHXS-CsdpqPIa.js} +1 -1
  55. package/dist/web/assets/{packet-7NZHBO7P-CS5I0NlV.js → packet-7NZHBO7P-CReAEF1h.js} +1 -1
  56. package/dist/web/assets/{pegDiagram-VL7TDLO6-WvOdhbxo.js → pegDiagram-VL7TDLO6-CE9-NPMu.js} +1 -1
  57. package/dist/web/assets/{pie-RZYD4A2V-BwNAZrQ1.js → pie-RZYD4A2V-GYixXUka.js} +1 -1
  58. package/dist/web/assets/{pieDiagram-7S7Q4E2Y-CbyrZjm7.js → pieDiagram-7S7Q4E2Y-CqaAKNg2.js} +1 -1
  59. package/dist/web/assets/{quadrantDiagram-CIZ2JOQS-CW9YBxAO.js → quadrantDiagram-CIZ2JOQS-eRMHJqfj.js} +1 -1
  60. package/dist/web/assets/{radar-I7S5WNFK-DBoCLDNH.js → radar-I7S5WNFK-BwHxP0iK.js} +1 -1
  61. package/dist/web/assets/{railroad-3IZDKUUU-BOjpYyDz.js → railroad-3IZDKUUU-AHc3O4Oz.js} +1 -1
  62. package/dist/web/assets/railroad-abnf-AHOZXSZD-ZKY5olmV.js +1 -0
  63. package/dist/web/assets/railroad-ebnf-EBAXGLYW-CrG1UCMo.js +1 -0
  64. package/dist/web/assets/railroad-peg-LSFZ7HO6-CoY6MIbj.js +1 -0
  65. package/dist/web/assets/{railroadDiagram-AXF67PYL-BdOOOq8o.js → railroadDiagram-AXF67PYL-BhAxCokG.js} +1 -1
  66. package/dist/web/assets/{requirementDiagram-LRYGKXZP-DIYlSrTb.js → requirementDiagram-LRYGKXZP-BRW-kYhg.js} +1 -1
  67. package/dist/web/assets/{sankeyDiagram-W5VNT64P-Cc1IGxp_.js → sankeyDiagram-W5VNT64P-DfnYLbDJ.js} +1 -1
  68. package/dist/web/assets/{sequenceDiagram-SI44F4Z6-CJsPO9Z9.js → sequenceDiagram-SI44F4Z6-WEkIPSg8.js} +1 -1
  69. package/dist/web/assets/{stateDiagram-OKZ733FA-B033gpHZ.js → stateDiagram-OKZ733FA-CdN7veIN.js} +1 -1
  70. package/dist/web/assets/stateDiagram-v2-UEYNNEHI-0xn0gbpn.js +1 -0
  71. package/dist/web/assets/{swimlanes-SLNWSIFB-C0Tstg7e.js → swimlanes-SLNWSIFB-g9wWLf5Y.js} +1 -1
  72. package/dist/web/assets/swimlanesDiagram-ULZ7WXOC-YJ3yh_d3.js +8 -0
  73. package/dist/web/assets/{timeline-definition-Z64GVDOM-BA3y-16W.js → timeline-definition-Z64GVDOM-DjkKZIPE.js} +1 -1
  74. package/dist/web/assets/{treeView-QDETBFTQ-BUNq-JXr.js → treeView-QDETBFTQ-WARa9r09.js} +1 -1
  75. package/dist/web/assets/{treemap-6X3UGDF4-FIR_NbUo.js → treemap-6X3UGDF4-CTFjdb6k.js} +1 -1
  76. package/dist/web/assets/{vennDiagram-T6HMQDX7-IeFFjnlq.js → vennDiagram-T6HMQDX7-CI9QrBwu.js} +1 -1
  77. package/dist/web/assets/{wardley-OPB4EBWU-DQAX4LKo.js → wardley-OPB4EBWU-Cfo_Nnla.js} +1 -1
  78. package/dist/web/assets/{wardleyDiagram-T6FBY63Y-guGPPMAG.js → wardleyDiagram-T6FBY63Y-CzGJ4fzZ.js} +1 -1
  79. package/dist/web/assets/{xychartDiagram-ELKLHX3M-Cj0v359_.js → xychartDiagram-ELKLHX3M-BXCiD7gJ.js} +1 -1
  80. package/dist/web/index.html +1 -1
  81. package/package.json +2 -1
  82. package/skills/rvw/SKILL.md +56 -15
  83. package/skills/rvw-watch-comments/SKILL.md +48 -17
  84. package/skills/rvw-watch-comments/scripts/watch-state.mjs +112 -62
  85. package/dist/web/assets/WalkthroughViewer-aDUeKC3B.js +0 -1
  86. package/dist/web/assets/architecture-TIHT7OUA-CuFS9GkN.js +0 -1
  87. package/dist/web/assets/channel-CTWz7tRI.js +0 -1
  88. package/dist/web/assets/classDiagram-JCYQIIEL-BJQv9QuO.js +0 -1
  89. package/dist/web/assets/classDiagram-v2-OCEON4UE-BJQv9QuO.js +0 -1
  90. package/dist/web/assets/eventmodeling-45OFAUF4-CfUhQK5g.js +0 -1
  91. package/dist/web/assets/flowDiagram-UKHOOZJN-FFZ82SPa.js +0 -1
  92. package/dist/web/assets/index-CY_JoUL3.js +0 -384
  93. package/dist/web/assets/railroad-abnf-AHOZXSZD-DQhDS2pf.js +0 -1
  94. package/dist/web/assets/railroad-ebnf-EBAXGLYW-Dtt2kOaN.js +0 -1
  95. package/dist/web/assets/railroad-peg-LSFZ7HO6-nfH8zno6.js +0 -1
  96. package/dist/web/assets/stateDiagram-v2-UEYNNEHI-wS01qj3t.js +0 -1
  97. package/dist/web/assets/swimlanesDiagram-ULZ7WXOC-DoAqfWAd.js +0 -8
@@ -98,17 +98,11 @@ function openState(statePath, create) {
98
98
  created_at TEXT NOT NULL,
99
99
  updated_at TEXT NOT NULL
100
100
  );
101
- CREATE TABLE IF NOT EXISTS comment_statuses (
102
- comment_ref TEXT PRIMARY KEY,
103
- idempotency_key TEXT NOT NULL UNIQUE,
104
- post_id TEXT UNIQUE,
105
- created_at TEXT NOT NULL,
106
- updated_at TEXT NOT NULL
107
- );
108
101
  CREATE TABLE IF NOT EXISTS operations (
109
102
  batch_id TEXT NOT NULL,
110
103
  comment_ref TEXT NOT NULL,
111
104
  idempotency_key TEXT NOT NULL UNIQUE,
105
+ post_id TEXT,
112
106
  PRIMARY KEY(batch_id, comment_ref)
113
107
  );
114
108
  CREATE TABLE IF NOT EXISTS suppressed_posts (
@@ -123,6 +117,7 @@ function openState(statePath, create) {
123
117
  CREATE INDEX IF NOT EXISTS batches_pending_pr
124
118
  ON batches(status, pull_request_url, next_attempt_at, created_at);
125
119
  `);
120
+ migrateStateSchema(database);
126
121
  if (create) chmodSync(absolute, 0o600);
127
122
  return { database, absolute };
128
123
  }
@@ -156,39 +151,102 @@ function setMeta(database, key, value) {
156
151
  .run(key, value);
157
152
  }
158
153
 
159
- function ensureCommentStatus(database, commentRef, now) {
160
- const existing = database
161
- .prepare("SELECT * FROM comment_statuses WHERE comment_ref = ?")
162
- .get(commentRef);
163
- if (existing) return existing;
164
- const legacyOperation = database
165
- .prepare(
166
- `SELECT o.idempotency_key
167
- FROM operations o
168
- JOIN batches b ON b.id = o.batch_id
169
- WHERE o.comment_ref = ? AND b.status IN ('pending', 'in_flight')
170
- ORDER BY b.created_at DESC LIMIT 1`,
171
- )
172
- .get(commentRef);
173
- const idempotencyKey =
174
- legacyOperation?.idempotency_key ?? `${getMeta(database, "task_id")}:status:${randomUUID()}`;
175
- database
176
- .prepare(
177
- `INSERT INTO comment_statuses(
178
- comment_ref, idempotency_key, post_id, created_at, updated_at
179
- ) VALUES (?, ?, NULL, ?, ?)`,
180
- )
181
- .run(commentRef, idempotencyKey, now, now);
182
- return database.prepare("SELECT * FROM comment_statuses WHERE comment_ref = ?").get(commentRef);
154
+ function tableExists(database, tableName) {
155
+ return Boolean(
156
+ database
157
+ .prepare("SELECT 1 AS present FROM sqlite_master WHERE type = 'table' AND name = ?")
158
+ .get(tableName),
159
+ );
160
+ }
161
+
162
+ function migrateStateSchema(database) {
163
+ const operationColumns = database.prepare("PRAGMA table_info(operations)").all();
164
+ if (
165
+ operationColumns.some((column) => column.name === "post_id") &&
166
+ getMeta(database, "batch_scoped_status_posts") === "1"
167
+ ) {
168
+ return;
169
+ }
170
+ transaction(database, () => {
171
+ const currentOperationColumns = database.prepare("PRAGMA table_info(operations)").all();
172
+ if (!currentOperationColumns.some((column) => column.name === "post_id")) {
173
+ database.exec("ALTER TABLE operations ADD COLUMN post_id TEXT;");
174
+ }
175
+ if (getMeta(database, "batch_scoped_status_posts") === "1") return;
176
+ if (tableExists(database, "comment_statuses")) {
177
+ const rows = database
178
+ .prepare(
179
+ `SELECT b.id AS batch_id, e.comment_ref,
180
+ b.created_at AS batch_created_at,
181
+ o.idempotency_key AS operation_key, o.post_id AS operation_post_id,
182
+ s.idempotency_key AS legacy_key, s.post_id AS legacy_post_id,
183
+ s.updated_at AS legacy_updated_at
184
+ FROM batches b
185
+ JOIN (
186
+ SELECT DISTINCT batch_id, comment_ref FROM events WHERE batch_id IS NOT NULL
187
+ ) e ON e.batch_id = b.id
188
+ LEFT JOIN operations o ON o.batch_id = b.id AND o.comment_ref = e.comment_ref
189
+ LEFT JOIN comment_statuses s ON s.comment_ref = e.comment_ref
190
+ WHERE b.status != 'completed' AND b.attempts > 0
191
+ ORDER BY e.comment_ref,
192
+ CASE b.status WHEN 'in_flight' THEN 0 WHEN 'pending' THEN 1 ELSE 2 END,
193
+ b.created_at DESC`,
194
+ )
195
+ .all();
196
+ const migratedCommentRefs = new Set();
197
+ for (const row of rows) {
198
+ const useLegacyStatus =
199
+ !migratedCommentRefs.has(row.comment_ref) &&
200
+ row.legacy_key &&
201
+ row.legacy_updated_at >= row.batch_created_at;
202
+ if (useLegacyStatus) migratedCommentRefs.add(row.comment_ref);
203
+ if (row.operation_key) {
204
+ if (useLegacyStatus && row.operation_post_id === null && row.legacy_post_id !== null) {
205
+ database
206
+ .prepare("UPDATE operations SET post_id = ? WHERE batch_id = ? AND comment_ref = ?")
207
+ .run(row.legacy_post_id, row.batch_id, row.comment_ref);
208
+ }
209
+ continue;
210
+ }
211
+ database
212
+ .prepare(
213
+ `INSERT INTO operations(batch_id, comment_ref, idempotency_key, post_id)
214
+ VALUES (?, ?, ?, ?)`,
215
+ )
216
+ .run(
217
+ row.batch_id,
218
+ row.comment_ref,
219
+ useLegacyStatus
220
+ ? row.legacy_key
221
+ : `${getMeta(database, "task_id") ?? "task"}:${row.batch_id}:${randomUUID()}`,
222
+ useLegacyStatus ? row.legacy_post_id : null,
223
+ );
224
+ }
225
+ }
226
+ setMeta(database, "batch_scoped_status_posts", "1");
227
+ });
228
+ }
229
+
230
+ function ensureBatchOperations(database, batchId) {
231
+ const commentRefs = database
232
+ .prepare("SELECT DISTINCT comment_ref FROM events WHERE batch_id = ? ORDER BY comment_ref")
233
+ .all(batchId)
234
+ .map((operation) => operation.comment_ref);
235
+ for (let index = 0; index < commentRefs.length; index += 1) {
236
+ database
237
+ .prepare(
238
+ `INSERT OR IGNORE INTO operations(batch_id, comment_ref, idempotency_key, post_id)
239
+ VALUES (?, ?, ?, NULL)`,
240
+ )
241
+ .run(batchId, commentRefs[index], `${getMeta(database, "task_id")}:${batchId}:${index + 1}`);
242
+ }
183
243
  }
184
244
 
185
245
  function batchStatusOperations(database, batchId) {
186
246
  return database
187
247
  .prepare(
188
- `SELECT DISTINCT e.comment_ref, s.post_id
189
- FROM events e
190
- LEFT JOIN comment_statuses s ON s.comment_ref = e.comment_ref
191
- WHERE e.batch_id = ? ORDER BY e.comment_ref`,
248
+ `SELECT comment_ref, post_id FROM operations
249
+ WHERE batch_id = ? ORDER BY comment_ref`,
192
250
  )
193
251
  .all(batchId)
194
252
  .map((operation) => ({
@@ -311,19 +369,19 @@ function ingestEvent(database, frame) {
311
369
  now,
312
370
  );
313
371
  if (event.deleted) {
314
- const commentStatus = database
315
- .prepare("SELECT comment_ref FROM comment_statuses WHERE post_id = ?")
316
- .get(event.postId);
317
- if (commentStatus) {
372
+ const operations = database
373
+ .prepare("SELECT batch_id, comment_ref FROM operations WHERE post_id = ?")
374
+ .all(event.postId);
375
+ for (const operation of operations) {
318
376
  database
319
377
  .prepare(
320
- `UPDATE comment_statuses SET post_id = NULL, idempotency_key = ?, updated_at = ?
321
- WHERE comment_ref = ?`,
378
+ `UPDATE operations SET post_id = NULL, idempotency_key = ?
379
+ WHERE batch_id = ? AND comment_ref = ?`,
322
380
  )
323
381
  .run(
324
- `${getMeta(database, "task_id")}:status:${randomUUID()}`,
325
- now,
326
- commentStatus.comment_ref,
382
+ `${getMeta(database, "task_id")}:${operation.batch_id}:${randomUUID()}`,
383
+ operation.batch_id,
384
+ operation.comment_ref,
327
385
  );
328
386
  }
329
387
  }
@@ -448,8 +506,7 @@ function createBatch(database, pullRequestUrl, now) {
448
506
  "UPDATE events SET batch_id = ?, updated_at = ? WHERE pull_request_url = ? AND status = 'pending' AND batch_id IS NULL",
449
507
  )
450
508
  .run(batchId, now, pullRequestUrl);
451
- const commentRefs = [...new Set(events.map((event) => event.comment_ref))];
452
- for (const commentRef of commentRefs) ensureCommentStatus(database, commentRef, now);
509
+ ensureBatchOperations(database, batchId);
453
510
  return batchId;
454
511
  }
455
512
 
@@ -497,17 +554,11 @@ function claim(database, pullRequestUrl, writeKey) {
497
554
  commentRef: event.comment_ref,
498
555
  pullRequestUrl: event.pull_request_url,
499
556
  }));
500
- const commentRefs = database
501
- .prepare("SELECT DISTINCT comment_ref FROM events WHERE batch_id = ? ORDER BY comment_ref")
502
- .all(batchId)
503
- .map((operation) => operation.comment_ref);
504
- for (const commentRef of commentRefs) ensureCommentStatus(database, commentRef, now);
557
+ ensureBatchOperations(database, batchId);
505
558
  const operations = database
506
559
  .prepare(
507
- `SELECT DISTINCT e.comment_ref, s.idempotency_key, s.post_id
508
- FROM events e
509
- JOIN comment_statuses s ON s.comment_ref = e.comment_ref
510
- WHERE e.batch_id = ? ORDER BY e.comment_ref`,
560
+ `SELECT comment_ref, idempotency_key, post_id FROM operations
561
+ WHERE batch_id = ? ORDER BY comment_ref`,
511
562
  )
512
563
  .all(batchId)
513
564
  .map((operation) => ({
@@ -568,17 +619,16 @@ function acknowledge(database, leaseId, input) {
568
619
  .get(leaseId);
569
620
  if (!batch) fail("Active lease was not found");
570
621
  const operation = database
571
- .prepare("SELECT 1 AS present FROM events WHERE batch_id = ? AND comment_ref = ? LIMIT 1")
622
+ .prepare("SELECT post_id FROM operations WHERE batch_id = ? AND comment_ref = ?")
572
623
  .get(batch.id, input.commentRef);
573
624
  if (!operation) fail("Comment is not part of the active lease");
574
625
  const now = new Date().toISOString();
575
- const status = ensureCommentStatus(database, input.commentRef, now);
576
- if (status.post_id !== null && status.post_id !== input.postId) {
577
- fail("Comment already has another status post");
626
+ if (operation.post_id !== null && operation.post_id !== input.postId) {
627
+ fail("Batch operation already has another status post");
578
628
  }
579
629
  database
580
- .prepare("UPDATE comment_statuses SET post_id = ?, updated_at = ? WHERE comment_ref = ?")
581
- .run(input.postId, now, input.commentRef);
630
+ .prepare("UPDATE operations SET post_id = ? WHERE batch_id = ? AND comment_ref = ?")
631
+ .run(input.postId, batch.id, input.commentRef);
582
632
  database
583
633
  .prepare("INSERT OR IGNORE INTO suppressed_posts(post_id, created_at) VALUES (?, ?)")
584
634
  .run(input.postId, now);
@@ -591,7 +641,7 @@ function acknowledge(database, leaseId, input) {
591
641
  batchId: batch.id,
592
642
  commentRef: input.commentRef,
593
643
  statusPostId: input.postId,
594
- status: status.post_id === null ? "recorded" : "existing",
644
+ status: operation.post_id === null ? "recorded" : "existing",
595
645
  };
596
646
  });
597
647
  }
@@ -1 +0,0 @@
1
- import{r as e}from"./rolldown-runtime-hePW80VL.js";import{C as t,D as n,E as r,F as i,G as a,H as o,I as s,L as c,P as l,S as u,U as d,V as f,W as p,c as m,d as h,f as g,o as _,p as v,s as y,u as b,y as x,z as S}from"./index-CY_JoUL3.js";import{a as C,i as w,n as T,o as E,r as D,t as O}from"./MarkdownTable-DbDc9VoP.js";var k=e(a(),1),A=p(),j=2400;function M(e){return k.Children.toArray(e).map(e=>typeof e==`string`||typeof e==`number`?String(e):(0,k.isValidElement)(e)?M(e.props.children):``).join(``)}function N(e,t){return!!(e&&t&&e.startLine===t.startLine&&e.endLine===t.endLine)}function P(){return(0,A.jsx)(`svg`,{"aria-hidden":`true`,viewBox:`0 0 16 16`,width:`16`,height:`16`,children:(0,A.jsx)(`path`,{fill:`currentColor`,d:`M5.5 1.75A1.75 1.75 0 0 1 7.25 0h1.5a1.75 1.75 0 0 1 1.75 1.75V2h3a.75.75 0 0 1 0 1.5h-.64l-.68 10.03A2.5 2.5 0 0 1 9.69 16H6.31a2.5 2.5 0 0 1-2.49-2.47L3.14 3.5H2.5a.75.75 0 0 1 0-1.5h3v-.25Zm1.5 0V2h2v-.25a.25.25 0 0 0-.25-.25h-1.5a.25.25 0 0 0-.25.25ZM4.65 3.5l.67 9.96c.02.58.46 1.04.99 1.04h3.38c.53 0 .97-.46.99-1.04l.67-9.96h-6.7Z`})})}function F({source:e,sourceRange:t,commented:n,bindings:r,references:i,themePreference:a,onOpenReference:o,onCommentRange:s,commentComposer:c}){let u=(0,k.useRef)(null),d=!!c;(0,k.useLayoutEffect)(()=>{if(!d)return;let e=window.requestAnimationFrame(()=>{u.current?.scrollIntoView({block:`nearest`,inline:`nearest`})});return()=>window.cancelAnimationFrame(e)},[d]);let f=(0,k.useCallback)(e=>{if(!(e instanceof Element))return;let t=e.closest(`[data-walkthrough-reference-id]`)?.dataset.walkthroughReferenceId;return t?i.get(t):void 0},[i]),p=(0,k.useCallback)(e=>{for(let t of e.querySelectorAll(`g.node, g.classGroup, g[data-id], g[id^='classId-']`)){let e=t.dataset.id??Object.keys(r).find(e=>t.id===e||t.id.includes(`-${e}`)||t.id.includes(`-${e}-`)||t.id.endsWith(`-${e}`));if(!e)continue;let n=r[e],a=n?i.get(n):void 0;a&&(t.classList.add(`walkthrough-diagram-node--linked`),t.setAttribute(`role`,`button`),t.setAttribute(`tabindex`,`0`),t.setAttribute(`aria-label`,`${a.label}をコードで開く`),t.dataset.walkthroughReferenceId=a.id)}},[r,i]);return(0,A.jsxs)(`div`,{className:`walkthrough-diagram-shell${n?` has-comment`:``}`,...t?{"data-rvw-navigation-start-line":t.startLine,"data-rvw-navigation-end-line":t.endLine}:{},children:[(0,A.jsxs)(`div`,{className:`walkthrough-diagram-toolbar`,children:[(0,A.jsx)(`span`,{children:`Mermaid diagram`}),(0,A.jsx)(`span`,{children:`nodeを選択して開く · Cmd/Ctrlで反対のペイン`}),t&&(0,A.jsxs)(`button`,{className:`button--quiet walkthrough-diagram-comment`,onPointerDown:e=>{e.button===0&&(e.preventDefault(),s(t))},onClick:e=>{e.detail===0&&s(t)},children:[(0,A.jsx)(l,{}),`図全体へコメント`]})]}),(0,A.jsx)(m,{className:`walkthrough-diagram`,source:e,themePreference:a,renderIdPrefix:`rvwWalkthrough`,errorClassName:`walkthrough-diagram-error`,onRendered:p,onPointerDown:e=>{let t=f(e.target);t&&(e.preventDefault(),e.stopPropagation(),o(t,e.metaKey||e.ctrlKey))},onKeyDown:e=>{if(e.key!==`Enter`&&e.key!==` `)return;let t=f(e.target);t&&(e.preventDefault(),o(t,!1))}}),c&&(0,A.jsx)(`div`,{className:`walkthrough-diagram-comment-composer`,ref:u,children:c})]})}var I=(0,k.createContext)(null);function L({range:e,pending:t,error:n,onCancel:r,onSubmit:a}){let[o,s]=(0,k.useState)(``),c=e.startLine===e.endLine?`L${e.startLine}へコメント`:`L${e.startLine}–${e.endLine}へコメント`;return(0,A.jsx)(i,{body:o,label:c,pending:t,error:n,validationError:void 0,placement:`line`,onBodyChange:s,onCancel:r,onSubmit:()=>a(o)})}var R=({children:e,node:t,...n})=>{let r=(0,k.useContext)(I),i=k.Children.count(e)===1?k.Children.only(e):null;if(!r||!(0,k.isValidElement)(i)||i.props.className!==`language-mermaid`)return(0,A.jsx)(`pre`,{...n,children:e});let a=w(t);return(0,A.jsx)(F,{source:M(i.props.children).trim(),sourceRange:a,commented:!!(a&&r.activeCommentId&&r.placedComments.some(({comment:e,placement:t})=>e.id===r.activeCommentId&&t.range&&t.range.startLine<=a.endLine&&t.range.endLine>=a.startLine)),bindings:r.diagramBindings,references:r.references,themePreference:r.themePreference,onOpenReference:r.onOpenReference,onCommentRange:r.onCommentRange,commentComposer:a&&N(a,r.diagramCommentRange)?(0,A.jsx)(L,{range:a,pending:r.diagramCommentPending,error:r.diagramCommentError,onCancel:r.onCancelDiagramComment,onSubmit:e=>r.onSubmitDiagramComment(a,e)},`${a.startLine}:${a.endLine}`):null})},z=(0,k.memo)(function({body:e,diagramBindings:i,references:a,placedComments:o,activeCommentId:s,selectedRange:c,selectionComposerOpen:l,diagramCommentRange:d,markdownSourceOid:f,themePreference:p,onOpenReference:m,onOpenCommentCodeReference:_,onOpenRepositoryLink:S,onCommentActiveChange:w,onCommentRange:T,diagramCommentPending:j,diagramCommentError:M,onCancelDiagramComment:N,onSubmitDiagramComment:P}){let F=(0,k.useMemo)(()=>o.map(({comment:e,placement:t})=>({id:e.id,range:t.range})),[o]),L=(0,k.useMemo)(()=>new Map(o.map(({comment:e,placement:t})=>[e.id,{comment:e,placement:t}])),[o]),z=(0,k.useCallback)(({node:e,children:t,...n})=>{let r=D(e);return r.length===0?(0,A.jsx)(`div`,{...n,children:t}):(0,A.jsx)(`div`,{className:`markdown-inline-comments`,children:r.map(e=>{let t=L.get(e);return t?(0,A.jsx)(y,{comment:t.comment,variant:`inline`,placement:t.placement,markdownSourceOid:f,themePreference:p,onActiveChange:w,onOpenCodeReference:_,onOpenRepositoryLink:S},e):null})})},[L,f,w,_,S,p]);return(0,A.jsx)(I.Provider,{value:{diagramBindings:i,references:a,placedComments:o,activeCommentId:s,diagramCommentRange:d,themePreference:p,onOpenReference:m,onCommentRange:T,diagramCommentPending:j,diagramCommentError:M,onCancelDiagramComment:N,onSubmitDiagramComment:P},children:(0,A.jsx)(`article`,{className:`walkthrough-markdown`,children:(0,A.jsx)(r,{rehypePlugins:[t,[u,v],[E,{annotations:F,activeCommentId:s,selectedRange:c,composerOpen:l}]],remarkPlugins:[x],urlTransform:e=>e.startsWith(`rvw-ref:`)?e:n(e),components:{div:z,table:O,a:({href:e,children:t,node:n,...r})=>{let i=g(e),o=i?a.get(i):void 0;return o?(0,A.jsx)(h,{reference:o,className:`walkthrough-inline-reference`,onOpen:m,children:t}):(0,A.jsx)(`a`,{...C(n),...r,href:e,children:t})},img:({alt:e,title:t,node:n})=>(0,A.jsx)(b,{alt:e,title:t,sourceAttributes:C(n)}),pre:R},children:e})})})});function B({walkthrough:e,comments:t,activeCommentId:n,navigationTarget:r,onNavigationApplied:a,themePreference:u,onCommentActiveChange:p,onOpenReference:m,onOpenCommentCodeReference:h,onOpenRepositoryLink:g,onDeleted:v}){let b=d(),x=(0,k.useRef)(null),C=(0,k.useRef)(null),w=(0,k.useRef)(a);w.current=a;let[E,D]=(0,k.useState)(!1),[O,M]=(0,k.useState)(null),[N,F]=(0,k.useState)(null),[I,L]=(0,k.useState)(null),[R,B]=(0,k.useState)(``),[V,H]=(0,k.useState)(null),U=(0,k.useRef)(0),W=(0,k.useRef)(null),G=(0,k.useMemo)(()=>new Map(e.references.map(e=>[e.id,e])),[e.references]);(0,k.useLayoutEffect)(()=>{if(!r||C.current===r.requestId)return;let e=r.requestId,t=window.requestAnimationFrame(()=>{let t=x.current;if(!t)return;if(r.line===null){t.scrollIntoView({behavior:`auto`,block:`start`,inline:`nearest`}),C.current=e,w.current(e);return}let n=String(r.line),i=t.querySelector(`[data-rvw-navigation-start-line="${n}"]`)??t.querySelector(`[data-rvw-source-start-line="${n}"]`),a=i?.closest(`details:not([open])`);a&&(a.open=!0),i&&(i.scrollIntoView({behavior:`auto`,block:`center`,inline:`nearest`}),C.current=e,w.current(e))});return()=>window.cancelAnimationFrame(t)},[r]);let ee=(0,k.useCallback)((t,n)=>{U.current+=1;let r=U.current;W.current!==null&&(window.clearTimeout(W.current),W.current=null),H(null),m(e,t,n).then(e=>{r!==U.current||!e||(H(e),W.current=window.setTimeout(()=>{H(null),W.current=null},j))})},[m,e]);(0,k.useEffect)(()=>()=>{U.current+=1,W.current!==null&&window.clearTimeout(W.current)},[]);let K=t.filter(t=>t.target.kind===`walkthrough`&&t.target.walkthroughId===e.id),te=K.reduce((e,t)=>e+t.posts.length,0),q=o({queryKey:[`walkthrough-comment-placements`,e.id,e.body,K.map(e=>`${e.id}:${e.updatedAt}`)],queryFn:async()=>{let t=new URLSearchParams({kind:`walkthrough`,pullRequestId:e.pullRequestId,walkthroughId:e.id});return await Promise.all(K.map(async e=>({comment:e,placement:(await c(`/api/comments/${e.id}/placement?${t.toString()}`)).placement})))},enabled:K.length>0}),J=(0,k.useMemo)(()=>q.data??[],[q.data]),ne=(0,k.useMemo)(()=>J.filter(({placement:e})=>!e.outdated&&e.range!==null),[J]),Y=(0,k.useMemo)(()=>J.filter(({comment:e,placement:t})=>e.target.kind===`walkthrough`&&e.target.startLine===null||t.outdated),[J]),X=f({mutationFn:async({range:t,body:n})=>await c(`/api/comments`,S({pullRequestId:e.pullRequestId,target:{kind:`walkthrough`,walkthroughId:e.id,startLine:t?.startLine??null,endLine:t?.endLine??null},body:n,authorLabel:`You`})),onSuccess:async()=>{window.getSelection()?.removeAllRanges(),B(``),D(!1),M(null),F(null),L(null),await b.invalidateQueries({queryKey:[`comments`]}),await b.invalidateQueries({queryKey:[`change-sequence`]})}}),Z=f({mutationFn:async()=>await c(`/api/pull-requests/${e.pullRequestId}/walkthroughs/${e.id}`,{...S({}),method:`DELETE`}),onSuccess:async()=>{v(e),await Promise.all([b.invalidateQueries({queryKey:[`walkthroughs`]}),b.invalidateQueries({queryKey:[`walkthrough`]}),b.invalidateQueries({queryKey:[`comments`]}),b.invalidateQueries({queryKey:[`change-sequence`]})])}}),Q=K.filter(e=>e.resolvedAt===null).length,re=()=>{let e=K.length===0?`紐づくコメントはありません。`:`紐づくコメント ${K.length}件と投稿 ${te}件も削除されます。`;window.confirm(`このウォークスルーを削除します。\n${e}\nコピー済みの参照は無効になります。\n\nこの操作は元に戻せません。`)&&Z.mutate()},ie=O?O.startLine===O.endLine?`L${O.startLine}`:`L${O.startLine}–${O.endLine}`:null,$=()=>{window.getSelection()?.removeAllRanges(),X.reset(),B(``),M(null),F(null),L(null)},ae=e=>{X.reset(),B(``),D(!1),M(null),F(e),L(`diagram`)},oe=O?(0,A.jsx)(i,{body:R,label:`${ie??`選択範囲`}へコメント`,pending:X.isPending,error:X.error,validationError:void 0,placement:`line`,onBodyChange:B,onCancel:$,onSubmit:()=>X.mutate({range:O,body:R})}):null,se=(0,A.jsx)(z,{body:e.body,diagramBindings:e.diagramBindings,references:G,placedComments:ne,activeCommentId:n,selectedRange:I===`selection`?O:null,selectionComposerOpen:I===`selection`,diagramCommentRange:N,markdownSourceOid:e.sourceOid,themePreference:u,onOpenReference:ee,onOpenCommentCodeReference:h,onOpenRepositoryLink:g,onCommentActiveChange:p,onCommentRange:ae,diagramCommentPending:X.isPending,diagramCommentError:X.error,onCancelDiagramComment:$,onSubmitDiagramComment:(e,t)=>X.mutate({range:e,body:t})});return(0,A.jsxs)(`div`,{className:`walkthrough-viewer`,ref:x,children:[(0,A.jsxs)(`header`,{className:`walkthrough-viewer-header`,children:[(0,A.jsxs)(`div`,{className:`walkthrough-viewer-title`,children:[(0,A.jsx)(`span`,{className:`walkthrough-viewer-icon`,children:(0,A.jsx)(_,{})}),(0,A.jsxs)(`div`,{className:`walkthrough-viewer-heading-copy`,children:[(0,A.jsx)(`span`,{className:`walkthrough-kicker`,children:`Agent-provided walkthrough`}),(0,A.jsx)(`h2`,{title:e.title,children:e.title})]})]}),(0,A.jsxs)(`div`,{className:`walkthrough-viewer-actions`,children:[(0,A.jsxs)(`button`,{className:`comment-icon-button walkthrough-comment-button`,"aria-label":`ウォークスルー全体へコメント`,title:`ウォークスルー全体へコメント`,"aria-pressed":E,onClick:()=>{X.reset(),B(``),M(null),F(null),L(null),D(e=>!e)},children:[(0,A.jsx)(l,{}),Q>0&&(0,A.jsx)(`span`,{children:Q})]}),(0,A.jsx)(`button`,{className:`comment-icon-button walkthrough-delete-button`,"aria-label":`ウォークスルーを削除`,title:`ウォークスルーを削除`,disabled:Z.isPending,onClick:re,children:(0,A.jsx)(P,{})})]}),V&&(0,A.jsx)(`div`,{className:`code-reference-notice walkthrough-reference-notice`,role:`status`,"aria-live":`polite`,children:V})]}),(0,A.jsx)(s,{error:Z.error}),(0,A.jsx)(s,{error:q.error}),(E||Y.length>0)&&(0,A.jsxs)(`div`,{className:`walkthrough-comment-area`,children:[E&&(0,A.jsx)(i,{body:R,label:`ウォークスルー全体へコメント`,pending:X.isPending,error:X.error,validationError:void 0,placement:`file`,onBodyChange:B,onCancel:()=>{X.reset(),B(``),D(!1)},onSubmit:()=>X.mutate({range:null,body:R})}),Y.map(({comment:t,placement:n})=>(0,A.jsx)(y,{comment:t,variant:`inline`,placement:n,markdownSourceOid:e.sourceOid,themePreference:u,onActiveChange:p,onOpenCodeReference:h,onOpenRepositoryLink:g},t.id))]}),(0,A.jsx)(T,{className:`walkthrough-markdown-surface`,selectedRange:O,composerOpen:I===`selection`,onSelection:e=>{if(!e){M(null),L(e=>e===`selection`?null:e);return}X.reset(),B(``),D(!1),M(e),F(null),L(null)},onOpenComposer:()=>L(`selection`),composer:oe,children:se})]})}export{B as WalkthroughViewer};
@@ -1 +0,0 @@
1
- import"./chunk-KEIR6QF5-BICK3FdT.js";import{M as e}from"./mermaid-parser.core-DvZnIth0.js";export{e as createArchitectureServices};
@@ -1 +0,0 @@
1
- import{at as e,ot as t}from"./chunk-I66GZJ75-DRdqLSyH.js";var n=(n,r)=>t.lang.round(e.parse(n)[r]);export{n as t};
@@ -1 +0,0 @@
1
- import{n as e}from"./chunk-Y2CYZVJY-DsF7k-Jl.js";import"./src-B6xuSHsQ.js";import"./chunk-I66GZJ75-DRdqLSyH.js";import"./chunk-NSK5VX7P-CXit1l3q.js";import"./chunk-4I5QYGJK-Bat5hdXD.js";import"./chunk-WRU74C26-DDUvJFNs.js";import"./chunk-7BUUIJ7U-Bb538aSH.js";import"./chunk-UBXNYLIW-i72Hgljr.js";import"./chunk-2GRJ4B5K-CaahxDVT.js";import"./chunk-XXDRQBXY-DqAYeljN.js";import"./chunk-KBJHAD2P-oOV-3e5-.js";import"./chunk-W5SLKNZC-DetAQo7M.js";import"./chunk-QR6OTTB3-DcdCU-01.js";import"./chunk-7Z6QIM7H-CGSwsKhC.js";import{i as t,n,r,t as i}from"./chunk-GF5L2VYU-Cuca3bAY.js";import"./mermaid.core-hykiOF_o.js";var a={parser:n,get db(){return new i},renderer:r,styles:t,init:e(e=>{e.class||={},e.class.arrowMarkerAbsolute=e.arrowMarkerAbsolute},`init`)};export{a as diagram};
@@ -1 +0,0 @@
1
- import{n as e}from"./chunk-Y2CYZVJY-DsF7k-Jl.js";import"./src-B6xuSHsQ.js";import"./chunk-I66GZJ75-DRdqLSyH.js";import"./chunk-NSK5VX7P-CXit1l3q.js";import"./chunk-4I5QYGJK-Bat5hdXD.js";import"./chunk-WRU74C26-DDUvJFNs.js";import"./chunk-7BUUIJ7U-Bb538aSH.js";import"./chunk-UBXNYLIW-i72Hgljr.js";import"./chunk-2GRJ4B5K-CaahxDVT.js";import"./chunk-XXDRQBXY-DqAYeljN.js";import"./chunk-KBJHAD2P-oOV-3e5-.js";import"./chunk-W5SLKNZC-DetAQo7M.js";import"./chunk-QR6OTTB3-DcdCU-01.js";import"./chunk-7Z6QIM7H-CGSwsKhC.js";import{i as t,n,r,t as i}from"./chunk-GF5L2VYU-Cuca3bAY.js";import"./mermaid.core-hykiOF_o.js";var a={parser:n,get db(){return new i},renderer:r,styles:t,init:e(e=>{e.class||={},e.class.arrowMarkerAbsolute=e.arrowMarkerAbsolute},`init`)};export{a as diagram};
@@ -1 +0,0 @@
1
- import"./chunk-KEIR6QF5-BICK3FdT.js";import{O as e}from"./mermaid-parser.core-DvZnIth0.js";export{e as createEventModelingServices};
@@ -1 +0,0 @@
1
- import"./src-B6xuSHsQ.js";import"./chunk-I66GZJ75-DRdqLSyH.js";import"./chunk-NSK5VX7P-CXit1l3q.js";import"./chunk-4I5QYGJK-Bat5hdXD.js";import"./chunk-WRU74C26-DDUvJFNs.js";import"./chunk-7BUUIJ7U-Bb538aSH.js";import"./chunk-UBXNYLIW-i72Hgljr.js";import"./chunk-2GRJ4B5K-CaahxDVT.js";import"./chunk-XXDRQBXY-DqAYeljN.js";import"./chunk-KBJHAD2P-oOV-3e5-.js";import"./chunk-W5SLKNZC-DetAQo7M.js";import"./chunk-QR6OTTB3-DcdCU-01.js";import"./chunk-7Z6QIM7H-CGSwsKhC.js";import{n as e}from"./chunk-JQJVKLGR-8xhLkhs2.js";import"./mermaid.core-hykiOF_o.js";export{e as diagram};