Skip to content

Commit 68c73f2

Browse files
authored
feat(install): prompt for setup mode and run p10k configure after init (#30)
## Summary - `install.sh` now asks the user to choose between `setup` (interactive, pick each step) and `init` (non-interactive, recommended defaults) when invoked without arguments; passing a command directly still bypasses the prompt - `init` mode now runs `p10k configure` at the end so users get their prompt theme set up immediately - `AGENTS.md`: added **Documentation Sync — REQUIRED** section enforcing that `README.md` and `README.zh-CN.md` must always be updated together - `README.md` + `README.zh-CN.md`: updated curl install behavior description and `init` feature list to reflect both changes above ## Testing All 189 tests pass (`npm test`).
1 parent 6a35372 commit 68c73f2

6 files changed

Lines changed: 108 additions & 41 deletions

File tree

AGENTS.md

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,3 +76,15 @@ This step must remain idempotent.
7676

7777
- `README.md`: end-user usage, installed tools, resulting file layout
7878
- `AGENTS.md`: implementation details, architecture, contributor guidance
79+
80+
## Documentation Sync — REQUIRED
81+
82+
`README.md` is the source of truth. `README.zh-CN.md` is its Simplified Chinese translation.
83+
84+
**You MUST update both files in the same commit** whenever changes affect user-facing content (features, commands, file paths, install behavior, directory layout). Updating one without the other is never acceptable.
85+
86+
Checklist for README changes:
87+
- Paths and directory structures match between both files
88+
- Command tables and descriptions reflect the current behavior
89+
- `install.sh` default behavior is accurately described in both files
90+
- The installed file layout section reflects the current shipped config structure

README.md

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,13 @@ When you run suitup locally from the repo, use a zsh session. The curl installer
4848
curl -fsSL https://raw.githubusercontent.com/ChangeHow/suitup/main/install.sh | bash
4949
```
5050

51-
The installer now defaults to `init`, bootstraps missing `zsh` and Node.js/npm when possible, downloads a temporary copy of the repo, runs `npm ci`, and launches suitup inside `zsh`.
51+
The installer bootstraps missing `zsh` and Node.js/npm when possible, downloads a temporary copy of the repo, runs `npm ci`, then asks whether you want interactive `setup` or non-interactive `init` before launching inside `zsh`.
52+
53+
You can also pass a command directly to skip the prompt:
54+
55+
```bash
56+
curl -fsSL https://raw.githubusercontent.com/ChangeHow/suitup/main/install.sh | bash -s -- init
57+
```
5258

5359
`init` is a non-interactive quick-start path that uses recommended defaults:
5460

@@ -58,14 +64,15 @@ The installer now defaults to `init`, bootstraps missing `zsh` and Node.js/npm w
5864
- install recommended CLI tools and frontend tooling
5965
- install recommended GUI apps on macOS
6066
- write shared aliases
67+
- run `p10k configure` at the end to set up your prompt theme
6168

62-
You can also pass a specific command to the installer:
69+
You can also pass any other command:
6370

6471
```bash
6572
curl -fsSL https://raw.githubusercontent.com/ChangeHow/suitup/main/install.sh | bash -s -- clean
6673
```
6774

68-
If you want append mode directly without the prompt:
75+
If you want append mode directly:
6976

7077
```bash
7178
curl -fsSL https://raw.githubusercontent.com/ChangeHow/suitup/main/install.sh | bash -s -- append

README.zh-CN.md

Lines changed: 61 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -14,14 +14,14 @@
1414
## 特性
1515

1616
- 基于 [@clack/prompts](https://github.com/bombshell-dev/clack) 的交互式终端界面
17-
- suitup 现在只支持 zsh;所有命令都需要在 zsh 会话中运行
17+
- suitup 只支持 zsh;所有命令都需要在 zsh 会话中运行
1818
- 模块化步骤选择,只安装你需要的内容
1919
- **追加模式**:向现有 `.zshrc` 追加推荐配置,不强制覆盖
2020
- **PATH 迁移模式**:把 `.zshrc` 里的 PATH / 工具初始化行迁移到 `~/.config/zsh/core/paths.zsh`
2121
- **验证模式**:检查安装完整性
2222
- **清理模式**:删除 suitup 生成的配置
2323
- 提供 `--help`,方便快速查看命令
24-
- 修改 Shell 启动配置前,会先把现有 zsh 启动文件备份到 `~/.config/suitup/backups/`
24+
- 修改 Shell 启动配置前,会先把现有 zsh 启动文件备份到 `~/.config/zsh/backups/`
2525
- Powerlevel10k 为可选项;推荐开启,因为它在大型 Git 仓库里的异步 git 状态会更流畅
2626
- 幂等执行,可安全重复运行
2727
- 不包含私有/公司特定内容
@@ -40,23 +40,39 @@ Suitup 可以帮你初始化 Zsh 和 Homebrew,但更稳妥的路径仍然是
4040

4141
### 安装并运行
4242

43-
suitup 现在默认你已经安装好 zsh,并且当前就在 zsh 会话里运行命令
43+
在本地从仓库运行 suitup 时,请使用 zsh 会话。curl 安装脚本可以在全新机器上自动补全缺少的依赖
4444

4545
### 通过 curl 快速安装
4646

4747
```bash
4848
curl -fsSL https://raw.githubusercontent.com/ChangeHow/suitup/main/install.sh | bash
4949
```
5050

51-
这个安装脚本会先询问你要走 `init`(完整 setup)还是 `append`(给现有 `.zshrc` 做增量补充),然后临时下载仓库、执行 `npm ci`最后在 `zsh` 中启动对应的 `node src/cli.js` 命令
51+
安装脚本会在必要时自动安装 `zsh` 和 Node.js/npm,临时下载仓库,执行 `npm ci`然后询问你想要交互式 `setup` 还是非交互式 `init`,再在 `zsh` 中启动对应流程
5252

53-
如果你想直接执行某个命令,也可以这样传参:
53+
你也可以直接传入命令来跳过询问:
54+
55+
```bash
56+
curl -fsSL https://raw.githubusercontent.com/ChangeHow/suitup/main/install.sh | bash -s -- init
57+
```
58+
59+
`init` 是非交互式快速初始化路径,使用推荐默认值:
60+
61+
- 按需安装包管理器和 zsh
62+
- 安装分层 zsh 配置
63+
- 安装 zinit + Powerlevel10k 预设
64+
- 安装推荐 CLI 工具和前端工具链
65+
- 在 macOS 上安装推荐 GUI 应用
66+
- 写入共享 aliases
67+
- 最后运行 `p10k configure` 完成提示符主题配置
68+
69+
你也可以传入其他命令:
5470

5571
```bash
5672
curl -fsSL https://raw.githubusercontent.com/ChangeHow/suitup/main/install.sh | bash -s -- clean
5773
```
5874

59-
如果你想跳过提示、直接进入 append 模式,也可以这样运行
75+
如果想直接进入 append 模式:
6076

6177
```bash
6278
curl -fsSL https://raw.githubusercontent.com/ChangeHow/suitup/main/install.sh | bash -s -- append
@@ -75,6 +91,7 @@ node src/cli.js
7591

7692
| 命令 | 说明 |
7793
|------|------|
94+
| `node src/cli.js init` | 非交互式快速初始化,使用推荐默认值 |
7895
| `node src/cli.js` | 完整交互式安装(默认) |
7996
| `node src/cli.js setup` | 同上 |
8097
| `node src/cli.js append` | 追加配置到已有 `.zshrc` |
@@ -89,7 +106,7 @@ node src/cli.js
89106

90107
交互式步骤如下:
91108

92-
1. **Bootstrap** — 包管理器 + Zsh(macOS 可安装/跳过 Homebrew;Linux 可选 apt-get/dnf/yum/brew/跳过)
109+
1. **Bootstrap** — 包管理器 + Zsh
93110
2. **Zsh Config** — 创建 `~/.config/zsh/` 分层结构
94111
3. **Plugin Manager** — zinit(推荐)或跳过,仅保留原生 zsh
95112
4. **Prompt Preset** — Powerlevel10k(推荐)或基础 zsh prompt
@@ -101,17 +118,17 @@ node src/cli.js
101118
10. **Vim Config** — 基础 Vim 配置
102119
11. **Dock Cleanup** — 清理 macOS Dock
103120

104-
在 suitup 修改 Shell 启动配置前,会先把现有 `.zshrc``.zprofile``.zshenv``.zlogin` 等 zsh 启动文件备份到 `~/.config/suitup/backups/`
121+
在 suitup 修改 Shell 启动配置前,会先把现有 `.zshrc``.zprofile``.zshenv``.zlogin` 等 zsh 启动文件备份到 `~/.config/zsh/backups/`
105122

106123
如果你选择 Powerlevel10k,suitup 会保持安装过程非交互;当缺少 `~/.p10k.zsh` 时,会先回退到基础 prompt,等你之后自行运行 `p10k configure` 再启用。
107124

108125
Bootstrap 细节:
109126

110127
- macOS:安装 Homebrew,或跳过包管理器初始化
111128
- Linux:可选 `apt-get``dnf``yum``brew`,或直接跳过
112-
- 如果 Homebrew 已经安装在非默认位置,suitup 现在会在 Zsh 启动时自动尝试常见 `shellenv` 路径
113-
- suitup 现在也会生成一个精简的 `~/.zshenv`,保证非交互式 shell 也能加载共享环境变量和 PATH
114-
- 当 fnm 安装 Node.js 后,suitup 会把 `fnm` 自身和该默认 Node 版本一起放进 PATH,确保交互式/非交互式 shell 下的 `fnm``node``npm` 和全局 CLI 都优先指向 fnm 管理的路径
129+
- 如果 Homebrew 已经安装在非默认位置,suitup 会在 Zsh 启动时自动尝试常见 `shellenv` 路径
130+
- suitup 也会生成一个精简的 `~/.zshenv`,保证非交互式 shell 也能加载共享环境变量和 PATH
131+
- 当 fnm 安装 Node.js 后,suitup 会把 `fnm` 自身和该默认 Node 版本一起放进 PATH,确保交互式/非交互式 shell 下的 `fnm``node``npm` 和全局 CLI 都能正确解析
115132

116133
### Append(追加)
117134

@@ -126,7 +143,7 @@ node src/cli.js append
126143
- aliases
127144
- zinit 插件
128145
- Powerlevel10k prompt 或基础 prompt 预设(会替换 `~/.config/zsh/shared/prompt.zsh`
129-
- 工具初始化(atuin/fzf/zoxide/fnm)
146+
- 工具初始化(atuinfzfzoxidefnm)
130147
- Zsh 选项(history/completion)
131148
- 环境变量
132149
- 启动性能报告
@@ -152,7 +169,7 @@ node src/cli.js migrate-paths
152169

153170
-`.zshrc` 中提取识别到的 PATH 相关配置
154171
- 追加到 `~/.config/zsh/core/paths.zsh`
155-
- 先创建 `~/.config/suitup/backups/` 备份
172+
- 先创建 `~/.config/zsh/backups/` 备份
156173
- 迁移后执行 Zsh 语法检查
157174
- 如果校验失败则自动回滚
158175

@@ -164,8 +181,8 @@ node src/cli.js clean
164181

165182
尽量安全地卸载 suitup 管理的配置:
166183

167-
- 若存在备份,优先恢复最近一次非 suitup 版本`~/.zshrc` / `~/.zshenv`
168-
- 对仍与项目模板一致的文件,删除 `~/.config/zsh/` `~/.config/suitup/` 下的 suitup 生成内容
184+
- 若存在备份,优先恢复最近一次"非 suitup 版本"`~/.zshrc` / `~/.zshenv`
185+
- 对仍与项目模板一致的文件,删除 `~/.config/zsh/` 下的 suitup 生成内容
169186
- 如果你用过 `append`,会从现有 `~/.zshrc` 中移除 `# >>> suitup/... >>>` 标记块
170187
- 对用户自己改过的文件会保留,不会盲删
171188

@@ -209,7 +226,7 @@ node src/cli.js --help
209226

210227
## 安装后的目录结构
211228

212-
```text
229+
```
213230
~/.zshrc # 轻量入口
214231
~/.zshenv # 非交互式 shell 的最小环境入口
215232
~/.config/zsh/
@@ -219,32 +236,43 @@ node src/cli.js --help
219236
paths.zsh # PATH 与工具引导配置
220237
options.zsh # Zsh 选项
221238
shared/
222-
tools.zsh # 工具初始化(带缓存)
223-
prompt.zsh # 提示符主题
239+
tools.zsh # 工具初始化编排入口
240+
tools/
241+
_loader.zsh # _load_tool_config() + 版本化缓存
242+
fzf.zsh # FZF 环境变量、初始化、Ctrl-T 组件
243+
runtime.zsh # zoxide + fnm
244+
atuin.zsh # Atuin 历史(占用 Ctrl-R)
245+
bun.zsh # Bun 异步补全
246+
plugins.zsh # zinit 插件声明
247+
highlighting.zsh # zsh-syntax-highlighting 样式
248+
aliases.zsh # 共享 aliases
249+
completion.zsh # 原生补全配置
250+
prompt.zsh # 提示符主题(p10k)
224251
local/
225252
machine.zsh # 机器本地覆盖
226-
secrets.zsh # 个人密钥(手动创建)
227-
~/.config/suitup/
228-
aliases # Shell aliases
229-
zinit-plugins # Zinit 插件配置
230-
config.vim # Vim 配置
253+
config.vim # Vim 配置
254+
secrets.zsh # 个人密钥(手动创建,不纳入 git)
231255
```
232256

233-
## 系统要求
234-
235-
- Node.js >= 18
236-
- 已安装 Zsh
237-
- 需要在 zsh 会话中运行 suitup(`echo $SHELL` 结果应以 `zsh` 结尾)
238-
- macOS(完整支持)
239-
- Linux(支持 bootstrap 包管理器选择;其余安装步骤当前仍以 Homebrew 生态为主)
240-
241257
## 测试
242258

243259
```bash
244-
npm test
245-
npm run test:watch
260+
npm test # 运行全套测试
261+
npm run test:watch # 监视模式
246262
```
247263

264+
测试在沙箱临时目录中运行。
265+
266+
实现细节和架构说明见 `AGENTS.md`
267+
268+
## 系统要求
269+
270+
- macOS(完整支持,在 Sonoma+ 上测试)
271+
- Linux(支持 bootstrap 包管理器选择;其余安装步骤当前仍以 Homebrew 生态为主)
272+
- 本地运行需要 Node.js >= 18;curl 安装脚本会在可能时自动安装
273+
- 本地运行需要 Zsh;curl 安装脚本会在可能时自动安装
274+
- 需要在 zsh 会话中运行 suitup(`echo $SHELL` 结果应以 `zsh` 结尾)
275+
248276
## 许可证
249277

250278
[Apache-2.0](LICENSE)

install.sh

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -194,9 +194,22 @@ fi
194194
ensure_zsh "${PACKAGE_MANAGER}"
195195
ensure_node_runtime "${PACKAGE_MANAGER}"
196196

197-
CLI_COMMAND="${1:-init}"
198197
if [[ $# -gt 0 ]]; then
198+
CLI_COMMAND="$1"
199199
shift
200+
elif [[ -r /dev/tty ]]; then
201+
echo '' >&2
202+
echo 'How would you like to run suitup?' >&2
203+
echo ' 1) setup — interactive, choose each step yourself' >&2
204+
echo ' 2) init — non-interactive, install everything with recommended defaults' >&2
205+
echo '' >&2
206+
read -r -p 'Enter 1 or 2 [default: 1]: ' _suitup_choice < /dev/tty
207+
case "${_suitup_choice}" in
208+
2) CLI_COMMAND="init" ;;
209+
*) CLI_COMMAND="setup" ;;
210+
esac
211+
else
212+
CLI_COMMAND="setup"
200213
fi
201214

202215
case "${CLI_COMMAND}" in

src/setup.js

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ import pc from "picocolors";
33
import { existsSync } from "node:fs";
44
import { homedir } from "node:os";
55
import { join } from "node:path";
6+
import { spawnSync } from "node:child_process";
67
import { bootstrap } from "./steps/bootstrap.js";
78
import { installZinit } from "./steps/plugin-manager.js";
89
import { CLI_TOOLS, installCliTools } from "./steps/cli-tools.js";
@@ -322,7 +323,12 @@ export async function runSetup({ defaults = false } = {}) {
322323
}
323324

324325
if (promptTheme === "p10k" && !existsSync(join(homedir(), ".p10k.zsh"))) {
325-
p.log.info("Powerlevel10k is selected, but `~/.p10k.zsh` was not found. Suitup keeps a basic prompt until you run `p10k configure` in zsh, which avoids dropping you into an interactive wizard during setup.");
326+
if (defaults) {
327+
p.log.step("Launching Powerlevel10k configuration wizard...");
328+
spawnSync("zsh", ["-lc", "p10k configure"], { stdio: "inherit" });
329+
} else {
330+
p.log.info("Powerlevel10k is selected, but `~/.p10k.zsh` was not found. Suitup keeps a basic prompt until you run `p10k configure` in zsh, which avoids dropping you into an interactive wizard during setup.");
331+
}
326332
}
327333

328334
p.outro(

tests/install-script.test.js

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -27,11 +27,12 @@ describe("install.sh", () => {
2727
expect(content).toContain("launch_cli");
2828
});
2929

30-
test("defaults to quick init when no command is provided", () => {
30+
test("prompts user to choose setup mode when no command is provided", () => {
3131
const content = readFileSync(INSTALL_SCRIPT, "utf-8");
3232

33-
expect(content).toContain('CLI_COMMAND="${1:-init}"');
34-
expect(content).not.toContain("Choose install mode:");
33+
expect(content).toContain("How would you like to run suitup?");
34+
expect(content).toContain("interactive, choose each step yourself");
35+
expect(content).toContain("non-interactive, install everything with recommended defaults");
3536
});
3637

3738
test("passes init directly to the CLI and validates supported commands", () => {

0 commit comments

Comments
 (0)