editprompt 1.3.0 → 1.4.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +33 -0
- package/dist/index.js +147 -74
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -202,6 +202,39 @@ This sends the content to the target pane (or clipboard) while keeping your edit
|
|
|
202
202
|
|
|
203
203
|
For Neovim users, we recommend using [editprompt.nvim](https://github.com/eetann/editprompt.nvim) for easy setup. For manual configuration, see [docs/neovim.md](docs/neovim.md).
|
|
204
204
|
|
|
205
|
+
### Key Sending (press)
|
|
206
|
+
|
|
207
|
+
Send individual key inputs to the target pane without leaving your editor. Useful for responding to AI agent selection prompts (e.g., choosing option 1, 2, 3, 4) without switching panes.
|
|
208
|
+
|
|
209
|
+
```bash
|
|
210
|
+
# Send a character key
|
|
211
|
+
editprompt press -- 1
|
|
212
|
+
|
|
213
|
+
# Send special keys (tmux format)
|
|
214
|
+
editprompt press -- Tab
|
|
215
|
+
editprompt press -- Up
|
|
216
|
+
editprompt press -- C-m # Enter
|
|
217
|
+
editprompt press -- C-c # Ctrl+C
|
|
218
|
+
|
|
219
|
+
# Send with delay
|
|
220
|
+
editprompt press --delay 500 -- Tab
|
|
221
|
+
```
|
|
222
|
+
|
|
223
|
+
**Key differences from `input`:**
|
|
224
|
+
|
|
225
|
+
- No Enter key is automatically appended
|
|
226
|
+
- Focus stays on the editor pane (no pane switching)
|
|
227
|
+
- Designed for single key inputs, not text content
|
|
228
|
+
|
|
229
|
+
**Key notation** depends on your multiplexer:
|
|
230
|
+
|
|
231
|
+
| Key | tmux | WezTerm |
|
|
232
|
+
| ------------- | ------------- | ------------------- |
|
|
233
|
+
| Enter | `C-m` | `\r` |
|
|
234
|
+
| Tab | `Tab` | `\t` |
|
|
235
|
+
| Escape | `Escape` | `\x1b` |
|
|
236
|
+
| Arrow Up/Down | `Up` / `Down` | `\x1b[A` / `\x1b[B` |
|
|
237
|
+
|
|
205
238
|
### Quote Workflow Setup
|
|
206
239
|
|
|
207
240
|
#### Collecting Quotes in tmux Copy Mode
|
package/dist/index.js
CHANGED
|
@@ -7,6 +7,7 @@ import { promisify } from "node:util";
|
|
|
7
7
|
import Conf from "conf";
|
|
8
8
|
import clipboardy from "clipboardy";
|
|
9
9
|
import { mkdir, readFile, writeFile } from "node:fs/promises";
|
|
10
|
+
import { randomBytes } from "node:crypto";
|
|
10
11
|
import { tmpdir } from "node:os";
|
|
11
12
|
import { join } from "node:path";
|
|
12
13
|
|
|
@@ -71,12 +72,12 @@ function setupLogger(options = {}) {
|
|
|
71
72
|
|
|
72
73
|
//#endregion
|
|
73
74
|
//#region package.json
|
|
74
|
-
var version = "1.
|
|
75
|
+
var version = "1.4.1";
|
|
75
76
|
|
|
76
77
|
//#endregion
|
|
77
78
|
//#region src/modules/tmux.ts
|
|
78
79
|
const execAsync$1 = promisify(exec);
|
|
79
|
-
const logger$
|
|
80
|
+
const logger$11 = getLogger(["editprompt", "tmux"]);
|
|
80
81
|
async function getCurrentPaneId$1() {
|
|
81
82
|
const envPaneId = process.env.TMUX_PANE?.trim();
|
|
82
83
|
if (envPaneId) return envPaneId;
|
|
@@ -157,7 +158,7 @@ async function sendKeyToTmuxPane(paneId, key, delay = 1e3) {
|
|
|
157
158
|
async function inputToTmuxPane(paneId, content) {
|
|
158
159
|
await execAsync$1(`tmux if-shell -t '${paneId}' '[ "#{pane_in_mode}" = "1" ]' "copy-mode -q -t '${paneId}'"`);
|
|
159
160
|
await execAsync$1(`tmux send-keys -t '${paneId}' -- '${content.replace(/'/g, "'\\''")}'`);
|
|
160
|
-
logger$
|
|
161
|
+
logger$11.debug("Content sent to tmux pane: {paneId}", { paneId });
|
|
161
162
|
}
|
|
162
163
|
|
|
163
164
|
//#endregion
|
|
@@ -167,7 +168,7 @@ const conf = new Conf({ projectName });
|
|
|
167
168
|
|
|
168
169
|
//#endregion
|
|
169
170
|
//#region src/modules/wezterm.ts
|
|
170
|
-
const logger$
|
|
171
|
+
const logger$10 = getLogger(["editprompt", "wezterm"]);
|
|
171
172
|
const execAsync = promisify(exec);
|
|
172
173
|
async function getCurrentPaneId() {
|
|
173
174
|
try {
|
|
@@ -175,26 +176,26 @@ async function getCurrentPaneId() {
|
|
|
175
176
|
const activePane = JSON.parse(stdout).find((pane) => pane.is_active === true);
|
|
176
177
|
return String(activePane?.pane_id);
|
|
177
178
|
} catch (error) {
|
|
178
|
-
logger$
|
|
179
|
+
logger$10.debug("getCurrentPaneId failed: {error}", { error });
|
|
179
180
|
return "";
|
|
180
181
|
}
|
|
181
182
|
}
|
|
182
183
|
async function checkPaneExists(paneId) {
|
|
183
184
|
try {
|
|
184
185
|
const { stdout } = await execAsync("wezterm cli list --format json");
|
|
185
|
-
logger$
|
|
186
|
+
logger$10.debug("wezterm cli list output: {stdout}", { stdout });
|
|
186
187
|
return JSON.parse(stdout).some((pane) => String(pane.pane_id) === paneId);
|
|
187
188
|
} catch (error) {
|
|
188
|
-
logger$
|
|
189
|
+
logger$10.debug("checkPaneExists failed: {error}", { error });
|
|
189
190
|
return false;
|
|
190
191
|
}
|
|
191
192
|
}
|
|
192
193
|
async function saveEditorPaneId(targetPaneId, editorPaneId) {
|
|
193
|
-
logger$
|
|
194
|
+
logger$10.debug("Saving editor pane ID to conf key: wezterm.targetPane.pane_{targetPaneId}", { targetPaneId });
|
|
194
195
|
try {
|
|
195
196
|
conf.set(`wezterm.targetPane.pane_${targetPaneId}`, { editorPaneId });
|
|
196
197
|
} catch (error) {
|
|
197
|
-
logger$
|
|
198
|
+
logger$10.debug("saveEditorPaneId failed: {error}", { error });
|
|
198
199
|
}
|
|
199
200
|
}
|
|
200
201
|
async function getEditorPaneId(targetPaneId) {
|
|
@@ -203,7 +204,7 @@ async function getEditorPaneId(targetPaneId) {
|
|
|
203
204
|
if (typeof data === "object" && data !== null && "editorPaneId" in data) return String(data.editorPaneId);
|
|
204
205
|
return "";
|
|
205
206
|
} catch (error) {
|
|
206
|
-
logger$
|
|
207
|
+
logger$10.debug("getEditorPaneId failed: {error}", { error });
|
|
207
208
|
return "";
|
|
208
209
|
}
|
|
209
210
|
}
|
|
@@ -213,7 +214,7 @@ async function clearEditorPaneId(targetPaneId) {
|
|
|
213
214
|
conf.delete(`wezterm.targetPane.pane_${targetPaneId}`);
|
|
214
215
|
if (editorPaneId) conf.delete(`wezterm.editorPane.pane_${editorPaneId}`);
|
|
215
216
|
} catch (error) {
|
|
216
|
-
logger$
|
|
217
|
+
logger$10.debug("clearEditorPaneId failed: {error}", { error });
|
|
217
218
|
}
|
|
218
219
|
}
|
|
219
220
|
async function focusPane(paneId) {
|
|
@@ -225,7 +226,7 @@ async function markAsEditorPane(editorPaneId, targetPaneIds) {
|
|
|
225
226
|
conf.set(`wezterm.editorPane.pane_${editorPaneId}`, { targetPaneIds: uniqueTargetPaneIds });
|
|
226
227
|
for (const targetPaneId of uniqueTargetPaneIds) await saveEditorPaneId(targetPaneId, editorPaneId);
|
|
227
228
|
} catch (error) {
|
|
228
|
-
logger$
|
|
229
|
+
logger$10.debug("markAsEditorPane failed: {error}", { error });
|
|
229
230
|
}
|
|
230
231
|
}
|
|
231
232
|
async function getTargetPaneIds(editorPaneId) {
|
|
@@ -237,7 +238,7 @@ async function getTargetPaneIds(editorPaneId) {
|
|
|
237
238
|
}
|
|
238
239
|
return [];
|
|
239
240
|
} catch (error) {
|
|
240
|
-
logger$
|
|
241
|
+
logger$10.debug("getTargetPaneIds failed: {error}", { error });
|
|
241
242
|
return [];
|
|
242
243
|
}
|
|
243
244
|
}
|
|
@@ -245,7 +246,7 @@ function isEditorPaneFromConf(paneId) {
|
|
|
245
246
|
try {
|
|
246
247
|
return conf.has(`wezterm.editorPane.pane_${paneId}`);
|
|
247
248
|
} catch (error) {
|
|
248
|
-
logger$
|
|
249
|
+
logger$10.debug("isEditorPaneFromConf failed: {error}", { error });
|
|
249
250
|
return false;
|
|
250
251
|
}
|
|
251
252
|
}
|
|
@@ -263,7 +264,7 @@ async function appendToQuoteText(paneId, content) {
|
|
|
263
264
|
} else newData = { quote_text: content };
|
|
264
265
|
conf.set(`wezterm.targetPane.pane_${paneId}`, newData);
|
|
265
266
|
} catch (error) {
|
|
266
|
-
logger$
|
|
267
|
+
logger$10.debug("appendToQuoteText failed: {error}", { error });
|
|
267
268
|
}
|
|
268
269
|
}
|
|
269
270
|
async function getQuoteText(paneId) {
|
|
@@ -272,7 +273,7 @@ async function getQuoteText(paneId) {
|
|
|
272
273
|
if (typeof data === "object" && data !== null && "quote_text" in data) return String(data.quote_text);
|
|
273
274
|
return "";
|
|
274
275
|
} catch (error) {
|
|
275
|
-
logger$
|
|
276
|
+
logger$10.debug("getQuoteText failed: {error}", { error });
|
|
276
277
|
return "";
|
|
277
278
|
}
|
|
278
279
|
}
|
|
@@ -281,7 +282,7 @@ async function clearQuoteText(paneId) {
|
|
|
281
282
|
const key = `wezterm.targetPane.pane_${paneId}.quote_text`;
|
|
282
283
|
if (conf.has(key)) conf.delete(key);
|
|
283
284
|
} catch (error) {
|
|
284
|
-
logger$
|
|
285
|
+
logger$10.debug("clearQuoteText failed: {error}", { error });
|
|
285
286
|
}
|
|
286
287
|
}
|
|
287
288
|
async function sendKeyToWeztermPane(paneId, key, delay = 1e3) {
|
|
@@ -290,7 +291,7 @@ async function sendKeyToWeztermPane(paneId, key, delay = 1e3) {
|
|
|
290
291
|
}
|
|
291
292
|
async function inputToWeztermPane(paneId, content) {
|
|
292
293
|
await execAsync(`wezterm cli send-text --no-paste --pane-id '${paneId}' -- '${content.replace(/'/g, "'\\''")}'`);
|
|
293
|
-
logger$
|
|
294
|
+
logger$10.debug("Content sent to wezterm pane: {paneId}", { paneId });
|
|
294
295
|
}
|
|
295
296
|
|
|
296
297
|
//#endregion
|
|
@@ -432,7 +433,7 @@ function processQuoteText(text, options) {
|
|
|
432
433
|
|
|
433
434
|
//#endregion
|
|
434
435
|
//#region src/modes/common.ts
|
|
435
|
-
const logger$
|
|
436
|
+
const logger$9 = getLogger(["editprompt", "delivery"]);
|
|
436
437
|
function isMuxType(value) {
|
|
437
438
|
return value === "tmux" || value === "wezterm";
|
|
438
439
|
}
|
|
@@ -460,9 +461,9 @@ async function handleContentDelivery(content, mux, targetPanes) {
|
|
|
460
461
|
if (targetPanes.length === 0) {
|
|
461
462
|
try {
|
|
462
463
|
await copyToClipboard(content);
|
|
463
|
-
logger$
|
|
464
|
+
logger$9.info("Content copied to clipboard.");
|
|
464
465
|
} catch (error) {
|
|
465
|
-
logger$
|
|
466
|
+
logger$9.warn(`Failed to copy to clipboard: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
466
467
|
}
|
|
467
468
|
return {
|
|
468
469
|
successCount: 0,
|
|
@@ -480,7 +481,7 @@ async function handleContentDelivery(content, mux, targetPanes) {
|
|
|
480
481
|
success: true
|
|
481
482
|
});
|
|
482
483
|
} catch (error) {
|
|
483
|
-
logger$
|
|
484
|
+
logger$9.warn(`Failed to send to pane ${targetPane}: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
484
485
|
results.push({
|
|
485
486
|
pane: targetPane,
|
|
486
487
|
success: false
|
|
@@ -490,13 +491,13 @@ async function handleContentDelivery(content, mux, targetPanes) {
|
|
|
490
491
|
const failedPanes = results.filter((r) => !r.success).map((r) => r.pane);
|
|
491
492
|
const allSuccess = successCount === targetPanes.length;
|
|
492
493
|
const allFailed = successCount === 0;
|
|
493
|
-
if (allSuccess) logger$
|
|
494
|
+
if (allSuccess) logger$9.info("Content sent successfully to all panes!");
|
|
494
495
|
else if (allFailed) {
|
|
495
|
-
logger$
|
|
496
|
-
logger$
|
|
496
|
+
logger$9.error("All target panes failed to receive content.");
|
|
497
|
+
logger$9.info("Falling back to clipboard...");
|
|
497
498
|
await copyToClipboard(content);
|
|
498
|
-
logger$
|
|
499
|
-
} else logger$
|
|
499
|
+
logger$9.info("Content copied to clipboard.");
|
|
500
|
+
} else logger$9.warn(`Content sent to ${successCount}/${targetPanes.length} panes. Failed panes: ${failedPanes.join(", ")}`);
|
|
500
501
|
return {
|
|
501
502
|
successCount,
|
|
502
503
|
totalCount: targetPanes.length,
|
|
@@ -508,7 +509,7 @@ async function handleContentDelivery(content, mux, targetPanes) {
|
|
|
508
509
|
|
|
509
510
|
//#endregion
|
|
510
511
|
//#region src/modes/args.ts
|
|
511
|
-
const logger$
|
|
512
|
+
const logger$8 = getLogger(["editprompt"]);
|
|
512
513
|
const ARG_MUX = {
|
|
513
514
|
short: "m",
|
|
514
515
|
description: "Multiplexer type (tmux or wezterm, default: tmux)",
|
|
@@ -560,14 +561,14 @@ const ARG_VERBOSE = {
|
|
|
560
561
|
function validateMux(value) {
|
|
561
562
|
const muxValue = value || "tmux";
|
|
562
563
|
if (!isMuxType(muxValue)) {
|
|
563
|
-
logger$
|
|
564
|
+
logger$8.error(`Invalid multiplexer type '${muxValue}'. Supported values: ${SUPPORTED_MUXES.join(", ")}`);
|
|
564
565
|
process.exit(1);
|
|
565
566
|
}
|
|
566
567
|
return muxValue;
|
|
567
568
|
}
|
|
568
569
|
function validateTargetPane(value, commandName) {
|
|
569
570
|
if (!value || typeof value !== "string") {
|
|
570
|
-
logger$
|
|
571
|
+
logger$8.error(`--target-pane is required for ${commandName} command`);
|
|
571
572
|
process.exit(1);
|
|
572
573
|
}
|
|
573
574
|
return value;
|
|
@@ -580,7 +581,7 @@ function normalizeTargetPanes(value) {
|
|
|
580
581
|
|
|
581
582
|
//#endregion
|
|
582
583
|
//#region src/modes/collect.ts
|
|
583
|
-
const logger$
|
|
584
|
+
const logger$7 = getLogger(["editprompt", "collect"]);
|
|
584
585
|
const SUPPORTED_OUTPUTS = ["buffer", "stdout"];
|
|
585
586
|
async function readStdin() {
|
|
586
587
|
return new Promise((resolve, reject) => {
|
|
@@ -604,7 +605,7 @@ function normalizeCollectOutputs(value) {
|
|
|
604
605
|
const uniqueOutputs = [...new Set(outputs)];
|
|
605
606
|
const invalid = uniqueOutputs.filter((v) => !SUPPORTED_OUTPUTS.includes(v));
|
|
606
607
|
if (invalid.length > 0) {
|
|
607
|
-
logger$
|
|
608
|
+
logger$7.error(`Invalid output(s) '${invalid.join(", ")}'. Supported values: ${SUPPORTED_OUTPUTS.join(", ")}`);
|
|
608
609
|
process.exit(1);
|
|
609
610
|
}
|
|
610
611
|
return uniqueOutputs;
|
|
@@ -620,7 +621,7 @@ async function runCollectMode(mux, targetPaneId, rawContent, outputs = ["buffer"
|
|
|
620
621
|
else if (mux === "wezterm") await appendToQuoteText(targetPaneId, processedText);
|
|
621
622
|
} else if (output === "stdout") process.stdout.write(processedText);
|
|
622
623
|
} catch (error) {
|
|
623
|
-
logger$
|
|
624
|
+
logger$7.error(`${error instanceof Error ? error.message : "Unknown error"}`);
|
|
624
625
|
process.exit(1);
|
|
625
626
|
}
|
|
626
627
|
}
|
|
@@ -650,7 +651,7 @@ const collectCommand = define({
|
|
|
650
651
|
if (mux === "wezterm") {
|
|
651
652
|
rawContent = extractRawContent(ctx.rest, ctx.positionals);
|
|
652
653
|
if (rawContent === void 0) {
|
|
653
|
-
logger$
|
|
654
|
+
logger$7.error("Text content is required for collect mode with wezterm. Use: editprompt collect --mux wezterm --target-pane <id> -- \"<text>\"");
|
|
654
655
|
process.exit(1);
|
|
655
656
|
}
|
|
656
657
|
}
|
|
@@ -677,7 +678,7 @@ function readSendConfig() {
|
|
|
677
678
|
|
|
678
679
|
//#endregion
|
|
679
680
|
//#region src/modes/dump.ts
|
|
680
|
-
const logger$
|
|
681
|
+
const logger$6 = getLogger(["editprompt", "dump"]);
|
|
681
682
|
async function runDumpMode() {
|
|
682
683
|
try {
|
|
683
684
|
const config = readSendConfig();
|
|
@@ -691,14 +692,14 @@ async function runDumpMode() {
|
|
|
691
692
|
isEditor = isEditorPaneFromConf(currentPaneId);
|
|
692
693
|
}
|
|
693
694
|
if (!isEditor) {
|
|
694
|
-
logger$
|
|
695
|
+
logger$6.error("Current pane is not an editor pane");
|
|
695
696
|
process.exit(1);
|
|
696
697
|
}
|
|
697
698
|
let targetPanes;
|
|
698
699
|
if (config.mux === "tmux") targetPanes = await getTargetPaneIds$1(currentPaneId);
|
|
699
700
|
else targetPanes = await getTargetPaneIds(currentPaneId);
|
|
700
701
|
if (targetPanes.length === 0) {
|
|
701
|
-
logger$
|
|
702
|
+
logger$6.error("No target panes registered for this editor pane");
|
|
702
703
|
process.exit(1);
|
|
703
704
|
}
|
|
704
705
|
const quoteContents = [];
|
|
@@ -717,7 +718,7 @@ async function runDumpMode() {
|
|
|
717
718
|
process.stdout.write(combinedContent.replace(/\n{3,}$/, "\n\n"));
|
|
718
719
|
process.exit(0);
|
|
719
720
|
} catch (error) {
|
|
720
|
-
logger$
|
|
721
|
+
logger$6.error(`${error instanceof Error ? error.message : "Unknown error"}`);
|
|
721
722
|
process.exit(1);
|
|
722
723
|
}
|
|
723
724
|
}
|
|
@@ -749,11 +750,11 @@ function processContent(content) {
|
|
|
749
750
|
|
|
750
751
|
//#endregion
|
|
751
752
|
//#region src/modes/input.ts
|
|
752
|
-
const logger$
|
|
753
|
+
const logger$5 = getLogger(["editprompt", "input"]);
|
|
753
754
|
async function runInputMode(rawContent, autoSend, sendKey, sendKeyDelay) {
|
|
754
755
|
const content = processContent(rawContent);
|
|
755
756
|
if (!content) {
|
|
756
|
-
logger$
|
|
757
|
+
logger$5.info("No content to send. Exiting.");
|
|
757
758
|
return;
|
|
758
759
|
}
|
|
759
760
|
const config = readSendConfig();
|
|
@@ -767,14 +768,14 @@ async function runInputMode(rawContent, autoSend, sendKey, sendKeyDelay) {
|
|
|
767
768
|
isEditor = isEditorPaneFromConf(currentPaneId);
|
|
768
769
|
}
|
|
769
770
|
if (!isEditor) {
|
|
770
|
-
logger$
|
|
771
|
+
logger$5.error("Current pane is not an editor pane");
|
|
771
772
|
process.exit(1);
|
|
772
773
|
}
|
|
773
774
|
let targetPanes;
|
|
774
775
|
if (config.mux === "tmux") targetPanes = await getTargetPaneIds$1(currentPaneId);
|
|
775
776
|
else targetPanes = await getTargetPaneIds(currentPaneId);
|
|
776
777
|
if (targetPanes.length === 0) {
|
|
777
|
-
logger$
|
|
778
|
+
logger$5.error("No target panes registered for this editor pane");
|
|
778
779
|
process.exit(1);
|
|
779
780
|
}
|
|
780
781
|
if (autoSend) {
|
|
@@ -791,15 +792,15 @@ async function runInputMode(rawContent, autoSend, sendKey, sendKeyDelay) {
|
|
|
791
792
|
}
|
|
792
793
|
successCount++;
|
|
793
794
|
} catch (error) {
|
|
794
|
-
logger$
|
|
795
|
+
logger$5.error(`Failed to send to pane ${targetPane}: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
795
796
|
}
|
|
796
797
|
if (config.alwaysCopy) {
|
|
797
798
|
await copyToClipboard(content);
|
|
798
|
-
logger$
|
|
799
|
+
logger$5.info("Also copied to clipboard.");
|
|
799
800
|
}
|
|
800
|
-
if (successCount > 0) logger$
|
|
801
|
+
if (successCount > 0) logger$5.info("Content sent and submitted successfully!");
|
|
801
802
|
else {
|
|
802
|
-
logger$
|
|
803
|
+
logger$5.error("All target panes failed to receive content");
|
|
803
804
|
process.exit(1);
|
|
804
805
|
}
|
|
805
806
|
return;
|
|
@@ -808,12 +809,12 @@ async function runInputMode(rawContent, autoSend, sendKey, sendKeyDelay) {
|
|
|
808
809
|
const result = await handleContentDelivery(content, config.mux, targetPanes);
|
|
809
810
|
if (config.alwaysCopy && !result.allFailed) {
|
|
810
811
|
await copyToClipboard(content);
|
|
811
|
-
logger$
|
|
812
|
+
logger$5.info("Also copied to clipboard.");
|
|
812
813
|
}
|
|
813
814
|
if (result.successCount > 0) await focusFirstSuccessPane(config.mux, targetPanes, result.failedPanes);
|
|
814
815
|
if (result.allFailed) process.exit(1);
|
|
815
816
|
} catch (error) {
|
|
816
|
-
logger$
|
|
817
|
+
logger$5.error(`${error instanceof Error ? error.message : "Unknown error"}`);
|
|
817
818
|
process.exit(1);
|
|
818
819
|
}
|
|
819
820
|
}
|
|
@@ -841,13 +842,13 @@ const inputCommand = define({
|
|
|
841
842
|
});
|
|
842
843
|
const rawContent = extractRawContent(ctx.rest, ctx.positionals);
|
|
843
844
|
if (rawContent === void 0) {
|
|
844
|
-
logger$
|
|
845
|
-
logger$
|
|
846
|
-
logger$
|
|
845
|
+
logger$5.error("Content is required for input command");
|
|
846
|
+
logger$5.error("Usage: editprompt input \"your content\"");
|
|
847
|
+
logger$5.error(" or: editprompt input -- \"your content\"");
|
|
847
848
|
process.exit(1);
|
|
848
849
|
}
|
|
849
850
|
if (ctx.values["send-key"] && !ctx.values["auto-send"]) {
|
|
850
|
-
logger$
|
|
851
|
+
logger$5.error("--send-key requires --auto-send to be enabled");
|
|
851
852
|
process.exit(1);
|
|
852
853
|
}
|
|
853
854
|
const config = readSendConfig();
|
|
@@ -888,7 +889,7 @@ function getFormattedDateTime() {
|
|
|
888
889
|
async function createTempFile() {
|
|
889
890
|
const tempDir = join(tmpdir(), "editprompt-prompts");
|
|
890
891
|
await mkdir(tempDir, { recursive: true });
|
|
891
|
-
const filePath = join(tempDir, `${TEMP_FILE_PREFIX}${getFormattedDateTime()}${TEMP_FILE_EXTENSION}`);
|
|
892
|
+
const filePath = join(tempDir, `${TEMP_FILE_PREFIX}${getFormattedDateTime()}-${randomBytes(4).toString("hex")}${TEMP_FILE_EXTENSION}`);
|
|
892
893
|
await writeFile(filePath, "", "utf-8");
|
|
893
894
|
return filePath;
|
|
894
895
|
}
|
|
@@ -947,7 +948,7 @@ async function openEditorAndGetContent(editorOption, envVars, sendConfig) {
|
|
|
947
948
|
|
|
948
949
|
//#endregion
|
|
949
950
|
//#region src/modes/openEditor.ts
|
|
950
|
-
const logger$
|
|
951
|
+
const logger$4 = getLogger(["editprompt", "open"]);
|
|
951
952
|
async function runOpenEditorMode(options) {
|
|
952
953
|
if (options.targetPanes.length > 0 && options.mux === "tmux") try {
|
|
953
954
|
await markAsEditorPane$1(await getCurrentPaneId$1(), options.targetPanes);
|
|
@@ -962,10 +963,10 @@ async function runOpenEditorMode(options) {
|
|
|
962
963
|
alwaysCopy: options.alwaysCopy,
|
|
963
964
|
sendKeyDelay: Number.parseInt(process.env.EDITPROMPT_SEND_KEY_DELAY || "", 10) || 1e3
|
|
964
965
|
};
|
|
965
|
-
logger$
|
|
966
|
+
logger$4.info("Opening editor...");
|
|
966
967
|
const content = await openEditorAndGetContent(options.editor, options.env, sendConfig);
|
|
967
968
|
if (!content) {
|
|
968
|
-
logger$
|
|
969
|
+
logger$4.info("No content entered. Exiting.");
|
|
969
970
|
return;
|
|
970
971
|
}
|
|
971
972
|
try {
|
|
@@ -974,12 +975,12 @@ async function runOpenEditorMode(options) {
|
|
|
974
975
|
console.log(content);
|
|
975
976
|
if (options.alwaysCopy && !result.allFailed) {
|
|
976
977
|
await copyToClipboard(content);
|
|
977
|
-
logger$
|
|
978
|
+
logger$4.info("Also copied to clipboard.");
|
|
978
979
|
}
|
|
979
980
|
if (options.targetPanes.length > 0 && result.successCount > 0) await focusFirstSuccessPane(options.mux, options.targetPanes, result.failedPanes);
|
|
980
981
|
if (!result.allSuccess) process.exit(1);
|
|
981
982
|
} catch (error) {
|
|
982
|
-
logger$
|
|
983
|
+
logger$4.error(`${error instanceof Error ? error.message : "Unknown error"}`);
|
|
983
984
|
process.exit(1);
|
|
984
985
|
}
|
|
985
986
|
} finally {
|
|
@@ -1027,10 +1028,10 @@ const openCommand = define({
|
|
|
1027
1028
|
|
|
1028
1029
|
//#endregion
|
|
1029
1030
|
//#region src/modes/register.ts
|
|
1030
|
-
const logger$
|
|
1031
|
+
const logger$3 = getLogger(["editprompt", "register"]);
|
|
1031
1032
|
async function runRegisterMode(options) {
|
|
1032
1033
|
if (options.targetPanes.length === 0) {
|
|
1033
|
-
logger$
|
|
1034
|
+
logger$3.error("--target-pane is required for register command");
|
|
1034
1035
|
process.exit(1);
|
|
1035
1036
|
}
|
|
1036
1037
|
let editorPaneId;
|
|
@@ -1038,17 +1039,17 @@ async function runRegisterMode(options) {
|
|
|
1038
1039
|
else if (options.mux === "tmux") {
|
|
1039
1040
|
editorPaneId = await getCurrentPaneId$1();
|
|
1040
1041
|
if (!await isEditorPane(editorPaneId)) {
|
|
1041
|
-
logger$
|
|
1042
|
+
logger$3.error("Current pane is not an editor pane. Please run this command from an editor pane or specify --editor-pane.");
|
|
1042
1043
|
process.exit(1);
|
|
1043
1044
|
}
|
|
1044
1045
|
} else if (options.mux === "wezterm") {
|
|
1045
1046
|
editorPaneId = await getCurrentPaneId();
|
|
1046
1047
|
if (!isEditorPaneFromConf(editorPaneId)) {
|
|
1047
|
-
logger$
|
|
1048
|
+
logger$3.error("Current pane is not an editor pane. Please run this command from an editor pane or specify --editor-pane.");
|
|
1048
1049
|
process.exit(1);
|
|
1049
1050
|
}
|
|
1050
1051
|
} else {
|
|
1051
|
-
logger$
|
|
1052
|
+
logger$3.error("Unsupported multiplexer");
|
|
1052
1053
|
process.exit(1);
|
|
1053
1054
|
}
|
|
1054
1055
|
try {
|
|
@@ -1058,9 +1059,9 @@ async function runRegisterMode(options) {
|
|
|
1058
1059
|
const mergedTargetPanes = [...new Set([...existingPanes, ...options.targetPanes])];
|
|
1059
1060
|
if (options.mux === "tmux") await markAsEditorPane$1(editorPaneId, mergedTargetPanes);
|
|
1060
1061
|
else if (options.mux === "wezterm") await markAsEditorPane(editorPaneId, mergedTargetPanes);
|
|
1061
|
-
logger$
|
|
1062
|
+
logger$3.info(`Editor pane ${editorPaneId} registered with target panes: ${mergedTargetPanes.join(", ")}`);
|
|
1062
1063
|
} catch (error) {
|
|
1063
|
-
logger$
|
|
1064
|
+
logger$3.error(`${error instanceof Error ? error.message : "Unknown error"}`);
|
|
1064
1065
|
process.exit(1);
|
|
1065
1066
|
}
|
|
1066
1067
|
}
|
|
@@ -1095,15 +1096,15 @@ const registerCommand = define({
|
|
|
1095
1096
|
|
|
1096
1097
|
//#endregion
|
|
1097
1098
|
//#region src/modes/resume.ts
|
|
1098
|
-
const logger$
|
|
1099
|
+
const logger$2 = getLogger(["editprompt", "resume"]);
|
|
1099
1100
|
async function runResumeMode(targetPane, mux) {
|
|
1100
1101
|
if (mux === "wezterm") {
|
|
1101
1102
|
const currentPaneId = await getCurrentPaneId();
|
|
1102
1103
|
if (isEditorPaneFromConf(currentPaneId)) {
|
|
1103
|
-
logger$
|
|
1104
|
+
logger$2.debug("Current pane is an editor pane");
|
|
1104
1105
|
const originalTargetPaneIds = await getTargetPaneIds(currentPaneId);
|
|
1105
1106
|
if (originalTargetPaneIds.length === 0) {
|
|
1106
|
-
logger$
|
|
1107
|
+
logger$2.debug("No target pane IDs found for editor pane");
|
|
1107
1108
|
process.exit(1);
|
|
1108
1109
|
}
|
|
1109
1110
|
let focused = false;
|
|
@@ -1113,20 +1114,20 @@ async function runResumeMode(targetPane, mux) {
|
|
|
1113
1114
|
break;
|
|
1114
1115
|
}
|
|
1115
1116
|
if (!focused) {
|
|
1116
|
-
logger$
|
|
1117
|
+
logger$2.debug("All target panes do not exist");
|
|
1117
1118
|
process.exit(1);
|
|
1118
1119
|
}
|
|
1119
1120
|
process.exit(0);
|
|
1120
1121
|
}
|
|
1121
|
-
logger$
|
|
1122
|
+
logger$2.debug("Current pane is not an editor pane");
|
|
1122
1123
|
const editorPaneId = await getEditorPaneId(targetPane);
|
|
1123
|
-
logger$
|
|
1124
|
+
logger$2.debug("wezterm editorPaneId: {editorPaneId}", { editorPaneId });
|
|
1124
1125
|
if (editorPaneId === "") {
|
|
1125
|
-
logger$
|
|
1126
|
+
logger$2.debug("Editor pane ID not found");
|
|
1126
1127
|
process.exit(1);
|
|
1127
1128
|
}
|
|
1128
1129
|
if (!await checkPaneExists(editorPaneId)) {
|
|
1129
|
-
logger$
|
|
1130
|
+
logger$2.debug("Editor pane does not exist");
|
|
1130
1131
|
await clearEditorPaneId(targetPane);
|
|
1131
1132
|
process.exit(1);
|
|
1132
1133
|
}
|
|
@@ -1134,7 +1135,7 @@ async function runResumeMode(targetPane, mux) {
|
|
|
1134
1135
|
await focusPane(editorPaneId);
|
|
1135
1136
|
process.exit(0);
|
|
1136
1137
|
} catch (error) {
|
|
1137
|
-
logger$
|
|
1138
|
+
logger$2.debug("Can't focus editorPaneId: {editorPaneId}, error: {error}", {
|
|
1138
1139
|
editorPaneId,
|
|
1139
1140
|
error
|
|
1140
1141
|
});
|
|
@@ -1183,6 +1184,77 @@ const resumeCommand = define({
|
|
|
1183
1184
|
}
|
|
1184
1185
|
});
|
|
1185
1186
|
|
|
1187
|
+
//#endregion
|
|
1188
|
+
//#region src/modes/press.ts
|
|
1189
|
+
const logger$1 = getLogger(["editprompt", "press"]);
|
|
1190
|
+
async function runPressMode(key, delay = 0) {
|
|
1191
|
+
if (!key) {
|
|
1192
|
+
logger$1.error("Key is required");
|
|
1193
|
+
process.exit(1);
|
|
1194
|
+
}
|
|
1195
|
+
const config = readSendConfig();
|
|
1196
|
+
let currentPaneId;
|
|
1197
|
+
let isEditor;
|
|
1198
|
+
if (config.mux === "tmux") {
|
|
1199
|
+
currentPaneId = await getCurrentPaneId$1();
|
|
1200
|
+
isEditor = await isEditorPane(currentPaneId);
|
|
1201
|
+
} else {
|
|
1202
|
+
currentPaneId = await getCurrentPaneId();
|
|
1203
|
+
isEditor = isEditorPaneFromConf(currentPaneId);
|
|
1204
|
+
}
|
|
1205
|
+
if (!isEditor) {
|
|
1206
|
+
logger$1.error("Current pane is not an editor pane");
|
|
1207
|
+
process.exit(1);
|
|
1208
|
+
}
|
|
1209
|
+
let targetPanes;
|
|
1210
|
+
if (config.mux === "tmux") targetPanes = await getTargetPaneIds$1(currentPaneId);
|
|
1211
|
+
else targetPanes = await getTargetPaneIds(currentPaneId);
|
|
1212
|
+
if (targetPanes.length === 0) {
|
|
1213
|
+
logger$1.error("No target panes registered for this editor pane");
|
|
1214
|
+
process.exit(1);
|
|
1215
|
+
}
|
|
1216
|
+
let successCount = 0;
|
|
1217
|
+
for (const targetPane of targetPanes) try {
|
|
1218
|
+
if (config.mux === "wezterm") await sendKeyToWeztermPane(targetPane, key, delay);
|
|
1219
|
+
else await sendKeyToTmuxPane(targetPane, key, delay);
|
|
1220
|
+
successCount++;
|
|
1221
|
+
} catch (error) {
|
|
1222
|
+
logger$1.warn(`Failed to send key to pane ${targetPane}: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
1223
|
+
}
|
|
1224
|
+
if (successCount > 0) logger$1.info("Key sent successfully!");
|
|
1225
|
+
else {
|
|
1226
|
+
logger$1.error("All target panes failed to receive key");
|
|
1227
|
+
process.exit(1);
|
|
1228
|
+
}
|
|
1229
|
+
}
|
|
1230
|
+
const pressCommand = define({
|
|
1231
|
+
name: "press",
|
|
1232
|
+
description: "Send a key to target pane without Enter",
|
|
1233
|
+
args: {
|
|
1234
|
+
delay: {
|
|
1235
|
+
description: "Delay before sending key (milliseconds)",
|
|
1236
|
+
type: "string"
|
|
1237
|
+
},
|
|
1238
|
+
"log-file": ARG_LOG_FILE,
|
|
1239
|
+
quiet: ARG_QUIET,
|
|
1240
|
+
verbose: ARG_VERBOSE
|
|
1241
|
+
},
|
|
1242
|
+
async run(ctx) {
|
|
1243
|
+
setupLogger({
|
|
1244
|
+
quiet: Boolean(ctx.values.quiet),
|
|
1245
|
+
verbose: Boolean(ctx.values.verbose),
|
|
1246
|
+
logFile: ctx.values["log-file"]
|
|
1247
|
+
});
|
|
1248
|
+
const key = extractRawContent(ctx.rest, ctx.positionals);
|
|
1249
|
+
if (key === void 0 || key === "") {
|
|
1250
|
+
logger$1.error("Key is required for press command");
|
|
1251
|
+
logger$1.error("Usage: editprompt press -- \"Tab\"");
|
|
1252
|
+
process.exit(1);
|
|
1253
|
+
}
|
|
1254
|
+
await runPressMode(key, ctx.values.delay ? Number(ctx.values.delay) : 0);
|
|
1255
|
+
}
|
|
1256
|
+
});
|
|
1257
|
+
|
|
1186
1258
|
//#endregion
|
|
1187
1259
|
//#region src/modes/stash.ts
|
|
1188
1260
|
const logger = getLogger(["editprompt", "stash"]);
|
|
@@ -1395,6 +1467,7 @@ await cli(process.argv.slice(2), {
|
|
|
1395
1467
|
register: registerCommand,
|
|
1396
1468
|
resume: resumeCommand,
|
|
1397
1469
|
input: inputCommand,
|
|
1470
|
+
press: pressCommand,
|
|
1398
1471
|
collect: collectCommand,
|
|
1399
1472
|
dump: dumpCommand,
|
|
1400
1473
|
stash: stashCommand
|