Skip to content

Commit 543be04

Browse files
committed
Initial commit
0 parents  commit 543be04

9 files changed

Lines changed: 1157 additions & 0 deletions

File tree

.github/workflows/release.yml

Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
name: Release
2+
3+
on:
4+
push:
5+
tags:
6+
- "v*"
7+
8+
permissions:
9+
contents: write
10+
11+
jobs:
12+
build:
13+
runs-on: ubuntu-latest
14+
strategy:
15+
matrix:
16+
goos: [windows, linux, darwin]
17+
goarch: [amd64, arm64]
18+
exclude:
19+
- goos: darwin
20+
goarch: amd64
21+
22+
steps:
23+
- name: Checkout
24+
uses: actions/checkout@v4
25+
26+
- name: Setup Go
27+
uses: actions/setup-go@v5
28+
with:
29+
go-version: "1.21"
30+
31+
- name: Build
32+
env:
33+
GOOS: ${{ matrix.goos }}
34+
GOARCH: ${{ matrix.goarch }}
35+
CGO_ENABLED: "0"
36+
run: |
37+
EXT=""
38+
if [ "${{ matrix.goos }}" = "windows" ]; then
39+
EXT=".exe"
40+
fi
41+
OUTPUT="ttab-${{ matrix.goos }}-${{ matrix.goarch }}${EXT}"
42+
go build -ldflags="-s -w" -o "$OUTPUT" .
43+
echo "ASSET_NAME=$OUTPUT" >> "$GITHUB_ENV"
44+
45+
- name: Upload Release Asset
46+
uses: softprops/action-gh-release@v2
47+
with:
48+
files: ${{ env.ASSET_NAME }}

.gitignore

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
# Binary
2+
ttab
3+
ttab.exe
4+
ttab-*
5+
6+
# Config (created at runtime)
7+
.terminal_tagger.json
8+
9+
# IDE
10+
.idea/
11+
.vscode/
12+
*.swp
13+
*.swo
14+
15+
# OS
16+
.DS_Store
17+
Thumbs.db

README.md

Lines changed: 112 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,112 @@
1+
# ttab — Terminal Tagger
2+
3+
Dynamically color your terminal tabs and set titles based on your current directory. Zero-latency, zero-dependency, cross-platform.
4+
5+
`ttab` injects a lightweight hook into your shell prompt. When you `cd` into a tagged directory, it instantly recolors the tab and updates the title — so you always know where you are at a glance.
6+
7+
## Supported Terminals
8+
9+
| Terminal | Tab Color | Text Contrast | Title |
10+
|---|---|---|---|
11+
| Windows Terminal ||||
12+
| iTerm2 || auto ||
13+
| GNOME Terminal ||||
14+
| Other (OSC-compatible) ||||
15+
16+
## Install
17+
18+
### Windows (PowerShell)
19+
20+
```powershell
21+
irm https://raw.githubusercontent.com/dpkay-io/ttab/main/install.ps1 | iex
22+
```
23+
24+
### macOS / Linux
25+
26+
```bash
27+
curl -fsSL https://raw.githubusercontent.com/dpkay-io/ttab/main/install.sh | sh
28+
```
29+
30+
## Usage
31+
32+
### Tag a directory
33+
34+
Navigate to any directory and tag it with a color:
35+
36+
```bash
37+
ttab set --color "#ff6b6b" --title "API"
38+
```
39+
40+
The `--title` flag is optional. If omitted, the folder name is used automatically.
41+
42+
### Clear a tag
43+
44+
Remove the color tag from the current directory:
45+
46+
```bash
47+
ttab clear
48+
```
49+
50+
### How it works
51+
52+
Once installed, `ttab` adds a tiny hook to your shell prompt. Every time you change directories, it:
53+
54+
1. Checks `~/.terminal_tagger.json` for a matching path
55+
2. Walks parent directories for inherited rules (tag `~/projects` and every subdirectory inherits it)
56+
3. Calculates optimal text contrast (white or black) using W3C luminance
57+
4. Emits escape sequences to color the tab and set the title
58+
59+
### Examples
60+
61+
```bash
62+
# Tag your API project red
63+
cd ~/projects/api
64+
ttab set --color "#ff6b6b" --title "API"
65+
66+
# Tag all projects with a base color (child dirs inherit)
67+
cd ~/projects
68+
ttab set --color "#4ecdc4" --title "Projects"
69+
70+
# Clear tagging
71+
ttab clear
72+
73+
# Manually trigger the hook (usually automatic)
74+
ttab hook /path/to/directory
75+
```
76+
77+
## Configuration
78+
79+
Tags are stored in `~/.terminal_tagger.json`:
80+
81+
```json
82+
{
83+
"/home/user/projects": {
84+
"color": "#4ecdc4",
85+
"title": "Projects"
86+
},
87+
"/home/user/projects/api": {
88+
"color": "#ff6b6b",
89+
"title": "API"
90+
}
91+
}
92+
```
93+
94+
You can edit this file directly if you prefer.
95+
96+
## Shell Support
97+
98+
| Shell | Profile | Hook Method |
99+
|---|---|---|
100+
| PowerShell | `$PROFILE` | `prompt` function wrapper |
101+
| Zsh | `~/.zshrc` | `precmd` via `add-zsh-hook` |
102+
| Bash | `~/.bashrc` | `PROMPT_COMMAND` |
103+
104+
## Building from Source
105+
106+
```bash
107+
go build -ldflags="-s -w" -o ttab .
108+
```
109+
110+
## License
111+
112+
MIT

