@buckits/claude-statusline 2.2.0 → 2.3.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 +151 -66
- package/bin/install.js +318 -39
- package/package.json +15 -3
package/README.md
CHANGED
|
@@ -1,6 +1,64 @@
|
|
|
1
1
|
# @buckits/claude-statusline
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
<div align="center">
|
|
4
|
+
|
|
5
|
+
**The statusline Claude Code deserves.**
|
|
6
|
+
|
|
7
|
+
[](https://www.npmjs.com/package/@buckits/claude-statusline)
|
|
8
|
+
[](https://opensource.org/licenses/MIT)
|
|
9
|
+
|
|
10
|
+
<br>
|
|
11
|
+
|
|
12
|
+

|
|
13
|
+
|
|
14
|
+
<br>
|
|
15
|
+
|
|
16
|
+
[Features](#features) • [Installation](#installation) • [Screenshots](#what-it-looks-like) • [GSD Compatible](#-gsd-compatible)
|
|
17
|
+
|
|
18
|
+
</div>
|
|
19
|
+
|
|
20
|
+
---
|
|
21
|
+
|
|
22
|
+
## Why This Statusline?
|
|
23
|
+
|
|
24
|
+
Claude Code's default statusline is... minimal. You deserve better.
|
|
25
|
+
|
|
26
|
+
**This statusline shows you everything you need at a glance:**
|
|
27
|
+
|
|
28
|
+
- 🎨 **Gradient progress bar** that flows green → yellow → red as you approach the limit
|
|
29
|
+
- ⚡ **Auto-compact threshold marker** so you know exactly when Claude will summarize
|
|
30
|
+
- 💰 **Session cost tracking** in real-time
|
|
31
|
+
- 🔀 **Full git integration** with branch, status, and ahead/behind tracking
|
|
32
|
+
|
|
33
|
+
## Features
|
|
34
|
+
|
|
35
|
+
### 🎨 Gradient Progress Bar
|
|
36
|
+
|
|
37
|
+
50 segments that smoothly transition through colors as your context fills up. The gradient is calculated relative to the auto-compact threshold, not total capacity—so you always know how close you are to summarization.
|
|
38
|
+
|
|
39
|
+
### ⚡ Auto-Compact Threshold
|
|
40
|
+
|
|
41
|
+
A red lightning bolt marks exactly where Claude will auto-summarize (78%). No more surprises—you'll see it coming.
|
|
42
|
+
|
|
43
|
+
### 💰 Real-Time Cost
|
|
44
|
+
|
|
45
|
+
See your session cost update as you work: `($12.41)`
|
|
46
|
+
|
|
47
|
+
### 🔀 Git Status at a Glance
|
|
48
|
+
|
|
49
|
+
| Symbol | Meaning |
|
|
50
|
+
|--------|---------|
|
|
51
|
+
| `✓` | Clean - all committed |
|
|
52
|
+
| `●` | Unstaged changes |
|
|
53
|
+
| `✚` | Staged and ready |
|
|
54
|
+
| `●✚` | Both staged and unstaged |
|
|
55
|
+
| `↑5` | 5 commits ahead of remote |
|
|
56
|
+
| `↓2` | 2 commits behind remote |
|
|
57
|
+
|
|
58
|
+
### 📊 2-Line Dashboard
|
|
59
|
+
|
|
60
|
+
- **Line 1:** 🤖 Model • Cost • Context Progress
|
|
61
|
+
- **Line 2:** 📁 Project • Branch • Git Status • Remote Tracking
|
|
4
62
|
|
|
5
63
|
## Installation
|
|
6
64
|
|
|
@@ -8,82 +66,86 @@ A beautiful 2-line dashboard statusline for Claude Code with gradient progress b
|
|
|
8
66
|
npx @buckits/claude-statusline
|
|
9
67
|
```
|
|
10
68
|
|
|
11
|
-
|
|
69
|
+
That's it. The installer will:
|
|
70
|
+
1. Ask where to install (global or local)
|
|
71
|
+
2. Copy the statusline script
|
|
72
|
+
3. Configure your settings
|
|
12
73
|
|
|
13
|
-
|
|
14
|
-
- **Gradient Progress Bar** - 50 segments (4k tokens each) that smoothly transition green → yellow → orange → red
|
|
15
|
-
- **⚡ Compact Threshold Marker** - Red lightning bolt shows exactly where auto-compact triggers (78%)
|
|
16
|
-
- **Session Cost Tracking** - See your running cost in real-time
|
|
17
|
-
- **Git Status Indicators**:
|
|
18
|
-
- `✓` Green checkmark = clean (all committed)
|
|
19
|
-
- `●` Yellow dot = unstaged changes
|
|
20
|
-
- `✚` Green plus = staged changes ready to commit
|
|
21
|
-
- `●✚` Both = partial commit state
|
|
22
|
-
- **Ahead/Behind Tracking** - `↑5 ↓2` shows commits ahead/behind remote
|
|
23
|
-
- **Visual Icons** - 🤖 for AI line, 📁 for project line
|
|
24
|
-
- **GSD Update Notifications** - Automatically detects [Get Shit Done](https://www.npmjs.com/package/get-shit-done-cc) installations and shows available updates
|
|
25
|
-
|
|
26
|
-
## Screenshot
|
|
74
|
+
### Options
|
|
27
75
|
|
|
28
|
-
```
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
```
|
|
76
|
+
```bash
|
|
77
|
+
# Interactive (recommended)
|
|
78
|
+
npx @buckits/claude-statusline
|
|
32
79
|
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
80
|
+
# Install globally for all projects
|
|
81
|
+
npx @buckits/claude-statusline --global
|
|
82
|
+
|
|
83
|
+
# Install for current project only
|
|
84
|
+
npx @buckits/claude-statusline --local
|
|
85
|
+
|
|
86
|
+
# Replace existing statusline
|
|
87
|
+
npx @buckits/claude-statusline --global --force
|
|
88
|
+
|
|
89
|
+
# Uninstall
|
|
90
|
+
npx @buckits/claude-statusline --global --uninstall
|
|
37
91
|
```
|
|
38
92
|
|
|
39
|
-
## What
|
|
93
|
+
## What It Looks Like
|
|
94
|
+
|
|
95
|
+
### 🟢 Normal Usage (Green Zone)
|
|
96
|
+
|
|
97
|
+

|
|
98
|
+
|
|
99
|
+
Safe and sound. Plenty of context remaining.
|
|
100
|
+
|
|
101
|
+
### 🟡 Getting Busy (Yellow Zone)
|
|
102
|
+
|
|
103
|
+

|
|
104
|
+
|
|
105
|
+
Making progress. Keep an eye on that threshold.
|
|
106
|
+
|
|
107
|
+
### 🔴 Approaching Limit (Red Zone)
|
|
40
108
|
|
|
41
|
-
|
|
42
|
-
| Element | Description |
|
|
43
|
-
|---------|-------------|
|
|
44
|
-
| 🤖 | AI indicator |
|
|
45
|
-
| `Opus 4.5` | Current model (cyan) |
|
|
46
|
-
| `($14.61)` | Session cost (green) |
|
|
47
|
-
| `│` | Separator |
|
|
48
|
-
| `[███░░░⚡░░░]` | Context usage with compact threshold |
|
|
49
|
-
| `80k/200k` | Tokens used / total |
|
|
109
|
+

|
|
50
110
|
|
|
51
|
-
|
|
52
|
-
| Element | Description |
|
|
53
|
-
|---------|-------------|
|
|
54
|
-
| 📁 | Project indicator |
|
|
55
|
-
| `trellis` | Project name (cyan) |
|
|
56
|
-
| `POC` | Current branch (magenta) |
|
|
57
|
-
| `✓●✚` | Git status (clean/unstaged/staged) |
|
|
58
|
-
| `→` | Points to tracking branch |
|
|
59
|
-
| `origin/POC` | Remote tracking branch (blue) |
|
|
60
|
-
| `↑15` | Commits ahead (green) |
|
|
61
|
-
| `↓3` | Commits behind (red) |
|
|
111
|
+
Getting close to auto-compact. Consider wrapping up or starting fresh.
|
|
62
112
|
|
|
63
|
-
## GSD
|
|
113
|
+
## 🤝 GSD Compatible
|
|
64
114
|
|
|
65
|
-
|
|
115
|
+
This statusline works perfectly alongside [Get Shit Done (GSD)](https://www.npmjs.com/package/get-shit-done-cc)!
|
|
66
116
|
|
|
67
|
-
|
|
68
|
-
1. Checks for GSD installation in project (`.claude/get-shit-done/VERSION`) or global (`~/.claude/get-shit-done/VERSION`)
|
|
69
|
-
2. Reads the latest version from GSD's update cache (`~/.claude/cache/gsd-update-check.json`)
|
|
70
|
-
3. If versions differ, shows the update notification on line 2
|
|
117
|
+
If you have GSD installed, the statusline will automatically show update notifications when a new GSD version is available.
|
|
71
118
|
|
|
72
|
-
|
|
119
|
+
```bash
|
|
120
|
+
# Install both for the ultimate Claude Code setup
|
|
121
|
+
npx @buckits/claude-statusline
|
|
122
|
+
npx get-shit-done-cc
|
|
123
|
+
```
|
|
124
|
+
|
|
125
|
+
## Requirements
|
|
126
|
+
|
|
127
|
+
- **Claude Code CLI** (obviously)
|
|
128
|
+
- **jq** - for JSON parsing ([install guide](https://stedolan.github.io/jq/download/))
|
|
129
|
+
- **Bash** - ships with macOS/Linux
|
|
130
|
+
- **Git** - for git status features (optional)
|
|
73
131
|
|
|
74
|
-
|
|
132
|
+
### Installing jq
|
|
75
133
|
|
|
76
|
-
|
|
134
|
+
```bash
|
|
135
|
+
# macOS
|
|
136
|
+
brew install jq
|
|
77
137
|
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
138
|
+
# Ubuntu/Debian
|
|
139
|
+
sudo apt install jq
|
|
140
|
+
|
|
141
|
+
# Windows (via chocolatey)
|
|
142
|
+
choco install jq
|
|
143
|
+
```
|
|
84
144
|
|
|
85
145
|
## Manual Installation
|
|
86
146
|
|
|
147
|
+
If you prefer to install manually:
|
|
148
|
+
|
|
87
149
|
1. Copy `statusline.sh` to `~/.claude/statusline.sh`
|
|
88
150
|
2. Make it executable: `chmod +x ~/.claude/statusline.sh`
|
|
89
151
|
3. Add to `~/.claude/settings.json`:
|
|
@@ -97,13 +159,36 @@ The bar gradient is calculated relative to the ⚡ threshold (not total capacity
|
|
|
97
159
|
}
|
|
98
160
|
```
|
|
99
161
|
|
|
100
|
-
##
|
|
162
|
+
## Troubleshooting
|
|
163
|
+
|
|
164
|
+
### Statusline not showing?
|
|
165
|
+
|
|
166
|
+
1. Make sure you restarted Claude Code after installation
|
|
167
|
+
2. Check that `jq` is installed: `which jq`
|
|
168
|
+
3. Verify the script is executable: `ls -la ~/.claude/statusline.sh`
|
|
169
|
+
|
|
170
|
+
### Wrong colors?
|
|
171
|
+
|
|
172
|
+
Your terminal needs to support 256 colors. Most modern terminals do.
|
|
173
|
+
|
|
174
|
+
### Git status not showing?
|
|
101
175
|
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
176
|
+
Make sure you're in a git repository with at least one commit.
|
|
177
|
+
|
|
178
|
+
## Contributing
|
|
179
|
+
|
|
180
|
+
Issues and PRs welcome at [github.com/Buckits/claude-statusline](https://github.com/Buckits/claude-statusline)
|
|
106
181
|
|
|
107
182
|
## License
|
|
108
183
|
|
|
109
|
-
MIT
|
|
184
|
+
MIT © [Buckits](https://github.com/Buckits)
|
|
185
|
+
|
|
186
|
+
---
|
|
187
|
+
|
|
188
|
+
<div align="center">
|
|
189
|
+
|
|
190
|
+
**Made for the Claude Code community** 🤖
|
|
191
|
+
|
|
192
|
+
*Star this repo if you find it useful!*
|
|
193
|
+
|
|
194
|
+
</div>
|
package/bin/install.js
CHANGED
|
@@ -3,56 +3,335 @@
|
|
|
3
3
|
const fs = require('fs');
|
|
4
4
|
const path = require('path');
|
|
5
5
|
const os = require('os');
|
|
6
|
+
const readline = require('readline');
|
|
6
7
|
|
|
7
|
-
|
|
8
|
-
const
|
|
9
|
-
const
|
|
10
|
-
const
|
|
8
|
+
// Colors
|
|
9
|
+
const cyan = '\x1b[36m';
|
|
10
|
+
const green = '\x1b[32m';
|
|
11
|
+
const yellow = '\x1b[33m';
|
|
12
|
+
const red = '\x1b[31m';
|
|
13
|
+
const magenta = '\x1b[35m';
|
|
14
|
+
const dim = '\x1b[2m';
|
|
15
|
+
const bold = '\x1b[1m';
|
|
16
|
+
const reset = '\x1b[0m';
|
|
11
17
|
|
|
12
|
-
|
|
18
|
+
// Get version from package.json
|
|
19
|
+
const pkg = require('../package.json');
|
|
13
20
|
|
|
14
|
-
//
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
21
|
+
// Parse args
|
|
22
|
+
const args = process.argv.slice(2);
|
|
23
|
+
const hasGlobal = args.includes('--global') || args.includes('-g');
|
|
24
|
+
const hasLocal = args.includes('--local') || args.includes('-l');
|
|
25
|
+
const hasHelp = args.includes('--help') || args.includes('-h');
|
|
26
|
+
const hasUninstall = args.includes('--uninstall') || args.includes('-u');
|
|
27
|
+
const hasForce = args.includes('--force') || args.includes('-f');
|
|
28
|
+
|
|
29
|
+
// Directory constants
|
|
30
|
+
const CLAUDE_DIR_NAME = '.claude';
|
|
31
|
+
|
|
32
|
+
function getGlobalDir() {
|
|
33
|
+
if (process.env.CLAUDE_CONFIG_DIR) {
|
|
34
|
+
return expandTilde(process.env.CLAUDE_CONFIG_DIR);
|
|
35
|
+
}
|
|
36
|
+
return path.join(os.homedir(), CLAUDE_DIR_NAME);
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
function getLocalDir() {
|
|
40
|
+
return path.join(process.cwd(), CLAUDE_DIR_NAME);
|
|
18
41
|
}
|
|
19
42
|
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
43
|
+
function expandTilde(filePath) {
|
|
44
|
+
if (filePath && filePath.startsWith('~/')) {
|
|
45
|
+
return path.join(os.homedir(), filePath.slice(2));
|
|
46
|
+
}
|
|
47
|
+
return filePath;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
// ASCII Art Banner
|
|
51
|
+
const banner = `
|
|
52
|
+
${cyan} ╔═╗╦ ╔═╗╦ ╦╔╦╗╔═╗
|
|
53
|
+
║ ║ ╠═╣║ ║ ║║║╣
|
|
54
|
+
╚═╝╩═╝╩ ╩╚═╝═╩╝╚═╝${reset}
|
|
55
|
+
${magenta}╔═╗╔╦╗╔═╗╔╦╗╦ ╦╔═╗╦ ╦╔╗╔╔═╗
|
|
56
|
+
╚═╗ ║ ╠═╣ ║ ║ ║╚═╗║ ║║║║║╣
|
|
57
|
+
╚═╝ ╩ ╩ ╩ ╩ ╚═╝╚═╝╩═╝╩╝╚╝╚═╝${reset}
|
|
58
|
+
|
|
59
|
+
${bold}The statusline Claude Code deserves${reset} ${dim}v${pkg.version}${reset}
|
|
60
|
+
|
|
61
|
+
${dim}───────────────────────────────────────────${reset}
|
|
62
|
+
${green}█${reset}${green}█${reset}${yellow}█${reset}${yellow}█${reset}${red}█${reset}${red}█${reset}░░░░⚡░░░ ${dim}Gradient progress • Git status${reset}
|
|
63
|
+
${dim}───────────────────────────────────────────${reset}
|
|
64
|
+
`;
|
|
65
|
+
|
|
66
|
+
const features = `
|
|
67
|
+
${cyan}✦${reset} ${bold}Gradient Progress Bar${reset}
|
|
68
|
+
50 segments that flow ${green}green${reset} → ${yellow}yellow${reset} → ${red}red${reset}
|
|
69
|
+
as you approach the context limit
|
|
70
|
+
|
|
71
|
+
${cyan}✦${reset} ${bold}⚡ Auto-Compact Threshold${reset}
|
|
72
|
+
Red lightning bolt shows exactly where
|
|
73
|
+
Claude will auto-summarize (78%)
|
|
74
|
+
|
|
75
|
+
${cyan}✦${reset} ${bold}Git Integration${reset}
|
|
76
|
+
Branch • ${green}✓${reset}/${yellow}●${reset}/${green}✚${reset} status • ${green}↑${reset}ahead ${red}↓${reset}behind
|
|
77
|
+
|
|
78
|
+
${cyan}✦${reset} ${bold}Session Cost Tracking${reset}
|
|
79
|
+
See your running \$ cost in real-time
|
|
80
|
+
|
|
81
|
+
${cyan}✦${reset} ${bold}2-Line Dashboard${reset}
|
|
82
|
+
Line 1: 🤖 Model • Cost • Context
|
|
83
|
+
Line 2: 📁 Project • Branch • Status
|
|
84
|
+
`;
|
|
85
|
+
|
|
86
|
+
const example = `
|
|
87
|
+
${dim}┌─────────────────────────────────────────────────────────────────┐${reset}
|
|
88
|
+
${dim}│${reset} 🤖 ${cyan}Opus 4.5${reset} ${green}(\$12.41)${reset} │ [${green}████████${yellow}████${red}██${reset}░░░░░░░⚡░░░░░] ${yellow}62k${reset}/${cyan}200k${reset} ${dim}│${reset}
|
|
89
|
+
${dim}│${reset} 📁 ${cyan}my-project${reset} ${magenta}main${reset} ${green}✓${reset} → ${cyan}origin/main${reset} ${green}↑2${reset} ${dim}│${reset}
|
|
90
|
+
${dim}└─────────────────────────────────────────────────────────────────┘${reset}
|
|
91
|
+
`;
|
|
92
|
+
|
|
93
|
+
// Help text
|
|
94
|
+
if (hasHelp) {
|
|
95
|
+
console.log(banner);
|
|
96
|
+
console.log(` ${yellow}Usage:${reset} npx @buckits/claude-statusline [options]
|
|
97
|
+
|
|
98
|
+
${yellow}Options:${reset}
|
|
99
|
+
${cyan}-g, --global${reset} Install globally (${dim}~/.claude${reset})
|
|
100
|
+
${cyan}-l, --local${reset} Install locally (${dim}./.claude${reset})
|
|
101
|
+
${cyan}-u, --uninstall${reset} Remove statusline configuration
|
|
102
|
+
${cyan}-f, --force${reset} Replace existing statusline config
|
|
103
|
+
${cyan}-h, --help${reset} Show this help message
|
|
24
104
|
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
105
|
+
${yellow}Examples:${reset}
|
|
106
|
+
${dim}# Interactive install (prompts for location)${reset}
|
|
107
|
+
npx @buckits/claude-statusline
|
|
28
108
|
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
109
|
+
${dim}# Install globally for all projects${reset}
|
|
110
|
+
npx @buckits/claude-statusline --global
|
|
111
|
+
|
|
112
|
+
${dim}# Install for current project only${reset}
|
|
113
|
+
npx @buckits/claude-statusline --local
|
|
114
|
+
|
|
115
|
+
${dim}# Replace existing statusline${reset}
|
|
116
|
+
npx @buckits/claude-statusline --global --force
|
|
117
|
+
`);
|
|
118
|
+
process.exit(0);
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
console.log(banner);
|
|
122
|
+
|
|
123
|
+
/**
|
|
124
|
+
* Read and parse settings.json
|
|
125
|
+
*/
|
|
126
|
+
function readSettings(settingsPath) {
|
|
127
|
+
if (fs.existsSync(settingsPath)) {
|
|
128
|
+
try {
|
|
129
|
+
return JSON.parse(fs.readFileSync(settingsPath, 'utf8'));
|
|
130
|
+
} catch (e) {
|
|
131
|
+
return {};
|
|
132
|
+
}
|
|
35
133
|
}
|
|
134
|
+
return {};
|
|
36
135
|
}
|
|
37
136
|
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
137
|
+
/**
|
|
138
|
+
* Write settings.json with proper formatting
|
|
139
|
+
*/
|
|
140
|
+
function writeSettings(settingsPath, settings) {
|
|
141
|
+
fs.writeFileSync(settingsPath, JSON.stringify(settings, null, 2) + '\n');
|
|
41
142
|
}
|
|
42
143
|
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
144
|
+
/**
|
|
145
|
+
* Uninstall statusline
|
|
146
|
+
*/
|
|
147
|
+
function uninstall(isGlobal) {
|
|
148
|
+
const targetDir = isGlobal ? getGlobalDir() : getLocalDir();
|
|
149
|
+
const locationLabel = isGlobal
|
|
150
|
+
? targetDir.replace(os.homedir(), '~')
|
|
151
|
+
: targetDir.replace(process.cwd(), '.');
|
|
48
152
|
|
|
49
|
-
|
|
153
|
+
console.log(` Uninstalling from ${cyan}${locationLabel}${reset}\n`);
|
|
50
154
|
|
|
51
|
-
|
|
52
|
-
console.log(
|
|
53
|
-
console.log(
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
155
|
+
if (!fs.existsSync(targetDir)) {
|
|
156
|
+
console.log(` ${yellow}⚠${reset} Directory does not exist: ${locationLabel}`);
|
|
157
|
+
console.log(` Nothing to uninstall.\n`);
|
|
158
|
+
return;
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
let removed = false;
|
|
162
|
+
|
|
163
|
+
// Remove statusline.sh
|
|
164
|
+
const statuslinePath = path.join(targetDir, 'statusline.sh');
|
|
165
|
+
if (fs.existsSync(statuslinePath)) {
|
|
166
|
+
fs.unlinkSync(statuslinePath);
|
|
167
|
+
console.log(` ${green}✓${reset} Removed statusline.sh`);
|
|
168
|
+
removed = true;
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
// Clean up settings.json
|
|
172
|
+
const settingsPath = path.join(targetDir, 'settings.json');
|
|
173
|
+
if (fs.existsSync(settingsPath)) {
|
|
174
|
+
const settings = readSettings(settingsPath);
|
|
175
|
+
|
|
176
|
+
if (settings.statusLine && settings.statusLine.command &&
|
|
177
|
+
settings.statusLine.command.includes('statusline.sh')) {
|
|
178
|
+
delete settings.statusLine;
|
|
179
|
+
writeSettings(settingsPath, settings);
|
|
180
|
+
console.log(` ${green}✓${reset} Removed statusline from settings.json`);
|
|
181
|
+
removed = true;
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
// Also clean up old format
|
|
185
|
+
if (settings.status_line) {
|
|
186
|
+
delete settings.status_line;
|
|
187
|
+
writeSettings(settingsPath, settings);
|
|
188
|
+
removed = true;
|
|
189
|
+
}
|
|
190
|
+
}
|
|
191
|
+
|
|
192
|
+
if (!removed) {
|
|
193
|
+
console.log(` ${yellow}⚠${reset} No statusline configuration found.`);
|
|
194
|
+
}
|
|
195
|
+
|
|
196
|
+
console.log(`
|
|
197
|
+
${green}Done!${reset} Statusline has been removed.
|
|
198
|
+
Restart Claude Code to see the change.
|
|
199
|
+
`);
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
/**
|
|
203
|
+
* Install statusline
|
|
204
|
+
*/
|
|
205
|
+
function install(isGlobal) {
|
|
206
|
+
const targetDir = isGlobal ? getGlobalDir() : getLocalDir();
|
|
207
|
+
const locationLabel = isGlobal
|
|
208
|
+
? targetDir.replace(os.homedir(), '~')
|
|
209
|
+
: targetDir.replace(process.cwd(), '.');
|
|
210
|
+
|
|
211
|
+
console.log(` Installing to ${cyan}${locationLabel}${reset}\n`);
|
|
212
|
+
|
|
213
|
+
// Ensure directory exists
|
|
214
|
+
if (!fs.existsSync(targetDir)) {
|
|
215
|
+
console.log(` ${dim}Creating ${locationLabel}...${reset}`);
|
|
216
|
+
fs.mkdirSync(targetDir, { recursive: true });
|
|
217
|
+
}
|
|
218
|
+
|
|
219
|
+
// Copy statusline.sh
|
|
220
|
+
const statuslineSrc = path.join(__dirname, '..', 'statusline.sh');
|
|
221
|
+
const statuslineDest = path.join(targetDir, 'statusline.sh');
|
|
222
|
+
fs.copyFileSync(statuslineSrc, statuslineDest);
|
|
223
|
+
fs.chmodSync(statuslineDest, '755');
|
|
224
|
+
console.log(` ${green}✓${reset} Installed statusline.sh`);
|
|
225
|
+
|
|
226
|
+
// Update settings.json
|
|
227
|
+
const settingsPath = path.join(targetDir, 'settings.json');
|
|
228
|
+
const settings = readSettings(settingsPath);
|
|
229
|
+
|
|
230
|
+
// Check for existing statusline
|
|
231
|
+
const hasExisting = settings.statusLine != null || settings.status_line != null;
|
|
232
|
+
|
|
233
|
+
if (hasExisting && !hasForce) {
|
|
234
|
+
const existingCmd = settings.statusLine?.command || settings.status_line?.script || '(custom)';
|
|
235
|
+
console.log(`
|
|
236
|
+
${yellow}⚠${reset} Existing statusline detected
|
|
237
|
+
${dim}Current: ${existingCmd}${reset}
|
|
238
|
+
|
|
239
|
+
Use ${cyan}--force${reset} to replace it, or keep your current config.
|
|
240
|
+
${dim}The statusline.sh file has been installed - you can switch anytime.${reset}
|
|
241
|
+
`);
|
|
242
|
+
} else {
|
|
243
|
+
// Remove old format if present
|
|
244
|
+
if (settings.status_line) {
|
|
245
|
+
delete settings.status_line;
|
|
246
|
+
}
|
|
247
|
+
|
|
248
|
+
// Set new format
|
|
249
|
+
settings.statusLine = {
|
|
250
|
+
type: 'command',
|
|
251
|
+
command: statuslineDest
|
|
252
|
+
};
|
|
253
|
+
|
|
254
|
+
writeSettings(settingsPath, settings);
|
|
255
|
+
console.log(` ${green}✓${reset} Configured settings.json`);
|
|
256
|
+
}
|
|
257
|
+
|
|
258
|
+
// Success message
|
|
259
|
+
console.log(`
|
|
260
|
+
${green}━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━${reset}
|
|
261
|
+
${green}✓${reset} ${bold}Installation complete!${reset}
|
|
262
|
+
${green}━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━${reset}
|
|
263
|
+
|
|
264
|
+
${cyan}Restart Claude Code${reset} to see your new statusline.
|
|
265
|
+
|
|
266
|
+
${dim}Tip: Works great with GSD (Get Shit Done)!${reset}
|
|
267
|
+
${dim} npx get-shit-done-cc${reset}
|
|
268
|
+
|
|
269
|
+
${dim}Issues? ${reset}${cyan}github.com/Buckits/claude-statusline${reset}
|
|
270
|
+
`);
|
|
271
|
+
}
|
|
272
|
+
|
|
273
|
+
/**
|
|
274
|
+
* Interactive prompt for install location
|
|
275
|
+
*/
|
|
276
|
+
function promptLocation() {
|
|
277
|
+
if (!process.stdin.isTTY) {
|
|
278
|
+
console.log(` ${dim}Non-interactive mode, defaulting to global install${reset}\n`);
|
|
279
|
+
install(true);
|
|
280
|
+
return;
|
|
281
|
+
}
|
|
282
|
+
|
|
283
|
+
console.log(features);
|
|
284
|
+
console.log(example);
|
|
285
|
+
|
|
286
|
+
const rl = readline.createInterface({
|
|
287
|
+
input: process.stdin,
|
|
288
|
+
output: process.stdout
|
|
289
|
+
});
|
|
290
|
+
|
|
291
|
+
let answered = false;
|
|
292
|
+
|
|
293
|
+
rl.on('close', () => {
|
|
294
|
+
if (!answered) {
|
|
295
|
+
console.log(`\n ${yellow}Installation cancelled${reset}\n`);
|
|
296
|
+
process.exit(0);
|
|
297
|
+
}
|
|
298
|
+
});
|
|
299
|
+
|
|
300
|
+
const globalPath = getGlobalDir().replace(os.homedir(), '~');
|
|
301
|
+
|
|
302
|
+
console.log(`
|
|
303
|
+
${yellow}Where would you like to install?${reset}
|
|
304
|
+
|
|
305
|
+
${cyan}1${reset}) ${bold}Global${reset} ${dim}(${globalPath})${reset}
|
|
306
|
+
Available in all your projects
|
|
307
|
+
|
|
308
|
+
${cyan}2${reset}) ${bold}Local${reset} ${dim}(./.claude)${reset}
|
|
309
|
+
This project only
|
|
310
|
+
`);
|
|
311
|
+
|
|
312
|
+
rl.question(` Choice ${dim}[1]${reset}: `, (answer) => {
|
|
313
|
+
answered = true;
|
|
314
|
+
rl.close();
|
|
315
|
+
console.log('');
|
|
316
|
+
const choice = answer.trim() || '1';
|
|
317
|
+
install(choice !== '2');
|
|
318
|
+
});
|
|
319
|
+
}
|
|
320
|
+
|
|
321
|
+
// Main logic
|
|
322
|
+
if (hasGlobal && hasLocal) {
|
|
323
|
+
console.log(` ${red}✗${reset} Cannot specify both --global and --local\n`);
|
|
324
|
+
process.exit(1);
|
|
325
|
+
}
|
|
326
|
+
|
|
327
|
+
if (hasUninstall) {
|
|
328
|
+
if (!hasGlobal && !hasLocal) {
|
|
329
|
+
console.log(` ${red}✗${reset} --uninstall requires --global or --local\n`);
|
|
330
|
+
process.exit(1);
|
|
331
|
+
}
|
|
332
|
+
uninstall(hasGlobal);
|
|
333
|
+
} else if (hasGlobal || hasLocal) {
|
|
334
|
+
install(hasGlobal);
|
|
335
|
+
} else {
|
|
336
|
+
promptLocation();
|
|
337
|
+
}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@buckits/claude-statusline",
|
|
3
|
-
"version": "2.
|
|
4
|
-
"description": "
|
|
3
|
+
"version": "2.3.1",
|
|
4
|
+
"description": "The statusline Claude Code deserves - gradient progress bar, auto-compact threshold marker, git status, cost tracking, 2-line dashboard",
|
|
5
5
|
"bin": {
|
|
6
6
|
"claude-statusline": "./bin/install.js"
|
|
7
7
|
},
|
|
@@ -14,7 +14,15 @@
|
|
|
14
14
|
"claude-code",
|
|
15
15
|
"statusline",
|
|
16
16
|
"cli",
|
|
17
|
-
"terminal"
|
|
17
|
+
"terminal",
|
|
18
|
+
"progress-bar",
|
|
19
|
+
"git-status",
|
|
20
|
+
"context-window",
|
|
21
|
+
"anthropic",
|
|
22
|
+
"ai",
|
|
23
|
+
"developer-tools",
|
|
24
|
+
"gsd",
|
|
25
|
+
"get-shit-done"
|
|
18
26
|
],
|
|
19
27
|
"author": "Buckits",
|
|
20
28
|
"license": "MIT",
|
|
@@ -22,6 +30,10 @@
|
|
|
22
30
|
"type": "git",
|
|
23
31
|
"url": "https://github.com/Buckits/claude-statusline"
|
|
24
32
|
},
|
|
33
|
+
"homepage": "https://github.com/Buckits/claude-statusline#readme",
|
|
34
|
+
"bugs": {
|
|
35
|
+
"url": "https://github.com/Buckits/claude-statusline/issues"
|
|
36
|
+
},
|
|
25
37
|
"engines": {
|
|
26
38
|
"node": ">=14"
|
|
27
39
|
}
|