diffprism 0.13.6 → 0.13.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/bin.js CHANGED
@@ -138,6 +138,17 @@ The tool blocks until the user submits their review in the browser. When it retu
138
138
  If the \`mcp__diffprism__open_review\` tool is not available:
139
139
  - Tell the user: "The DiffPrism MCP server isn't configured. Run \`npx diffprism setup\` to set it up, then restart Claude Code."
140
140
 
141
+ ## Watch Mode: Polling for Review Feedback
142
+
143
+ When \`diffprism watch\` is active (detected via \`.diffprism/watch.json\`), the developer can submit reviews at any time in the browser. Since there is no push notification, **you must poll for feedback** to close the loop.
144
+
145
+ **After pushing context to a watch session**, call \`mcp__diffprism__get_review_result\` to check for pending feedback:
146
+ - **Between tasks** \u2014 Before starting a new piece of work, check for feedback.
147
+ - **After making changes** \u2014 After addressing requested changes, push updated reasoning via \`update_review_context\`, then check again shortly after.
148
+ - **When the user mentions review feedback** \u2014 If the user says they submitted a review or left comments, check immediately.
149
+
150
+ Do not poll in a tight loop. Check at natural breakpoints in your workflow (e.g., after finishing a subtask, before committing, before moving to the next file).
151
+
141
152
  ## Behavior Rules
142
153
 
143
154
  - When invoked via \`/review\`, always open a review regardless of the \`reviewTrigger\` setting.
@@ -236,6 +247,34 @@ function setupSkill(gitRoot, global, force) {
236
247
  fs.writeFileSync(filePath, skillContent);
237
248
  return { action, filePath };
238
249
  }
250
+ function cleanDiffprismHooks(gitRoot) {
251
+ const filePath = path.join(gitRoot, ".claude", "settings.json");
252
+ const existing = readJsonFile(filePath);
253
+ const hooks = existing.hooks;
254
+ if (!hooks) return { removed: 0 };
255
+ const stopHooks = hooks.Stop;
256
+ if (!Array.isArray(stopHooks) || stopHooks.length === 0) {
257
+ return { removed: 0 };
258
+ }
259
+ const filtered = stopHooks.filter((entry) => {
260
+ const innerHooks = entry.hooks;
261
+ if (!Array.isArray(innerHooks)) return true;
262
+ return !innerHooks.some((h) => {
263
+ const cmd = h.command;
264
+ return typeof cmd === "string" && cmd.includes("diffprism") && cmd.includes("notify-stop");
265
+ });
266
+ });
267
+ const removed = stopHooks.length - filtered.length;
268
+ if (removed > 0) {
269
+ if (filtered.length > 0) {
270
+ hooks.Stop = filtered;
271
+ } else {
272
+ delete hooks.Stop;
273
+ }
274
+ writeJsonFile(filePath, { ...existing, hooks });
275
+ }
276
+ return { removed };
277
+ }
239
278
  function setupStopHook(gitRoot, force) {
240
279
  const filePath = path.join(gitRoot, ".claude", "settings.json");
241
280
  const existing = readJsonFile(filePath);
@@ -325,6 +364,10 @@ async function setup(flags) {
325
364
  result[mcp.action === "skipped" ? "skipped" : mcp.action === "created" ? "created" : "updated"].push(mcp.filePath);
326
365
  const settings = setupClaudeSettings(gitRoot, force);
327
366
  result[settings.action === "skipped" ? "skipped" : settings.action === "created" ? "created" : "updated"].push(settings.filePath);
367
+ const cleaned = cleanDiffprismHooks(gitRoot);
368
+ if (cleaned.removed > 0) {
369
+ console.log(` Cleaned ${cleaned.removed} stale hook(s)`);
370
+ }
328
371
  const hook = setupStopHook(gitRoot, force);
329
372
  result[hook.action === "skipped" ? "skipped" : hook.action === "created" ? "created" : "updated"].push(hook.filePath);
330
373
  const skill = setupSkill(gitRoot, global, force);
@@ -420,7 +463,7 @@ async function notifyStop() {
420
463
 
421
464
  // cli/src/index.ts
422
465
  var program = new Command();
423
- program.name("diffprism").description("Local-first code review tool for agent-generated changes").version(true ? "0.13.6" : "0.0.0-dev");
466
+ program.name("diffprism").description("Local-first code review tool for agent-generated changes").version(true ? "0.13.8" : "0.0.0-dev");
424
467
  program.command("review [ref]").description("Open a browser-based diff review").option("--staged", "Review staged changes").option("--unstaged", "Review unstaged changes").option("-t, --title <title>", "Review title").option("--dev", "Use Vite dev server with HMR instead of static files").action(review);
425
468
  program.command("watch [ref]").description("Start a persistent diff watcher with live-updating browser UI").option("--staged", "Watch staged changes").option("--unstaged", "Watch unstaged changes").option("-t, --title <title>", "Review title").option("--interval <ms>", "Poll interval in milliseconds (default: 1000)").option("--dev", "Use Vite dev server with HMR instead of static files").action(watch);
426
469
  program.command("notify-stop").description("Signal the watch server to refresh (used by Claude Code hooks)").action(notifyStop);
@@ -14,7 +14,7 @@ import { z } from "zod";
14
14
  async function startMcpServer() {
15
15
  const server = new McpServer({
16
16
  name: "diffprism",
17
- version: true ? "0.13.6" : "0.0.0-dev"
17
+ version: true ? "0.13.8" : "0.0.0-dev"
18
18
  });
19
19
  server.tool(
20
20
  "open_review",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "diffprism",
3
- "version": "0.13.6",
3
+ "version": "0.13.8",
4
4
  "type": "module",
5
5
  "description": "Local-first code review tool for agent-generated code changes",
6
6
  "bin": {