go.mod

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
module github.com/dpkay-io/ttab
2+
3+
go 1.21

install.ps1

Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
#!/usr/bin/env pwsh
2+
# install.ps1 — Install ttab on Windows
3+
# Usage: irm https://raw.githubusercontent.com/dpkay-io/ttab/main/install.ps1 | iex
4+
5+
$ErrorActionPreference = "Stop"
6+
7+
$repo = "dpkay-io/ttab"
8+
$installDir = Join-Path $HOME ".terminal_tagger" "bin"
9+
$binaryName = "ttab.exe"
10+
11+
Write-Host ""
12+
Write-Host " ttab installer" -ForegroundColor Cyan
13+
Write-Host " ─────────────────────────────" -ForegroundColor DarkGray
14+
Write-Host ""
15+
16+
# ── Create install directory ──────────────────────────────────────────────────
17+
if (-not (Test-Path $installDir)) {
18+
New-Item -ItemType Directory -Path $installDir -Force | Out-Null
19+
Write-Host " Created $installDir" -ForegroundColor DarkGray
20+
}
21+
22+
# ── Detect architecture ──────────────────────────────────────────────────────
23+
$arch = switch ($env:PROCESSOR_ARCHITECTURE) {
24+
"ARM64" { "arm64" }
25+
default { "amd64" }
26+
}
27+
Write-Host " Architecture: $arch" -ForegroundColor DarkGray
28+
29+
# ── Fetch latest release ─────────────────────────────────────────────────────
30+
Write-Host " Fetching latest release..." -ForegroundColor DarkGray
31+
$releaseUrl = "https://api.github.com/repos/$repo/releases/latest"
32+
33+
try {
34+
$release = Invoke-RestMethod -Uri $releaseUrl -Headers @{
35+
"User-Agent" = "ttab-installer"
36+
"Accept" = "application/vnd.github+json"
37+
}
38+
} catch {
39+
Write-Host " Error: Could not reach GitHub API." -ForegroundColor Red
40+
Write-Host " $_" -ForegroundColor DarkRed
41+
exit 1
42+
}
43+
44+
$assetName = "ttab-windows-$arch.exe"
45+
$asset = $release.assets | Where-Object { $_.name -eq $assetName }
46+
47+
if (-not $asset) {
48+
Write-Host " Error: Asset '$assetName' not found in the latest release." -ForegroundColor Red
49+
Write-Host " Available assets:" -ForegroundColor Yellow
50+
$release.assets | ForEach-Object { Write-Host " - $($_.name)" }
51+
exit 1
52+
}
53+
54+
# ── Download binary ───────────────────────────────────────────────────────────
55+
$downloadUrl = $asset.browser_download_url
56+
$targetPath = Join-Path $installDir $binaryName
57+
58+
Write-Host " Downloading $assetName..." -ForegroundColor DarkGray
59+
Invoke-WebRequest -Uri $downloadUrl -OutFile $targetPath -UseBasicParsing
60+
61+
if (-not (Test-Path $targetPath)) {
62+
Write-Host " Error: Download failed." -ForegroundColor Red
63+
exit 1
64+
}
65+
66+
Write-Host " Saved to $targetPath" -ForegroundColor DarkGray
67+
68+
# ── Add to user PATH ─────────────────────────────────────────────────────────
69+
$userPath = [Environment]::GetEnvironmentVariable("PATH", "User")
70+
if ($userPath -notlike "*$installDir*") {
71+
[Environment]::SetEnvironmentVariable("PATH", "$userPath;$installDir", "User")
72+
$env:PATH = "$env:PATH;$installDir"
73+
Write-Host " Added to PATH" -ForegroundColor DarkGray
74+
} else {
75+
Write-Host " Already in PATH" -ForegroundColor DarkGray
76+
}
77+
78+
# ── Install shell hook ───────────────────────────────────────────────────────
79+
Write-Host " Installing shell hook..." -ForegroundColor DarkGray
80+
& $targetPath install --profile $PROFILE
81+
82+
Write-Host ""
83+
Write-Host " ✓ ttab installed successfully!" -ForegroundColor Green
84+
Write-Host " Restart your terminal to activate." -ForegroundColor Yellow
85+
Write-Host ""

