mintree 0.5.6 → 0.5.9
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 +1 -0
- package/dist/lib/claude.js +12 -12
- package/dist/lib/terminal.d.ts +8 -9
- package/dist/lib/terminal.js +22 -20
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -292,6 +292,7 @@ Linear authentication lives in `~/.mintree/credentials.json` (user-scoped, not p
|
|
|
292
292
|
- **Sessions persist by issue**: each issue gets a UUID stored in `metadata.json`. Subsequent `worktree work` calls pass `--resume <uuid>` so Claude reopens the same conversation.
|
|
293
293
|
- **Live state** (optional): the four hooks installed by `mintree helpers session-signal install` write the current Claude state to `.mintree/session-states/<issue>.json` on every prompt / stop / notification / session-end. The dashboard reads those files to colour each row in real time.
|
|
294
294
|
- **Remote Control** (optional): `mintree doctor` checks `~/.claude.json` for `remoteControlAtStartup: true`. Enabling it lets you continue a local session from a different device.
|
|
295
|
+
- **iTerm2 tab title** (automatic): when you launch on [iTerm2](https://iterm2.com), mintree sets the **tab title** to the session name (the worktree issue id like `VAL-68`, or the orchestrator's name) so each tab stays identifiable at a glance. It sets the tab title via OSC 1 (icon name) rather than the window title, because Claude Code rewrites the window title with a descriptive summary while it runs; the icon-name slot is independent of it. The title clears on exit. No-op on other terminals (detected via `TERM_PROGRAM` / `LC_TERMINAL`).
|
|
295
296
|
|
|
296
297
|
---
|
|
297
298
|
|
package/dist/lib/claude.js
CHANGED
|
@@ -2,7 +2,7 @@ import { execSync, spawn } from "child_process";
|
|
|
2
2
|
import { existsSync, writeFileSync } from "fs";
|
|
3
3
|
import { homedir, tmpdir } from "os";
|
|
4
4
|
import { join } from "path";
|
|
5
|
-
import {
|
|
5
|
+
import { setITermTabTitle, clearITermTabTitle } from "./terminal.js";
|
|
6
6
|
export const PERMISSION_MODES = ["default", "auto"];
|
|
7
7
|
/**
|
|
8
8
|
* Resolves the absolute path of the Claude Code CLI binary, or null if not on
|
|
@@ -75,17 +75,17 @@ export function launchClaude(options) {
|
|
|
75
75
|
if (options.prompt && options.prompt.length > 0) {
|
|
76
76
|
args.push("--", promptArg(options.prompt));
|
|
77
77
|
}
|
|
78
|
-
// Label the session
|
|
79
|
-
//
|
|
80
|
-
// identifiable (worktree issue id, or
|
|
81
|
-
// No-op outside iTerm2.
|
|
82
|
-
const
|
|
83
|
-
if (
|
|
84
|
-
|
|
78
|
+
// Label the session via the iTerm2 tab title before handing over the TTY.
|
|
79
|
+
// We use OSC 1 (icon name), a slot separate from the window title Claude
|
|
80
|
+
// rewrites, so the tab stays identifiable (worktree issue id, or
|
|
81
|
+
// orchestrator name) while it runs. No-op outside iTerm2.
|
|
82
|
+
const tabTitle = options.remoteControlName;
|
|
83
|
+
if (tabTitle)
|
|
84
|
+
setITermTabTitle(tabTitle);
|
|
85
85
|
const child = spawn(bin, args, { stdio: "inherit", cwd: options.cwd });
|
|
86
|
-
// Clear the
|
|
87
|
-
//
|
|
88
|
-
if (
|
|
89
|
-
child.on("exit", () =>
|
|
86
|
+
// Clear the tab title once Claude exits so it doesn't linger on the shell
|
|
87
|
+
// that regains the TTY.
|
|
88
|
+
if (tabTitle)
|
|
89
|
+
child.on("exit", () => clearITermTabTitle());
|
|
90
90
|
return child;
|
|
91
91
|
}
|
package/dist/lib/terminal.d.ts
CHANGED
|
@@ -1,13 +1,12 @@
|
|
|
1
1
|
/** True when the active terminal is iTerm2 (also detected through tmux). */
|
|
2
2
|
export declare function isITerm(): boolean;
|
|
3
3
|
/**
|
|
4
|
-
* Builds the raw
|
|
5
|
-
* so it can be unit-tested; an empty string clears the
|
|
6
|
-
*
|
|
7
|
-
* parens so the base64-encoded literal renders verbatim.
|
|
4
|
+
* Builds the raw OSC 1 (set icon name) escape sequence for `text`. Pure (no I/O)
|
|
5
|
+
* so it can be unit-tested; an empty string clears the tab title, letting
|
|
6
|
+
* iTerm2 fall back to its default.
|
|
8
7
|
*/
|
|
9
|
-
export declare function
|
|
10
|
-
/** Sets the iTerm2
|
|
11
|
-
export declare function
|
|
12
|
-
/** Clears the iTerm2
|
|
13
|
-
export declare function
|
|
8
|
+
export declare function buildTabTitleSequence(text: string): string;
|
|
9
|
+
/** Sets the iTerm2 tab title to `text`. No-op outside iTerm2 or with empty text. */
|
|
10
|
+
export declare function setITermTabTitle(text: string): void;
|
|
11
|
+
/** Clears the iTerm2 tab title. No-op outside iTerm2. */
|
|
12
|
+
export declare function clearITermTabTitle(): void;
|
package/dist/lib/terminal.js
CHANGED
|
@@ -1,11 +1,15 @@
|
|
|
1
|
-
// iTerm2
|
|
1
|
+
// iTerm2 tab-title integration.
|
|
2
2
|
//
|
|
3
|
-
//
|
|
4
|
-
//
|
|
5
|
-
//
|
|
6
|
-
//
|
|
7
|
-
//
|
|
8
|
-
//
|
|
3
|
+
// We label each mintree session with the iTerm2 *tab title* (the small text in
|
|
4
|
+
// the tab bar) so a session is identifiable at a glance — e.g. the worktree
|
|
5
|
+
// issue id `VAL-68`, or `orchestrator-VAL-12_BE-16`.
|
|
6
|
+
//
|
|
7
|
+
// We use OSC 1 (set icon name) rather than OSC 2 (window title): Claude Code
|
|
8
|
+
// rewrites the window title with a descriptive summary while it runs, but the
|
|
9
|
+
// icon name / tab title is a separate slot it leaves alone. An earlier version
|
|
10
|
+
// used the iTerm2 badge instead, but the badge font scales to fill a
|
|
11
|
+
// profile-controlled box and rendered enormous for short labels, with no
|
|
12
|
+
// per-session escape to shrink it. The tab title is small and unobtrusive.
|
|
9
13
|
//
|
|
10
14
|
// Everything here is a no-op outside iTerm2, so callers can invoke it
|
|
11
15
|
// unconditionally.
|
|
@@ -25,14 +29,12 @@ function wrapForTmux(seq) {
|
|
|
25
29
|
return `${ESC}Ptmux;${doubled}${ESC}\\`;
|
|
26
30
|
}
|
|
27
31
|
/**
|
|
28
|
-
* Builds the raw
|
|
29
|
-
* so it can be unit-tested; an empty string clears the
|
|
30
|
-
*
|
|
31
|
-
* parens so the base64-encoded literal renders verbatim.
|
|
32
|
+
* Builds the raw OSC 1 (set icon name) escape sequence for `text`. Pure (no I/O)
|
|
33
|
+
* so it can be unit-tested; an empty string clears the tab title, letting
|
|
34
|
+
* iTerm2 fall back to its default.
|
|
32
35
|
*/
|
|
33
|
-
export function
|
|
34
|
-
|
|
35
|
-
return wrapForTmux(`${ESC}]1337;SetBadgeFormat=${b64}${BEL}`);
|
|
36
|
+
export function buildTabTitleSequence(text) {
|
|
37
|
+
return wrapForTmux(`${ESC}]1;${text}${BEL}`);
|
|
36
38
|
}
|
|
37
39
|
function writeToTty(seq) {
|
|
38
40
|
// We only call this right before spawning Claude / right after it exits,
|
|
@@ -41,15 +43,15 @@ function writeToTty(seq) {
|
|
|
41
43
|
if (process.stdout.isTTY)
|
|
42
44
|
process.stdout.write(seq);
|
|
43
45
|
}
|
|
44
|
-
/** Sets the iTerm2
|
|
45
|
-
export function
|
|
46
|
+
/** Sets the iTerm2 tab title to `text`. No-op outside iTerm2 or with empty text. */
|
|
47
|
+
export function setITermTabTitle(text) {
|
|
46
48
|
if (!isITerm() || !text)
|
|
47
49
|
return;
|
|
48
|
-
writeToTty(
|
|
50
|
+
writeToTty(buildTabTitleSequence(text));
|
|
49
51
|
}
|
|
50
|
-
/** Clears the iTerm2
|
|
51
|
-
export function
|
|
52
|
+
/** Clears the iTerm2 tab title. No-op outside iTerm2. */
|
|
53
|
+
export function clearITermTabTitle() {
|
|
52
54
|
if (!isITerm())
|
|
53
55
|
return;
|
|
54
|
-
writeToTty(
|
|
56
|
+
writeToTty(buildTabTitleSequence(""));
|
|
55
57
|
}
|
package/package.json
CHANGED