Personal Rust CLI. Name joins Jacob and Taotao.
Bootstrap terminal tooling:
jt cli bootstrapInteractive bootstrap supports macOS, Debian/Ubuntu, and WSL on x86_64 and ARM64. It installs:
- Fish or Zsh and Starship with Catppuccin Mocha.
- bat, eza, fd, ripgrep, fzf, btop, zoxide, jq, tldr, git-delta, and lazygit.
- Fish Git abbreviations/functions plus
proxy-onandproxy-off. - Zellij when selected.
The command asks before mutation, changes the default shell, writes only jt-managed shell files, backs up replaced files, and configures git-delta globally. Fish users can explicitly enable proxy-on at shell startup; this option defaults to No and validates GitHub through http://127.0.0.1:7890 before exporting proxy variables. Ghostty, fonts, Node.js, fnm, and pnpm stay outside this bootstrap.
Install Ghostty on macOS:
jt ghostty installThis separate interactive command installs Ghostty and Maple Mono NF CN through Homebrew, then writes a jt-managed Ghostty configuration. It backs up replaced files and asks before mutation. Linux and WSL servers are rejected without installation.
Write project Zed settings from the live repository template:
jt zed-confThe command finds the current Git repository root and writes .zed/settings.json. Existing
different content is backed up beside the file before an atomic update. The template is fetched
over HTTPS from templates/zed/settings.json on main, so merging a
template-only change updates future command runs without releasing a new jt version.
Configure npm package release automation:
jt repo cicdCommand operates on current directory. It validates project, then creates only:
.github/workflows/npm-release.yml
Generated file calls reusable workflow in this repository. Version changes, CHANGELOG.md, Git tags, GitHub Releases, and npm publish all run in GitHub Actions. jt never runs those release operations locally and never stores NPM_TOKEN.
Initialize global Node/pnpm environment through Vite+:
jt node initThis interactive command supports macOS/Linux on x86_64 and ARM64. macOS Apple Silicon needs Rosetta 2 for the Node 14 x64 runtime. It:
- Installs or reuses Vite+, then prepares Node
14.21.3,16.19.0,20.11.0,22.21.0, and24.15.0. - Installs default pnpm, prewarms pnpm
7.4.1,9.7.0, and10.12.4, then installs nrm. - Configures npm mirror, nrm
taobao/zz, and Vite+ shell loaders. - Migrates globals whose npm inventory proves an npmjs/npmmirror registry source to Vite+.
- Freshly scans old nvm/fnm/Homebrew/pnpm/Bun state. It shows every cleanup action and asks again before deleting anything.
Both confirmations default to No. Canceling first confirmation makes no changes. Incomplete inventory blocks cleanup. Existing Vite+ installation and additive changes remain when a later stage fails or cleanup is declined.
PNPM/Bun package manifests do not prove install provenance. jt reports those globals as unreconstructable and retains PNPM_HOME/Bun targets instead of guessing a registry package or Bun global directory. After cleanup confirmation, jt fresh-checks both legacy inventory and every target Vite+ global before deleting old providers.
Recursive deletion is limited to exact known dedicated nvm/fnm roots. Custom manager roots and unverified fnm wrappers are reported and retained. Shell cleanup follows actual removable providers; a failed shell write stops all later provider deletion.
Write one JT icon into ./public:
jt icon 64
jt icon svgPass a directory as the fourth shell argument to override the destination:
jt icon 64 ./assets
jt icon svg ./assetsPNG sizes are 16, 24, 32, 48, 64, 128, 256, 512, and 1024. A PNG selector writes the matching original jt-<size>.png; svg creates jt.svg from its embedded markup. Commands work offline, create the destination directory, and refuse to overwrite an existing file.
./install.shThe script builds the current source with cargo build --release --locked, installs jt to ~/.local/bin, and verifies the installed binary. Override the directory when needed:
JT_INSTALL_DIR=/path/to/bin ./install.shInstall a published release, replacing vX.Y.Z with a tag from GitHub Releases:
cargo install --git https://github.com/JacobZyy/jt-cli --tag vX.Y.Z --locked --root "$HOME/.local"Upgrade an existing user-owned installation:
jt upgrade --check
jt upgrade
jt upgrade --dry-run --forcejt upgrade resolves an exact published GitHub Release and pins its Git commit, asks Cargo to build it in a temporary directory, verifies the staged binary, then atomically replaces ~/.local/bin/jt. A failed post-install version check restores the previous binary. --force reinstalls the current version. The command never runs a shell or sudo. Other paths and package-manager shims must use their original installer or manager. Cargo and Git remain required; prebuilt release assets and persistent rollback are not implemented yet.
- Single npm package hosted on GitHub, default branch
main - Valid
package.jsonwithname, SemVerversion,repository,scripts.test, andscripts.build - Exactly one
package-lock.jsonorpnpm-lock.yaml - pnpm projects declare an exact
packageManager, such aspnpm@10.15.0 - npm registry, with
publishConfig.registryabsent orhttps://registry.npmjs.org - Publishable package:
privateis absent orfalse
GitLab, workspaces, Yarn, and Bun are rejected explicitly in this first version.
- Run
jt repo cicd, commit generated workflow on a feature branch, then merge it through a PR. - In GitHub Actions settings, grant workflows read/write permission and allow GitHub Actions to create pull requests.
- In npm package settings, add GitHub Actions Trusted Publisher:
- organization or user: package repository owner
- repository: package repository name
- workflow filename:
npm-release.yml - allowed action:
npm publish
- Use Conventional Commits on
main, for examplefeat: add export command.
npm validates caller workflow in consuming repository, not central reusable workflow. Trusted Publishing also requires package.json.repository to match GitHub repository. Workflow uses GitHub-hosted runner, Node.js 24, npm OIDC, and no publish token.
Release flow:
- Merge a Conventional Commit PR into
main. - Install, test, build.
- release-please creates or updates Release PR from Conventional Commits.
- Merge Release PR.
- Same workflow validates again; release-please creates version,
CHANGELOG.md, tag, and GitHub Release. release_createdpublishes package to npm through Trusted Publishing.
Validation produces package tarball before release. Only isolated publish job receives OIDC permission; package lifecycle scripts are disabled during publish. If npm publish fails after GitHub Release creation, use Re-run failed jobs so publish reuses same release output and tarball.
Generated workflow pins reusable workflow to @v1.0.0; consuming repositories never execute mutable main with write and OIDC permissions.
Push features through a Conventional Commit PR. .github/workflows/release.yml runs release-please on main; its Release PR owns Cargo.toml, Cargo.lock, CHANGELOG.md, the Git tag, and the GitHub Release. Never version or tag jt locally.
cargo fmt --check
cargo clippy --locked --all-targets --all-features -- -D warnings
cargo test --lockedActivate repository pre-commit hook once per clone:
ln -s ../../.githooks/pre-commit .git/hooks/pre-commitEvery commit runs cargo test --locked --quiet. Failed tests abort commit. GitHub CI remains final required check because local hooks can be bypassed.
Use Conventional Commits because release-please derives versions and changelog entries from commits on main. Git does not activate repository hooks automatically, and --no-verify can bypass them. For squash merges, enforce Conventional Commit PR titles with GitHub rules or a server-side PR-title check.
release-please currently uses built-in GITHUB_TOKEN. GitHub suppresses workflows triggered by its Release PR. Repositories requiring PR checks need a bot bypass until optional GitHub App token support is added.
MIT