@diegopetrucci/pi-annotate-git-diff 0.1.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/.pi-fleet-tested-version +1 -0
- package/README.md +43 -0
- package/clipboard.ts +143 -0
- package/git.ts +943 -0
- package/glimpseui.d.ts +89 -0
- package/index.ts +412 -0
- package/package.json +50 -0
- package/prompt.ts +65 -0
- package/quiet-glimpse.ts +156 -0
- package/types.ts +202 -0
- package/ui.ts +71 -0
- package/watch.ts +104 -0
- package/web/app.js +2381 -0
- package/web/index.html +913 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
0.78.0
|
package/README.md
ADDED
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
# annotate-git-diff
|
|
2
|
+
|
|
3
|
+
A standalone pi extension that adds `/annotate-git-diff`, a native Glimpse window for reviewing git changes and sending structured feedback back to the current editor buffer.
|
|
4
|
+
|
|
5
|
+
## Attribution
|
|
6
|
+
|
|
7
|
+
This extension was ported from the first-party The Last Harness implementation. It adapts the MIT-licensed `@ryan_nookpi/pi-extension-diff-review` implementation from the `Jonghakseo/pi-extension` monorepo and preserves its original inspiration credit to [badlogic/pi-diff-review](https://github.com/badlogic/pi-diff-review).
|
|
8
|
+
|
|
9
|
+
## Install
|
|
10
|
+
|
|
11
|
+
```bash
|
|
12
|
+
pi install npm:@diegopetrucci/pi-annotate-git-diff
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
Then reload pi:
|
|
16
|
+
|
|
17
|
+
```text
|
|
18
|
+
/reload
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
## Usage
|
|
22
|
+
|
|
23
|
+
Run `/annotate-git-diff` inside a git repository. The command opens a native review window with:
|
|
24
|
+
|
|
25
|
+
- Monaco-based diff viewing,
|
|
26
|
+
- branch diff, per-commit including working tree, and all-files scopes,
|
|
27
|
+
- inline, file-level, and overall review comments,
|
|
28
|
+
- submit-to-editor feedback prompt insertion.
|
|
29
|
+
|
|
30
|
+
Submitting feedback does not auto-apply code changes. The extension appends a structured prompt to the current editor buffer so you can send that feedback back to the active agent.
|
|
31
|
+
|
|
32
|
+
## Requirements
|
|
33
|
+
|
|
34
|
+
- Run inside a git repository.
|
|
35
|
+
- Local desktop support for opening a native [Glimpse](https://github.com/mariozechner/glimpse) window.
|
|
36
|
+
- Packaged Monaco and Tailwind assets from this npm package.
|
|
37
|
+
- POSIX shell utilities (`bash`, `mktemp`, `base64`, and `tr`) for some git snapshot/binary-file paths.
|
|
38
|
+
|
|
39
|
+
## Troubleshooting
|
|
40
|
+
|
|
41
|
+
- `Review failed: Not inside a git repository.` → change into a git repo and rerun `/annotate-git-diff`.
|
|
42
|
+
- `No reviewable files found.` → make or fetch reviewable changes, then rerun.
|
|
43
|
+
- `Review failed: Glimpse host not found ...` → the native window runtime is unavailable; reinstall/update the package and rerun from a machine/session that can open native windows.
|
package/clipboard.ts
ADDED
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
import { spawnSync } from "node:child_process";
|
|
2
|
+
|
|
3
|
+
const MAX_CLIPBOARD_BYTES = 16 * 1024 * 1024;
|
|
4
|
+
|
|
5
|
+
type ClipboardPlatform = NodeJS.Platform;
|
|
6
|
+
|
|
7
|
+
interface ClipboardCommand {
|
|
8
|
+
command: string;
|
|
9
|
+
args: string[];
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
export interface ClipboardCommandResult {
|
|
13
|
+
status: number | null;
|
|
14
|
+
signal?: NodeJS.Signals | null;
|
|
15
|
+
stdout?: string | Buffer;
|
|
16
|
+
stderr?: string | Buffer;
|
|
17
|
+
error?: Error;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
export type ClipboardCommandRunner = (
|
|
21
|
+
command: string,
|
|
22
|
+
args: string[],
|
|
23
|
+
options: { encoding: "utf8"; maxBuffer: number; input?: string },
|
|
24
|
+
) => ClipboardCommandResult;
|
|
25
|
+
|
|
26
|
+
interface ClipboardOptions {
|
|
27
|
+
platform?: ClipboardPlatform;
|
|
28
|
+
runner?: ClipboardCommandRunner;
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
const defaultRunner: ClipboardCommandRunner = (command, args, options) => spawnSync(command, args, options);
|
|
32
|
+
|
|
33
|
+
function clipboardReadCommands(platform: ClipboardPlatform): ClipboardCommand[] {
|
|
34
|
+
switch (platform) {
|
|
35
|
+
case "darwin":
|
|
36
|
+
return [{ command: "pbpaste", args: [] }];
|
|
37
|
+
case "win32":
|
|
38
|
+
return [
|
|
39
|
+
{
|
|
40
|
+
command: "powershell.exe",
|
|
41
|
+
args: [
|
|
42
|
+
"-NoProfile",
|
|
43
|
+
"-NonInteractive",
|
|
44
|
+
"-Command",
|
|
45
|
+
"[Console]::OutputEncoding = [System.Text.Encoding]::UTF8; Get-Clipboard -Raw",
|
|
46
|
+
],
|
|
47
|
+
},
|
|
48
|
+
];
|
|
49
|
+
case "linux":
|
|
50
|
+
return [
|
|
51
|
+
{ command: "wl-paste", args: ["--type", "text/plain"] },
|
|
52
|
+
{ command: "xclip", args: ["-selection", "clipboard", "-out"] },
|
|
53
|
+
{ command: "xsel", args: ["--clipboard", "--output"] },
|
|
54
|
+
];
|
|
55
|
+
default:
|
|
56
|
+
return [];
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
function clipboardWriteCommands(platform: ClipboardPlatform): ClipboardCommand[] {
|
|
61
|
+
switch (platform) {
|
|
62
|
+
case "darwin":
|
|
63
|
+
return [{ command: "pbcopy", args: [] }];
|
|
64
|
+
case "win32":
|
|
65
|
+
return [
|
|
66
|
+
{
|
|
67
|
+
command: "powershell.exe",
|
|
68
|
+
args: [
|
|
69
|
+
"-NoProfile",
|
|
70
|
+
"-NonInteractive",
|
|
71
|
+
"-Command",
|
|
72
|
+
"[Console]::InputEncoding = [System.Text.Encoding]::UTF8; $text = [Console]::In.ReadToEnd(); Set-Clipboard -Value $text",
|
|
73
|
+
],
|
|
74
|
+
},
|
|
75
|
+
];
|
|
76
|
+
case "linux":
|
|
77
|
+
return [
|
|
78
|
+
{ command: "wl-copy", args: ["--type", "text/plain"] },
|
|
79
|
+
{ command: "xclip", args: ["-selection", "clipboard", "-in"] },
|
|
80
|
+
{ command: "xsel", args: ["--clipboard", "--input"] },
|
|
81
|
+
];
|
|
82
|
+
default:
|
|
83
|
+
return [];
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
function commandLabel(command: ClipboardCommand): string {
|
|
88
|
+
return [command.command, ...command.args].join(" ");
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
function outputToString(value: string | Buffer | undefined): string {
|
|
92
|
+
if (value == null) return "";
|
|
93
|
+
return typeof value === "string" ? value : value.toString("utf8");
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
function runClipboardCommand(command: ClipboardCommand, runner: ClipboardCommandRunner, input?: string): string {
|
|
97
|
+
const result = runner(command.command, command.args, {
|
|
98
|
+
encoding: "utf8",
|
|
99
|
+
maxBuffer: MAX_CLIPBOARD_BYTES,
|
|
100
|
+
...(input == null ? {} : { input }),
|
|
101
|
+
});
|
|
102
|
+
if (result.error) throw result.error;
|
|
103
|
+
if (result.status !== 0) {
|
|
104
|
+
const stderr = outputToString(result.stderr).trim();
|
|
105
|
+
const status = result.status == null ? result.signal || "unknown" : result.status;
|
|
106
|
+
throw new Error(`${commandLabel(command)} exited with ${status}${stderr ? `: ${stderr}` : ""}`);
|
|
107
|
+
}
|
|
108
|
+
return outputToString(result.stdout);
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
function runFirstAvailable(commands: ClipboardCommand[], runner: ClipboardCommandRunner, input?: string): string {
|
|
112
|
+
if (commands.length === 0) {
|
|
113
|
+
throw new Error(`System clipboard is unsupported on ${process.platform}.`);
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
const errors: string[] = [];
|
|
117
|
+
for (const command of commands) {
|
|
118
|
+
try {
|
|
119
|
+
return runClipboardCommand(command, runner, input);
|
|
120
|
+
} catch (error) {
|
|
121
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
122
|
+
errors.push(`${commandLabel(command)}: ${message}`);
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
throw new Error(`No system clipboard command succeeded. ${errors.join("; ")}`);
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
export function readSystemClipboard(options: ClipboardOptions = {}): string {
|
|
129
|
+
const platform = options.platform ?? process.platform;
|
|
130
|
+
const runner = options.runner ?? defaultRunner;
|
|
131
|
+
return runFirstAvailable(clipboardReadCommands(platform), runner);
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
export function writeSystemClipboard(text: string, options: ClipboardOptions = {}): void {
|
|
135
|
+
const platform = options.platform ?? process.platform;
|
|
136
|
+
const runner = options.runner ?? defaultRunner;
|
|
137
|
+
runFirstAvailable(clipboardWriteCommands(platform), runner, text);
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
export const __testing = {
|
|
141
|
+
clipboardReadCommands,
|
|
142
|
+
clipboardWriteCommands,
|
|
143
|
+
};
|