install.sh

Lines changed: 99 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,99 @@
1+
#!/bin/sh
2+
# install.sh — Install ttab on macOS / Linux
3+
# Usage: curl -fsSL https://raw.githubusercontent.com/dpkay-io/ttab/main/install.sh | sh
4+
5+
set -e
6+
7+
REPO="dpkay-io/ttab"
8+
INSTALL_DIR="$HOME/.terminal_tagger/bin"
9+
BINARY_NAME="ttab"
10+
11+
echo ""
12+
echo " ttab installer"
13+
echo " ─────────────────────────────"
14+
echo ""
15+
16+
# ── Create install directory ──────────────────────────────────────────────────
17+
mkdir -p "$INSTALL_DIR"
18+
19+
# ── Detect OS ─────────────────────────────────────────────────────────────────
20+
OS_RAW=$(uname -s)
21+
case "$OS_RAW" in
22+
Darwin) OS="darwin" ;;
23+
Linux) OS="linux" ;;
24+
*)
25+
echo " Error: Unsupported OS: $OS_RAW"
26+
exit 1
27+
;;
28+
esac
29+
30+
# ── Detect architecture ──────────────────────────────────────────────────────
31+
ARCH_RAW=$(uname -m)
32+
case "$ARCH_RAW" in
33+
x86_64)
34+
if [ "$OS" = "darwin" ]; then
35+
echo " Error: Mac Intel (darwin/amd64) is no longer supported."
36+
exit 1
37+
fi
38+
ARCH="amd64"
39+
;;
40+
aarch64|arm64) ARCH="arm64" ;;
41+
*)
42+
echo " Error: Unsupported architecture: $ARCH_RAW"
43+
exit 1
44+
;;
45+
esac
46+
47+
echo " Platform: ${OS}/${ARCH}"
48+
49+
# ── Download binary ───────────────────────────────────────────────────────────
50+
ASSET_NAME="ttab-${OS}-${ARCH}"
51+
DOWNLOAD_URL="https://github.com/$REPO/releases/latest/download/$ASSET_NAME"
52+
TARGET_PATH="$INSTALL_DIR/$BINARY_NAME"
53+
54+
echo " Downloading $ASSET_NAME..."
55+
if command -v curl >/dev/null 2>&1; then
56+
curl -fsSL "$DOWNLOAD_URL" -o "$TARGET_PATH"
57+
elif command -v wget >/dev/null 2>&1; then
58+
wget -qO "$TARGET_PATH" "$DOWNLOAD_URL"
59+
else
60+
echo " Error: Neither curl nor wget found. Please install one and retry."
61+
exit 1
62+
fi
63+
64+
chmod +x "$TARGET_PATH"
65+
echo " Saved to $TARGET_PATH"
66+
67+
# ── Add to PATH in shell profile ─────────────────────────────────────────────
68+
add_to_path() {
69+
local profile_file="$1"
70+
if [ -f "$profile_file" ] && grep -q "terminal_tagger" "$profile_file" 2>/dev/null; then
71+
echo " PATH already configured in $(basename "$profile_file")"
72+
return
73+
fi
74+
{
75+
echo ""
76+
echo "# ttab — terminal tagger"
77+
echo "export PATH=\"\$PATH:$INSTALL_DIR\""
78+
} >> "$profile_file"
79+
echo " Added to PATH in $(basename "$profile_file")"
80+
}
81+
82+
SHELL_NAME=$(basename "${SHELL:-/bin/sh}")
83+
case "$SHELL_NAME" in
84+
zsh) add_to_path "$HOME/.zshrc" ;;
85+
bash) add_to_path "$HOME/.bashrc" ;;
86+
*) add_to_path "$HOME/.profile" ;;
87+
esac
88+
89+
# Make ttab available in the current session
90+
export PATH="$PATH:$INSTALL_DIR"
91+
92+
# ── Install shell hook ───────────────────────────────────────────────────────
93+
echo " Installing shell hook..."
94+
"$TARGET_PATH" install
95+
96+
echo ""
97+
echo " ✓ ttab installed successfully!"
98+
echo " Restart your terminal to activate."
99+
echo ""

0 commit comments

Comments
 (0)