Skip to content

Commit 82c5801

Browse files
initial
0 parents  commit 82c5801

15 files changed

Lines changed: 1554 additions & 0 deletions

File tree

.github/workflows/ci.yml

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
name: CI
2+
3+
on:
4+
push:
5+
branches: [main]
6+
pull_request:
7+
branches: [main]
8+
9+
jobs:
10+
test:
11+
strategy:
12+
matrix:
13+
os: [ubuntu-latest, macos-latest, windows-latest]
14+
runs-on: ${{ matrix.os }}
15+
steps:
16+
- uses: actions/checkout@v4
17+
- uses: dtolnay/rust-toolchain@stable
18+
- run: cargo test --verbose
19+
- run: cargo clippy --all-targets -- -D warnings
20+
- run: cargo fmt -- --check

.github/workflows/release.yml

Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
name: Release
2+
3+
on:
4+
push:
5+
paths:
6+
- 'Cargo.toml'
7+
branches:
8+
- main
9+
10+
jobs:
11+
check-version:
12+
runs-on: ubuntu-latest
13+
outputs:
14+
version_changed: ${{ steps.check.outputs.changed }}
15+
version: ${{ steps.extract.outputs.version }}
16+
steps:
17+
- uses: actions/checkout@v4
18+
with:
19+
fetch-depth: 2
20+
21+
- name: Check if version changed
22+
id: check
23+
run: |
24+
if git diff HEAD^ HEAD -- Cargo.toml | grep -q '^[+-]version = '; then
25+
echo "changed=true" >> $GITHUB_OUTPUT
26+
else
27+
echo "changed=false" >> $GITHUB_OUTPUT
28+
fi
29+
30+
- name: Extract version
31+
id: extract
32+
if: steps.check.outputs.changed == 'true'
33+
run: |
34+
VERSION=$(grep '^version = ' Cargo.toml | head -1 | sed 's/version = "\(.*\)"/\1/')
35+
echo "version=$VERSION" >> $GITHUB_OUTPUT
36+
37+
build:
38+
needs: check-version
39+
if: needs.check-version.outputs.version_changed == 'true'
40+
strategy:
41+
matrix:
42+
include:
43+
- os: ubuntu-latest
44+
target: x86_64-unknown-linux-musl
45+
artifact_name: pik
46+
asset_name: pik-linux-x86_64
47+
- os: macos-latest
48+
target: x86_64-apple-darwin
49+
artifact_name: pik
50+
asset_name: pik-macos-x86_64
51+
- os: macos-latest
52+
target: aarch64-apple-darwin
53+
artifact_name: pik
54+
asset_name: pik-macos-aarch64
55+
- os: windows-latest
56+
target: x86_64-pc-windows-msvc
57+
artifact_name: pik.exe
58+
asset_name: pik-windows-x86_64.exe
59+
runs-on: ${{ matrix.os }}
60+
steps:
61+
- uses: actions/checkout@v4
62+
63+
- uses: dtolnay/rust-toolchain@stable
64+
with:
65+
targets: ${{ matrix.target }}
66+
67+
- name: Install musl-tools
68+
if: matrix.os == 'ubuntu-latest'
69+
run: sudo apt-get install -y musl-tools
70+
71+
- name: Build
72+
run: cargo build --release --target ${{ matrix.target }}
73+
74+
- name: Strip binary
75+
if: matrix.os != 'windows-latest'
76+
run: strip target/${{ matrix.target }}/release/${{ matrix.artifact_name }}
77+
78+
- name: Upload artifact
79+
uses: actions/upload-artifact@v4
80+
with:
81+
name: ${{ matrix.asset_name }}
82+
path: target/${{ matrix.target }}/release/${{ matrix.artifact_name }}
83+
84+
release:
85+
needs: [check-version, build]
86+
runs-on: ubuntu-latest
87+
permissions:
88+
contents: write
89+
steps:
90+
- uses: actions/checkout@v4
91+
92+
- name: Download artifacts
93+
uses: actions/download-artifact@v4
94+
with:
95+
path: artifacts
96+
97+
- name: Create release
98+
env:
99+
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
100+
run: |
101+
VERSION="${{ needs.check-version.outputs.version }}"
102+
gh release create "v$VERSION" \
103+
--title "v$VERSION" \
104+
--generate-notes \
105+
artifacts/*/* \
106+
|| echo "Release already exists"

.gitignore

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
/target/
2+
*.pdb
3+
*.swp
4+
*~
5+
.DS_Store
6+
Thumbs.db
7+
*.log
8+
Cargo.lock

CHANGELOG.md

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
# Changelog
2+
3+
## [0.1.0] - 2026-07-12
4+
5+
- Interactive line picker with centered bordered UI
6+
- Stdin and file input (`-f`), prompt header (`-p`)
7+
- Vim keybindings and arrow keys
8+
- Mouse click support
9+
- Color tier detection with `NO_COLOR` support
10+
- Exit codes: 0 (selected), 1 (error), 130 (cancelled)

CONTRIBUTING.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
# Contributing
2+
3+
Open an issue before writing code. Keep changes focused.
4+
5+
- Run `make check` (fmt + clippy + test) before submitting
6+
- No new dependencies without strong justification

Cargo.toml

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
[package]
2+
name = "pik"
3+
version = "0.1.0"
4+
edition = "2021"
5+
description = "The minimal interactive line picker for the command line"
6+
license = "MIT"
7+
repository = "https://github.com/programmersd21/pik"
8+
keywords = ["cli", "terminal", "picker", "selector", "interactive"]
9+
categories = ["command-line-utilities"]
10+
11+
[dependencies]
12+
crossterm = "0.28"
13+
unicode-width = "0.1"
14+
rand = "0.8"
15+
16+
[[bin]]
17+
name = "pik"
18+
path = "src/main.rs"

LICENSE

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
MIT License
2+
3+
Copyright (c) 2026 pik contributors
4+
5+
Permission is hereby granted, free of charge, to any person obtaining a copy
6+
of this software and associated documentation files (the "Software"), to deal
7+
in the Software without restriction, including without limitation the rights
8+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9+
copies of the Software, and to permit persons to whom the Software is
10+
furnished to do so, subject to the following conditions:
11+
12+
The above copyright notice and this permission notice shall be included in all
13+
copies or substantial portions of the Software.
14+
15+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21+
SOFTWARE.

Makefile

Lines changed: 179 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,179 @@
1+
.PHONY: help build release test clean install uninstall fmt check clippy lint ci demo all
2+
3+
# Detect OS - works on Windows (no uname) and Unix
4+
UNAME := $(shell uname -s 2>NUL)
5+
ifneq ($(UNAME),)
6+
DETECTED_OS := $(UNAME)
7+
BINARY := target/release/pik
8+
DEBUG_BINARY := target/debug/pik
9+
NULL_DEVICE := /dev/null
10+
WHICH := which
11+
else
12+
DETECTED_OS := Windows
13+
BINARY := target\release\pik.exe
14+
DEBUG_BINARY := target\debug\pik.exe
15+
NULL_DEVICE := NUL
16+
WHICH := where
17+
endif
18+
19+
# Default target
20+
help:
21+
@echo "pik - Makefile targets (OS: $(DETECTED_OS))"
22+
@echo ""
23+
@echo "Development:"
24+
@echo " make build Build debug binary"
25+
@echo " make release Build optimized binary"
26+
@echo " make test Run all tests"
27+
@echo " make fmt Format code"
28+
@echo " make clippy Run clippy lints"
29+
@echo " make check Run fmt + clippy + test"
30+
@echo " make ci Full CI check (fmt check + clippy + test)"
31+
@echo ""
32+
@echo "Installation:"
33+
@echo " make install Install binary to cargo bin"
34+
@echo " make uninstall Remove installed binary"
35+
@echo ""
36+
@echo "Cleanup:"
37+
@echo " make clean Remove build artifacts"
38+
@echo ""
39+
@echo "Demo:"
40+
@echo " make demo Generate demo.gif (requires VHS)"
41+
@echo ""
42+
@echo "Shortcuts:"
43+
@echo " make all Same as: make check"
44+
@echo " make lint Same as: make clippy"
45+
46+
# Build debug binary
47+
build:
48+
@echo "Building debug binary..."
49+
@cargo build
50+
@echo "✓ Debug build complete: $(DEBUG_BINARY)"
51+
52+
# Build optimized release binary
53+
release:
54+
@echo "Building release binary..."
55+
@cargo build --release
56+
@echo "✓ Release build complete: $(BINARY)"
57+
58+
# Run all tests
59+
test:
60+
@echo "Running tests..."
61+
@cargo test --all-targets
62+
@echo "✓ All tests passed"
63+
64+
# Format code
65+
fmt:
66+
@echo "Formatting code..."
67+
@cargo fmt
68+
@echo "✓ Code formatted"
69+
70+
# Check formatting without modifying files
71+
fmt-check:
72+
@echo "Checking code format..."
73+
@cargo fmt -- --check
74+
@echo "✓ Code format verified"
75+
76+
# Run clippy
77+
clippy:
78+
@echo "Running clippy..."
79+
@cargo clippy --all-targets -- -D warnings
80+
@echo "✓ Clippy checks passed"
81+
82+
# Alias for clippy
83+
lint: clippy
84+
85+
# Quick check (format + lint + test)
86+
check: fmt clippy test
87+
@echo ""
88+
@echo "✓✓✓ All checks passed ✓✓✓"
89+
90+
# Full CI check (non-modifying format check + clippy + test)
91+
ci: fmt-check clippy test
92+
@echo ""
93+
@echo "✓✓✓ CI checks passed ✓✓✓"
94+
95+
# Install binary
96+
install:
97+
@echo "Installing pik..."
98+
@cargo install --path .
99+
@echo "✓ Installed to cargo bin directory"
100+
@$(WHICH) pik >$(NULL_DEVICE) 2>&1 && $(WHICH) pik || echo "Note: Make sure cargo bin is in PATH"
101+
102+
# Uninstall binary
103+
uninstall:
104+
@echo "Uninstalling pik..."
105+
@cargo uninstall pik
106+
@echo "✓ Uninstalled"
107+
108+
# Clean build artifacts
109+
clean:
110+
@echo "Cleaning build artifacts..."
111+
@cargo clean
112+
@echo "✓ Cleaned"
113+
114+
# Generate demo (requires VHS)
115+
demo:
116+
@echo "Generating demo.gif..."
117+
ifdef OS
118+
ifeq ($(OS),Windows_NT)
119+
@where vhs >$(NULL_DEVICE) 2>&1 || (echo Error: VHS not found. Install from https://github.com/charmbracelet/vhs && exit 1)
120+
else
121+
@command -v vhs >$(NULL_DEVICE) 2>&1 || { echo "Error: VHS not found. Install from https://github.com/charmbracelet/vhs"; exit 1; }
122+
endif
123+
else
124+
@command -v vhs >$(NULL_DEVICE) 2>&1 || { echo "Error: VHS not found. Install from https://github.com/charmbracelet/vhs"; exit 1; }
125+
endif
126+
@vhs demo.tape
127+
@echo "✓ Demo generated: demo.gif"
128+
129+
# Default: run all checks
130+
all: check
131+
132+
# Development workflow: watch and test (requires cargo-watch)
133+
watch:
134+
ifdef OS
135+
ifeq ($(OS),Windows_NT)
136+
@where cargo-watch >$(NULL_DEVICE) 2>&1 || (echo Installing cargo-watch... && cargo install cargo-watch)
137+
else
138+
@command -v cargo-watch >$(NULL_DEVICE) 2>&1 || { echo "Installing cargo-watch..."; cargo install cargo-watch; }
139+
endif
140+
else
141+
@command -v cargo-watch >$(NULL_DEVICE) 2>&1 || { echo "Installing cargo-watch..."; cargo install cargo-watch; }
142+
endif
143+
@cargo watch -x test
144+
145+
# Show binary size
146+
size: release
147+
@echo ""
148+
@echo "Binary size:"
149+
ifdef OS
150+
ifeq ($(OS),Windows_NT)
151+
@powershell -Command "Get-Item $(BINARY) | Select-Object Name, @{Name='Size';Expression={'{0:N2} KB' -f ($_.Length / 1KB)}}"
152+
else
153+
@ls -lh $(BINARY) | awk '{print $$5 "\t" $$NF}'
154+
endif
155+
else
156+
@ls -lh $(BINARY) | awk '{print $$5 "\t" $$NF}'
157+
endif
158+
159+
# Benchmark build time
160+
bench-build:
161+
@echo "Benchmarking clean release build..."
162+
@cargo clean
163+
ifeq ($(DETECTED_OS),Windows)
164+
@powershell -Command "Measure-Command { cargo build --release | Out-Default } | Select-Object TotalSeconds"
165+
else
166+
@time cargo build --release
167+
endif
168+
169+
# Run a quick smoke test
170+
smoke: release
171+
@echo "Running smoke test..."
172+
@echo "Note: This requires manual interaction - press Ctrl+C to cancel"
173+
ifeq ($(DETECTED_OS),Windows)
174+
@echo option1& echo option2& echo option3 | $(BINARY) || echo "Manual verification needed"
175+
else
176+
@echo -e "option1\noption2\noption3" | $(BINARY) || echo "Manual verification needed"
177+
endif
178+
@echo "✓ Smoke test setup complete"
179+

0 commit comments

Comments
 (0)