Created
July 13, 2026 02:34
-
-
Save brucevanhorn2/783d078e224f922c3165ca66d6021e8b to your computer and use it in GitHub Desktop.
Claude Code Status Line Script
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| { | |
| "respectGitignore": true, | |
| "attribution": { | |
| "commit": "", | |
| "pr": "" | |
| }, | |
| "permissions": { | |
| "deny": [ | |
| "Bash(rm -rf*)", | |
| "Bash(git push*)" | |
| ], | |
| "defaultMode": "bypassPermissions" | |
| }, | |
| "model": "sonnet", | |
| "statusLine": { | |
| "type": "command", | |
| "command": "~/.claude/statusline.sh", | |
| "padding": 1, | |
| "refreshInterval": 5 | |
| }, | |
| "enabledPlugins": { | |
| "frontend-design@claude-plugins-official": true, | |
| "github@claude-plugins-official": true, | |
| "feature-dev@claude-plugins-official": true, | |
| "understand-anything@understand-anything": true, | |
| "superpowers@claude-plugins-official": true | |
| }, | |
| "extraKnownMarketplaces": { | |
| "compound-engineering-plugin": { | |
| "source": { | |
| "source": "github", | |
| "repo": "EveryInc/compound-engineering-plugin" | |
| } | |
| }, | |
| "understand-anything": { | |
| "source": { | |
| "source": "github", | |
| "repo": "Lum1104/Understand-Anything" | |
| } | |
| } | |
| }, | |
| "effortLevel": "high", | |
| "advisorModel": "fable", | |
| "tui": "fullscreen", | |
| "voice": { | |
| "enabled": true, | |
| "mode": "hold" | |
| }, | |
| "skipDangerousModePermissionPrompt": true, | |
| "editorMode": "vim", | |
| "skipAutoPermissionPrompt": true, | |
| "hideVimModeIndicator": true | |
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| #!/usr/bin/env bash | |
| # =========================================================================== | |
| # Claude Code status line — MAXED OUT edition (Pro subscription build) | |
| # =========================================================================== | |
| # Line 1 · Identity : model ⟐effort ⟐think · 🔗repo · 🌳worktree · ⑂branch | |
| # +staged ~modified · PR#/state · +N dirs · agent · style | |
| # Line 2 · Context : gradient ctx bar · tok in/out · cache-hit% · 200k flag | |
| # Line 3 · Headroom : 5h gradient bar → reset · 7d gradient bar → reset | |
| # · session clock · notional $ (dimmed) | |
| # | |
| # Adapts to terminal width (COLUMNS): drops detail segments on narrow panes. | |
| # Repo name + PR badge are OSC 8 hyperlinks (Cmd/Ctrl-click) in iTerm2, | |
| # Kitty, WezTerm, Ghostty. Terminal.app shows them as plain text. | |
| # | |
| # Runs locally, zero API tokens. Requires: bash, jq, git (optional). | |
| # macOS (BSD date/stat) first, GNU/Linux fallbacks throughout. | |
| # | |
| # Pairs with: "hideVimModeIndicator": true in settings.json | |
| # (this script renders vim.mode itself, so the built-in -- INSERT -- is off) | |
| # =========================================================================== | |
| input=$(cat) | |
| # ---- palette (256-color) -------------------------------------------------- | |
| RESET='\033[0m'; BOLD='\033[1m'; DIM='\033[2m' | |
| CY='\033[38;5;44m'; GY='\033[38;5;245m'; WT='\033[38;5;252m' | |
| GRN='\033[38;5;46m'; YEL='\033[38;5;226m'; ORG='\033[38;5;208m'; RED='\033[38;5;196m' | |
| PUR='\033[38;5;141m'; BLU='\033[38;5;39m'; PNK='\033[38;5;213m' | |
| # gradient ramp: green -> yellow -> orange -> red | |
| RAMP=(46 82 118 154 190 226 220 214 208 202 196) | |
| WIDE=0; [ "${COLUMNS:-80}" -ge 100 ] && WIDE=1 # show detail segments? | |
| VWIDE=0; [ "${COLUMNS:-80}" -ge 130 ] && VWIDE=1 # show everything? | |
| # ---- helpers -------------------------------------------------------------- | |
| jqget() { printf '%s' "$input" | jq -r "$1" 2>/dev/null; } | |
| to_int() { [ -z "$1" ] && return; printf '%.0f' "$1" 2>/dev/null; } | |
| fmt_time() { # epoch -> "4:35PM" | |
| local e="$1"; [ -z "$e" ] && return | |
| date -r "$e" "+%-I:%M%p" 2>/dev/null || date -d "@$e" "+%-I:%M%p" 2>/dev/null | |
| } | |
| fmt_day() { # epoch -> "Mon 9AM" | |
| local e="$1"; [ -z "$e" ] && return | |
| date -r "$e" "+%a %-I%p" 2>/dev/null || date -d "@$e" "+%a %-I%p" 2>/dev/null | |
| } | |
| fmt_tok() { # 45500 -> "45k", 1250000 -> "1.2M" | |
| awk -v n="${1:-0}" 'BEGIN{ | |
| if(n=="") {print ""; exit} | |
| if(n>=1000000) {printf "%.1fM", n/1000000} | |
| else if(n>=1000) {printf "%dk", int(n/1000+0.5)} | |
| else {printf "%d", n} | |
| }' | |
| } | |
| fmt_dur() { # ms -> "12m" / "1h04m" | |
| local s=$(( ${1:-0} / 1000 )) h m | |
| h=$(( s/3600 )); m=$(( (s%3600)/60 )) | |
| if [ "$h" -gt 0 ]; then printf '%dh%02dm' "$h" "$m"; else printf '%dm' "$m"; fi | |
| } | |
| # gradient bar from a 0-100 pct. $1=pct (10 cells) | |
| gradbar() { | |
| local pct="${1:-0}" w=10 filled i idx out="" | |
| filled=$(( pct * w / 100 )); [ "$filled" -gt "$w" ] && filled=$w; [ "$filled" -lt 0 ] && filled=0 | |
| for ((i=0;i<w;i++)); do | |
| if [ "$i" -lt "$filled" ]; then | |
| idx=$(( i * (${#RAMP[@]}-1) / (w-1) )) | |
| out="${out}\033[38;5;${RAMP[$idx]}m█" | |
| else | |
| out="${out}\033[38;5;238m░" | |
| fi | |
| done | |
| printf '%s' "${out}${RESET}" | |
| } | |
| # OSC 8 hyperlink: $1=url $2=text | |
| link() { [ -z "$1" ] && { printf '%s' "$2"; return; }; printf '%s' "\033]8;;$1\a$2\033]8;;\a"; } | |
| # ---- scalar fields -------------------------------------------------------- | |
| MODEL=$(jqget '.model.display_name') | |
| DIR=$(jqget '.workspace.current_dir') | |
| PROJ=$(jqget '.workspace.project_dir // empty') | |
| WORKTREE=$(jqget '.workspace.git_worktree // empty') | |
| REPO=$(jqget '.workspace.repo.name // empty') | |
| ADDED=$(jqget '.workspace.added_dirs | length') | |
| EFFORT=$(jqget '.effort.level // empty') | |
| THINK=$(jqget '.thinking.enabled // false') | |
| STYLE=$(jqget '.output_style.name // empty') | |
| SESSNAME=$(jqget '.session_name // empty') | |
| AGENT=$(jqget '.agent.name // empty') | |
| VIM=$(jqget '.vim.mode // empty') | |
| SESSION_ID=$(jqget '.session_id') | |
| CTX=$(to_int "$(jqget '.context_window.used_percentage // 0')") | |
| TIN=$(jqget '.context_window.total_input_tokens // empty') | |
| TOUT=$(jqget '.context_window.total_output_tokens // empty') | |
| OVER200=$(jqget '.exceeds_200k_tokens // false') | |
| # cache-hit % from current_usage (null-safe, integer or empty) | |
| CACHE_HIT=$(jqget '(.context_window.current_usage // {}) | |
| | (.cache_read_input_tokens // 0) as $r | |
| | (.input_tokens // 0) as $i | |
| | (.cache_creation_input_tokens // 0) as $c | |
| | if ($i+$c+$r) > 0 then (($r*100)/($i+$c+$r)|floor) else empty end') | |
| FIVE=$(to_int "$(jqget '.rate_limits.five_hour.used_percentage // empty')") | |
| FIVE_R=$(jqget '.rate_limits.five_hour.resets_at // empty') | |
| WEEK=$(to_int "$(jqget '.rate_limits.seven_day.used_percentage // empty')") | |
| WEEK_R=$(jqget '.rate_limits.seven_day.resets_at // empty') | |
| COST=$(jqget '.cost.total_cost_usd // 0') | |
| DUR=$(jqget '.cost.total_duration_ms // 0') | |
| PR_NUM=$(jqget '.pr.number // empty') | |
| PR_URL=$(jqget '.pr.url // empty') | |
| PR_STATE=$(jqget '.pr.review_state // empty') | |
| # ---- git branch / dirty / remote (cached per session, 5s TTL) ------------- | |
| CACHE="/tmp/ccsl-git-${SESSION_ID:-default}" | |
| stale() { | |
| [ ! -f "$CACHE" ] && return 0 | |
| local now mt; now=$(date +%s) | |
| mt=$(stat -c %Y "$CACHE" 2>/dev/null || stat -f %m "$CACHE" 2>/dev/null || echo 0) | |
| [ $(( now - mt )) -gt 5 ] | |
| } | |
| if stale; then | |
| if git -C "$DIR" rev-parse --git-dir >/dev/null 2>&1; then | |
| B=$(git -C "$DIR" branch --show-current 2>/dev/null) | |
| S=$(git -C "$DIR" diff --cached --numstat 2>/dev/null | wc -l | tr -d ' ') | |
| M=$(git -C "$DIR" diff --numstat 2>/dev/null | wc -l | tr -d ' ') | |
| R=$(git -C "$DIR" remote get-url origin 2>/dev/null \ | |
| | sed -e 's#git@github.com:#https://github.com/#' -e 's#\.git$##') | |
| printf '%s|%s|%s|%s' "$B" "$S" "$M" "$R" > "$CACHE" | |
| else | |
| printf '|||' > "$CACHE" | |
| fi | |
| fi | |
| IFS='|' read -r BRANCH STAGED MODIFIED REMOTE < "$CACHE" | |
| # =========================================================================== | |
| # LINE 1 — identity | |
| # =========================================================================== | |
| L1="${CY}${BOLD}${MODEL}${RESET}" | |
| # effort glyph | |
| case "$EFFORT" in | |
| low) L1="${L1} ${GY}○${RESET}";; | |
| medium) L1="${L1} ${CY}◐${RESET}";; | |
| high) L1="${L1} ${ORG}●${RESET}";; | |
| xhigh) L1="${L1} ${PUR}◆${RESET}";; | |
| max) L1="${L1} ${RED}${BOLD}◆${RESET}";; | |
| esac | |
| [ "$THINK" = "true" ] && L1="${L1} ${PNK}💭${RESET}" | |
| [ -n "$VIM" ] && case "$VIM" in | |
| NORMAL) L1="${L1} ${DIM}[N]${RESET}";; | |
| INSERT) L1="${L1} ${GRN}[I]${RESET}";; | |
| VISUAL*) L1="${L1} ${YEL}[V]${RESET}";; | |
| esac | |
| # repo (clickable) / worktree / branch | |
| LOC="${REPO:-${DIR##*/}}" | |
| L1="${L1} ${DIM}·${RESET} ${BLU}🔗 $(link "$REMOTE" "$LOC")${RESET}" | |
| [ -n "$WORKTREE" ] && L1="${L1} ${DIM}·${RESET} ${GRN}🌳 ${WORKTREE}${RESET}" | |
| [ -n "$BRANCH" ] && L1="${L1} ${DIM}·${RESET} ${WT}⑂ ${BRANCH}${RESET}" | |
| GIT="" | |
| [ "${STAGED:-0}" -gt 0 ] 2>/dev/null && GIT="${GRN}+${STAGED}${RESET}" | |
| [ "${MODIFIED:-0}" -gt 0 ] 2>/dev/null && GIT="${GIT:+$GIT }${YEL}~${MODIFIED}${RESET}" | |
| [ -n "$GIT" ] && L1="${L1} ${GIT}" | |
| # PR badge (clickable) with review-state icon | |
| if [ -n "$PR_NUM" ]; then | |
| case "$PR_STATE" in | |
| approved) pic="${GRN}✓${RESET}";; | |
| changes_requested) pic="${RED}✗${RESET}";; | |
| pending) pic="${YEL}•${RESET}";; | |
| draft) pic="${DIM}◦${RESET}";; | |
| *) pic="";; | |
| esac | |
| L1="${L1} ${DIM}·${RESET} ${PUR}$(link "$PR_URL" "PR #${PR_NUM}")${RESET} ${pic}" | |
| fi | |
| # extras (wide terminals only) | |
| if [ "$WIDE" -eq 1 ]; then | |
| [ "${ADDED:-0}" -gt 0 ] 2>/dev/null && L1="${L1} ${DIM}·${RESET} ${GY}+${ADDED} dir$([ "$ADDED" -gt 1 ] && echo s)${RESET}" | |
| [ -n "$AGENT" ] && L1="${L1} ${DIM}·${RESET} ${PNK}🤖 ${AGENT}${RESET}" | |
| [ -n "$SESSNAME" ] && L1="${L1} ${DIM}·${RESET} ${GY}«${SESSNAME}»${RESET}" | |
| { [ -n "$STYLE" ] && [ "$STYLE" != "default" ]; } && L1="${L1} ${DIM}· ${STYLE}${RESET}" | |
| fi | |
| printf '%b\n' "$L1" | |
| # =========================================================================== | |
| # LINE 2 — context window | |
| # =========================================================================== | |
| L2="${GY}🧠 ctx${RESET} $(gradbar "$CTX") ${WT}${CTX}%${RESET}" | |
| if [ "$WIDE" -eq 1 ] && [ -n "$TIN" ]; then | |
| L2="${L2} ${DIM}·${RESET} ${GY}$(fmt_tok "$TIN") in / $(fmt_tok "$TOUT") out${RESET}" | |
| fi | |
| [ "$VWIDE" -eq 1 ] && [ -n "$CACHE_HIT" ] && L2="${L2} ${DIM}·${RESET} ${CY}⚡ ${CACHE_HIT}% cache${RESET}" | |
| [ "$OVER200" = "true" ] && L2="${L2} ${ORG}⚠ 200k+${RESET}" | |
| printf '%b\n' "$L2" | |
| # =========================================================================== | |
| # LINE 3 — subscription headroom + session | |
| # =========================================================================== | |
| L3="" | |
| if [ -n "$FIVE" ]; then | |
| seg="${GY}⏱ 5h${RESET} $(gradbar "$FIVE") ${WT}${FIVE}%${RESET}" | |
| rt=$(fmt_time "$FIVE_R"); [ -n "$rt" ] && seg="${seg} ${DIM}→ ${rt}${RESET}" | |
| L3="$seg" | |
| fi | |
| if [ -n "$WEEK" ]; then | |
| seg="${GY}📅 7d${RESET} $(gradbar "$WEEK") ${WT}${WEEK}%${RESET}" | |
| rd=$(fmt_day "$WEEK_R"); [ -n "$rd" ] && seg="${seg} ${DIM}→ ${rd}${RESET}" | |
| L3="${L3:+$L3 ${DIM}·${RESET} }$seg" | |
| fi | |
| if [ "$WIDE" -eq 1 ]; then | |
| L3="${L3:+$L3 ${DIM}·${RESET} }${GY}⧗ $(fmt_dur "$DUR")${RESET}" | |
| L3="${L3} ${DIM}·${RESET} ${DIM}$(printf '$%.2f' "$COST") notional${RESET}" | |
| fi | |
| [ -n "$L3" ] && printf '%b\n' "$L3" |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment