Compare commits
61 Commits
e77f561747
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
| a4c7f28849 | |||
| 8d68dfafd2 | |||
| f9d7d40e4e | |||
| d072bb491c | |||
| f011b5027d | |||
| 007a104ef3 | |||
| 41913d9a24 | |||
| 2cd41bcd16 | |||
| 7fccb75e4f | |||
| 8c0ada01b9 | |||
| 4e7ddff3eb | |||
| ba7e0bb7af | |||
| af82b03b3e | |||
| b84b747b76 | |||
| aec2625eaa | |||
| 40731eda73 | |||
| bd5b0d9772 | |||
| 0cc6294e44 | |||
| 883d551f8e | |||
| 27b265803c | |||
| 635ea270aa | |||
| 54c56501e4 | |||
| 1df2e87a6e | |||
| 2147d2917e | |||
| 82a148a894 | |||
| 7e5e05470a | |||
| f6e2f92da3 | |||
| 5583970878 | |||
| beeb9948f4 | |||
| 804e96a979 | |||
| fbb83ff013 | |||
| 8714184fbd | |||
| 895b3c2978 | |||
| 235b81c21e | |||
| 9a4582a752 | |||
| 2cd888e1cf | |||
| 75340604f1 | |||
| d6a0bf0cae | |||
| be247ff3b9 | |||
| d7e0aaf798 | |||
| 5f7ef35a34 | |||
| bf01c40ebb | |||
| 53f8c2ceb3 | |||
| a1ba07faf5 | |||
| d2f7210d1a | |||
| 77c2190f00 | |||
| ed69dba1ca | |||
| 4acff86a06 | |||
| 35ac63e068 | |||
| 3c6910cfb1 | |||
| 067608f4f8 | |||
| 1e78149a4f | |||
| 09463d0dbb | |||
| 82ab946ba1 | |||
| 50808a9ecf | |||
| 024ea2c676 | |||
| 9e610b89b2 | |||
| 8f26433357 | |||
| b9e8566cee | |||
| 2f6e3aea89 | |||
| 2a1fb40fd3 |
@@ -1,9 +0,0 @@
|
||||
keys:
|
||||
# imbytecat — derived from ~/.ssh/id_ed25519 via ssh-to-age
|
||||
- &imbytecat age1w74wqpmum6xa3mk5p7ya620e8mhn9afdyf30gh3fk44javxsmvssm4hs64
|
||||
|
||||
creation_rules:
|
||||
- path_regex: secrets/[^/]+\.(yaml|json|env)$
|
||||
key_groups:
|
||||
- age:
|
||||
- *imbytecat
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
## Overview
|
||||
|
||||
Nix flake managing 3 devices: Mac Mini, MacBook Air (both aarch64-darwin via nix-darwin), and a Windows PC via NixOS-WSL (x86_64-linux). Single user `imbytecat` everywhere.
|
||||
Nix flake — 3 devices (Mac Mini, MacBook Air: aarch64-darwin; WSL: x86_64-linux). Single user `imbytecat`. Uses **Lix**.
|
||||
|
||||
## Architecture
|
||||
|
||||
@@ -13,88 +13,75 @@ flake.nix
|
||||
└── nixosConfigurations.wsl (x86_64-linux)
|
||||
```
|
||||
|
||||
- `lib/default.nix` — builders: `mkDarwin`, `mkNixos`. All hosts get shared modules + home-manager + catppuccin + lazyvim-nix + sops-nix.
|
||||
- `modules/shared/` — both platforms: nixpkgs config, overlays, nix settings, Lix
|
||||
- `modules/darwin/` — macOS: system preferences, homebrew (casks/brews/masApps), fonts, fish shell, user
|
||||
- `modules/nixos/` — NixOS: base packages, docker, locale, user
|
||||
- `home/` — home-manager (shared across all hosts via `useGlobalPkgs`)
|
||||
- `hosts/*/` — per-host overrides (mac-mini: 24/7 server with sleep disabled; macbook-air: portable)
|
||||
- `overlays/` + `pkgs/` — custom packages (comment-checker)
|
||||
- `secrets/` — sops-encrypted secrets (age key derived from `~/.ssh/id_ed25519`)
|
||||
- `lib/default.nix` — `mkDarwin`/`mkNixos` builders, `sshKeys` (via `specialArgs`), `homeManagerConfig`
|
||||
- `modules/shared/` — cross-platform: Lix, overlays, fonts, fish, openssh, 1password
|
||||
- `modules/darwin/` — system preferences, homebrew, user
|
||||
- `modules/nixos/` — system packages, locale, docker, user
|
||||
- `home/` — home-manager (shared, `useGlobalPkgs`), catppuccin
|
||||
- `hosts/*/` — per-host overrides
|
||||
- `overlays/` + `pkgs/` — custom packages (`comment-checker`)
|
||||
|
||||
Config flows: `hosts/*` (host-specific) -> `modules/*` (platform) -> `home/*` (user-level, cross-platform)
|
||||
|
||||
## Nix implementation
|
||||
|
||||
All platforms use **Lix** (`nix.package = pkgs.lix` in `modules/shared/nix.nix`). Channels are disabled (`nix.channel.enable = false`) — flakes only.
|
||||
Flow: `hosts/*` → `modules/*` → `home/*`
|
||||
|
||||
## Commands
|
||||
|
||||
```bash
|
||||
# Justfile shortcuts (preferred)
|
||||
just rebuild mac-mini # rebuild macOS host (on macOS)
|
||||
just rebuild mac-mini # macOS host (darwin-rebuild)
|
||||
just rebuild macbook-air
|
||||
just rebuild # rebuild WSL (linux only, default: "wsl")
|
||||
just check # eval configs without building (platform-aware)
|
||||
just rebuild wsl # NixOS host (nixos-rebuild)
|
||||
just check # eval without building (platform-aware)
|
||||
just update # nix flake update
|
||||
just up nixpkgs # update a single flake input
|
||||
just show # nix flake show
|
||||
just secrets # sops secrets/secrets.yaml
|
||||
just clean # nix-collect-garbage -d
|
||||
just up nixpkgs # update single input
|
||||
just clean # nix-collect-garbage -d (user-level only)
|
||||
just rollback # NixOS only — rollback to previous generation
|
||||
just history # list system profile generations
|
||||
just lsp mac-mini # generate .vscode/settings.json for nixd option completion
|
||||
|
||||
# Direct (when just isn't available)
|
||||
sudo darwin-rebuild switch --flake .#mac-mini
|
||||
sudo nixos-rebuild switch --flake .#wsl
|
||||
nix build .#darwinConfigurations.mac-mini.system --dry-run # validate (eval only)
|
||||
nix build .#darwinConfigurations.mac-mini.system # validate (full build)
|
||||
|
||||
# First-time bootstrap (nix-darwin not yet installed)
|
||||
sudo nix run nix-darwin -- switch --flake .#mac-mini
|
||||
just show # nix flake show
|
||||
just lsp mac-mini # nixd option completion for VSCode
|
||||
```
|
||||
|
||||
## Critical gotchas
|
||||
Note: `just check` and `just rebuild` have `[macos]`/`[linux]` variants — the justfile auto-selects by platform.
|
||||
|
||||
- **Neovim uses lazyvim-nix**: `programs.lazyvim` in `home/dev/neovim.nix` manages neovim via the `lazyvim-nix` flake input. Catppuccin nvim integration is explicitly disabled (`catppuccin.nvim.enable = false`) because LazyVim manages its own colorscheme. Don't try to use `catppuccin.enable` for nvim or the old `programs.neovim.plugins` approach.
|
||||
- **catppuccin module name**: Home-manager uses `catppuccin.homeModules.catppuccin` (imported in `home/default.nix`). NixOS uses `catppuccin.nixosModules.catppuccin` (in `lib/default.nix`). Don't use the old `homeManagerModules` name.
|
||||
- **Homebrew tap casks**: Casks from taps need full path (e.g. `"goooler/repo/fl-clash"`), not just the short name.
|
||||
- **`onActivation.cleanup = "zap"`**: Any brew formula/cask NOT declared in `modules/darwin/default.nix` WILL be removed on rebuild. Be comprehensive.
|
||||
- **First-time bootstrap requires sudo**: `sudo nix run nix-darwin -- switch --flake .#mac-mini` (not `darwin-rebuild` which doesn't exist yet).
|
||||
- **mise for version management**: Activated in `home/shell/fish.nix` via `mise activate fish | source`. Config in `home/dev/languages.nix` trusts all config paths.
|
||||
## Gotchas
|
||||
|
||||
## Secrets (sops-nix)
|
||||
- **Shared settings in `modules/shared/`** — don't re-declare fish/openssh/1password/fonts in platform modules.
|
||||
- **`sshKeys` centralized** in `lib/default.nix` via `specialArgs`. Don't hardcode.
|
||||
- **WSL aliases force-cleared** — `hosts/wsl/default.nix` uses `lib.mkForce {}`. All aliases via Home Manager only.
|
||||
- **Neovim = lazyvim-nix** — `programs.lazyvim` in `home/dev/neovim.nix`. `catppuccin.nvim.enable = false` (LazyVim manages colorscheme). The `lazyvim.homeManagerModules.default` is loaded as a sharedModule in `lib/default.nix`.
|
||||
- **catppuccin modules** — `catppuccin.homeModules.catppuccin` (home), `catppuccin.nixosModules.catppuccin` (NixOS). Not the old `homeManagerModules`.
|
||||
- **Homebrew `cleanup = "zap"`** — undeclared casks/brews get removed. `greedyCasks = true` upgrades even auto-updating casks. Shared → `modules/darwin/`, host-specific → `hosts/*/`. Tap casks need full path (e.g. `"goooler/repo/fl-clash"`).
|
||||
- **Ghostty macOS-only** — `enable = pkgs.stdenv.isDarwin`, `package = null` (Homebrew cask). Terminfo propagated via `ghostty.terminfo` in `modules/nixos/`.
|
||||
- **nix-ld on WSL** — `programs.nix-ld.enable = true` for VSCode Remote.
|
||||
- **home-manager `backupFileExtension = "bak"`** — set in `lib/default.nix`. Existing dotfiles get `.bak` suffix on conflict.
|
||||
- **mise** — runtime version management (`home/dev/languages.nix`). `trusted_config_paths = [ "/" ]` trusts all config files.
|
||||
|
||||
- Encrypted with age, key derived from `~/.ssh/id_ed25519` (see `.sops.yaml`)
|
||||
- Secrets file: `secrets/secrets.yaml` — edit with `just secrets` (runs `sops`)
|
||||
- Decrypted at runtime via `home/secrets.nix`, exposed as env vars in fish: `AI_GATEWAY_BASE_URL`, `AI_GATEWAY_API_KEY`, `EXA_API_KEY`, `CONTEXT7_API_KEY`
|
||||
- sops-nix integrated via `home-manager` sharedModules in `lib/default.nix`
|
||||
- Never commit `*.dec.yaml`, `*.dec.json`, `*.plaintext` (in `.gitignore`)
|
||||
## Environment
|
||||
|
||||
## Shell
|
||||
1Password CLI secrets are **cached locally** — shell startup reads `~/.cache/op-env/env.fish` (no network).
|
||||
|
||||
Fish (not zsh). All tool integrations use `enableFishIntegration`. Key files:
|
||||
- `home/shell/fish.nix` — abbreviations, interactiveShellInit, mise activation
|
||||
- `home/shell/tools.nix` — fzf, atuin, zoxide (`--cmd cd`), direnv, bat, eza, yazi, btop, zellij
|
||||
- `home/shell/starship.nix` — prompt
|
||||
- Template: `home/shell/fish.nix` → `~/.config/op-env/env.tpl` (`op://` refs, safe to commit)
|
||||
- Cache: `~/.cache/op-env/env.fish` (plaintext, `chmod 600`, outside git/nix store)
|
||||
- Auth: `OP_SERVICE_ACCOUNT_TOKEN` in `~/.config/fish/local.fish` (gitignored)
|
||||
- Refresh: user runs `op-env-refresh` manually (needs network). Atomic write (mktemp + mv), failure keeps old cache.
|
||||
- Clear: `op-env-clear` removes cache file.
|
||||
- `local.fish` is sourced **after** the cache, so it can override env vars per-machine.
|
||||
|
||||
## Home Manager option API
|
||||
|
||||
These options were renamed in recent home-manager; use the new names:
|
||||
Use the new names:
|
||||
- `programs.git.settings.user.{name,email}` (not `userName`/`userEmail`)
|
||||
- `programs.git.settings.*` (not `extraConfig`)
|
||||
- `programs.delta.{enable,options}` (not `programs.git.delta.*`)
|
||||
- `programs.delta.enableGitIntegration = true` (must be explicit)
|
||||
- `programs.ssh.matchBlocks."*".addKeysToAgent` (not top-level `addKeysToAgent`)
|
||||
- `programs.ssh.enableDefaultConfig = false` (set explicitly)
|
||||
- `programs.ssh.matchBlocks."*".addKeysToAgent` (not top-level)
|
||||
- `programs.ssh.enableDefaultConfig = false`
|
||||
|
||||
## Nix LSP & formatter
|
||||
## Nix tooling
|
||||
|
||||
- LSP: `nixd` (not `nil`). Provides nixpkgs/option completion.
|
||||
- Formatter: `nixfmt`. Run: `nixfmt <file.nix>`
|
||||
- Both installed via `home/dev/languages.nix`.
|
||||
- VSCode settings for nixd option completion: `just lsp <host>` (generates `.vscode/settings.json` from `.vscode/settings.base.json`)
|
||||
- LSP: `nixd`. Formatter: `nixfmt`. Linter: `statix`.
|
||||
- All in `home/dev/languages.nix`.
|
||||
- `just lsp <host>` generates `.vscode/settings.json` from `.vscode/settings.base.json` (gitignored output).
|
||||
|
||||
## Tool usage
|
||||
|
||||
- **Always use the `nixos_nix` MCP tool** when searching for nix-darwin / NixOS / home-manager options. Query with `source=darwin/nixos/home-manager` and `type=options/packages` to find available options before writing config. Do not guess option names or value types — verify first.
|
||||
- `opencode.jsonc` configures `just-lsp` (LSP) and `mcp-nixos` (MCP).
|
||||
- **Always use `nixos_nix` MCP** to look up nix-darwin/NixOS/home-manager options before writing config. Don't guess option names.
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
# Nix Config
|
||||
|
||||
使用 [nix-darwin](https://github.com/nix-darwin/nix-darwin) + [NixOS-WSL](https://github.com/nix-community/NixOS-WSL) + [Home Manager](https://github.com/nix-community/home-manager) + [Flakes](https://nix.dev/concepts/flakes) 声明式管理三台设备的系统配置。
|
||||
nix-darwin + NixOS-WSL + Home Manager + Flakes 声明式管理三台设备的系统配置。
|
||||
|
||||
## 设备
|
||||
|
||||
@@ -12,108 +12,114 @@
|
||||
|
||||
## 快速开始
|
||||
|
||||
### macOS (Mac Mini / MacBook Air)
|
||||
### macOS
|
||||
|
||||
1. 安装 [Lix](https://lix.systems/)(Nix 的社区分支,nix-darwin 官方推荐):
|
||||
1. 安装 [Lix](https://lix.systems/):
|
||||
|
||||
```bash
|
||||
curl -sSf -L https://install.lix.systems/lix | sh -s -- install
|
||||
```
|
||||
|
||||
2. 克隆仓库并首次构建:
|
||||
2. 安装 [Homebrew](https://brew.sh/)(nix-darwin 不会自动安装):
|
||||
|
||||
```bash
|
||||
/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
|
||||
```
|
||||
|
||||
3. 克隆仓库并首次构建:
|
||||
|
||||
```bash
|
||||
git clone <repo-url> ~/nix-config
|
||||
cd ~/nix-config
|
||||
# 首次(nix-darwin 尚未安装):
|
||||
sudo nix run nix-darwin -- switch --flake .#mac-mini
|
||||
# 之后日常重建:
|
||||
sudo darwin-rebuild switch --flake .#mac-mini
|
||||
sudo nix run nix-darwin -- switch --flake .#macbook-air
|
||||
```
|
||||
|
||||
### WSL (Windows PC)
|
||||
之后日常重建:`just rebuild macbook-air`
|
||||
|
||||
1. 安装 [NixOS-WSL](https://github.com/nix-community/NixOS-WSL/releases):
|
||||
### WSL
|
||||
|
||||
1. 启用 WSL 并更新内核:
|
||||
|
||||
```powershell
|
||||
wsl --install --no-distribution
|
||||
wsl --update
|
||||
```
|
||||
|
||||
2. 安装 [NixOS-WSL](https://github.com/nix-community/NixOS-WSL/releases):
|
||||
|
||||
```powershell
|
||||
wsl --import NixOS C:\wsl\nixos nixos-wsl.tar.gz
|
||||
wsl -d NixOS
|
||||
```
|
||||
|
||||
2. 克隆仓库并构建:
|
||||
3. 首次构建:
|
||||
|
||||
```bash
|
||||
nix shell nixpkgs#git
|
||||
git clone <repo-url> ~/nix-config
|
||||
cd ~/nix-config
|
||||
sudo nixos-rebuild switch --flake .#wsl
|
||||
```
|
||||
|
||||
之后日常重建:`just rebuild wsl`
|
||||
|
||||
## 仓库结构
|
||||
|
||||
```
|
||||
├── flake.nix # 入口:输入源 + 输出配置
|
||||
├── flake.lock # 依赖锁定文件
|
||||
├── hosts/
|
||||
│ ├── mac-mini/default.nix # Mac Mini 特定配置
|
||||
│ ├── macbook-air/default.nix# MacBook Air 特定配置
|
||||
│ └── wsl/default.nix # WSL 特定配置
|
||||
├── modules/
|
||||
│ ├── darwin/default.nix # macOS 模块(Homebrew、系统偏好等)
|
||||
│ ├── nixos/ # NixOS 模块
|
||||
│ │ ├── base.nix # 基础包
|
||||
│ │ ├── docker.nix # Docker 配置
|
||||
│ │ ├── locale.nix # 区域 / 语言
|
||||
│ │ └── default.nix # 入口(用户、shell)
|
||||
│ └── shared/ # 共享模块(Nix 设置)
|
||||
├── home/ # Home Manager 配置
|
||||
│ ├── default.nix # 入口 + 用户级包
|
||||
│ ├── theme.nix # Catppuccin 主题
|
||||
│ ├── dev/ # 开发工具
|
||||
│ │ ├── neovim.nix
|
||||
│ │ ├── languages.nix # 语言运行时、LSP
|
||||
│ │ └── git.nix
|
||||
│ └── shell/ # Shell 配置
|
||||
│ ├── fish.nix # Fish shell
|
||||
│ ├── starship.nix # Prompt
|
||||
│ └── tools.nix # fzf, atuin, zoxide 等
|
||||
├── lib/default.nix # 构建辅助函数
|
||||
├── overlays/ # 自定义包覆盖
|
||||
└── pkgs/ # 自定义包
|
||||
flake.nix # 入口
|
||||
hosts/ # 主机特定配置
|
||||
modules/
|
||||
├── darwin/ # macOS 模块
|
||||
├── nixos/ # NixOS 模块
|
||||
└── shared/ # 共享模块
|
||||
home/ # Home Manager 配置
|
||||
├── dev/ # 开发工具
|
||||
└── shell/ # Shell 配置
|
||||
lib/default.nix # 构建辅助函数
|
||||
overlays/ + pkgs/ # 自定义包
|
||||
```
|
||||
|
||||
**配置层级**:`hosts/*`(主机特定) → `modules/*`(平台模块) → `home/*`(用户级,跨平台共享)
|
||||
配置层级:`hosts/*` → `modules/*` → `home/*`
|
||||
|
||||
## 日常使用
|
||||
|
||||
```bash
|
||||
# 重建(abbreviation 自动选择 darwin-rebuild 或 nixos-rebuild)
|
||||
rebuild
|
||||
|
||||
# 更新所有依赖
|
||||
update
|
||||
|
||||
# 回滚(NixOS)
|
||||
sudo nixos-rebuild switch --rollback
|
||||
|
||||
# 清理旧 generation
|
||||
sudo nix-collect-garbage -d # NixOS
|
||||
nix-collect-garbage -d # macOS
|
||||
just rebuild <host> # 重建系统
|
||||
just update # 更新所有 flake 输入
|
||||
just up <input> # 更新单个输入
|
||||
just check # 检查配置
|
||||
just clean # 清理旧 generation
|
||||
just rollback # 回滚(仅 NixOS)
|
||||
just history # 查看 profile 历史
|
||||
just show # 显示 flake 输出
|
||||
```
|
||||
|
||||
## Shell
|
||||
|
||||
使用 **Fish** 作为默认 shell,搭配:
|
||||
Fish + Starship + Atuin + Zoxide + FZF + Direnv,Catppuccin Mocha 主题。
|
||||
|
||||
- **Starship** — 跨平台 prompt
|
||||
- **Atuin** — shell 历史搜索
|
||||
- **Zoxide** — 智能 cd(`cd` = zoxide, `cdi` = 交互选择)
|
||||
- **FZF** — 模糊搜索(Ctrl-R 历史, Ctrl-T 文件, Alt-C 目录)
|
||||
- **Direnv** — 自动加载项目环境
|
||||
- **Catppuccin Mocha** — 统一主题
|
||||
常用自定义:
|
||||
- fish abbreviation → `home/shell/fish.nix`
|
||||
- 添加包 → `home/default.nix` 或 `home/dev/languages.nix`
|
||||
- Homebrew cask → `modules/darwin/default.nix`
|
||||
|
||||
### 自定义
|
||||
## Environment
|
||||
|
||||
- 添加 fish abbreviation: 编辑 `home/shell/fish.nix` 中的 `shellAbbrs`
|
||||
- 添加包: 编辑 `home/default.nix` 或 `home/dev/languages.nix`
|
||||
- 添加 Homebrew cask: 编辑 `modules/darwin/default.nix` 中的 `homebrew.casks`
|
||||
- 查包名: `nix search nixpkgs <关键词>` 或 [search.nixos.org](https://search.nixos.org/packages)
|
||||
1Password CLI `op inject` 获取环境变量,本地缓存后离线可用。
|
||||
|
||||
模板文件 `~/.config/op-env/env.tpl` 由 `home/shell/fish.nix` 生成,仅包含 `op://` 引用,可安全提交。
|
||||
|
||||
Shell 启动时只读取本地缓存(`~/.cache/op-env/env.fish`),不联网。首次使用或密钥变更后需手动刷新:
|
||||
|
||||
```bash
|
||||
op-env-refresh # 从 1Password 获取并缓存(需联网)
|
||||
op-env-clear # 清除本地缓存
|
||||
```
|
||||
|
||||
认证需要在 `~/.config/fish/local.fish`(gitignored)中设置:
|
||||
|
||||
```bash
|
||||
set -gx OP_SERVICE_ACCOUNT_TOKEN "your-service-account-token"
|
||||
```
|
||||
|
||||
未设置 token 时 `op-env-refresh` 会提示错误,不影响已有缓存的正常使用。
|
||||
|
||||
Generated
+7
-28
@@ -7,11 +7,11 @@
|
||||
]
|
||||
},
|
||||
"locked": {
|
||||
"lastModified": 1775938181,
|
||||
"narHash": "sha256-3VRl7wTV2guWBI1kYT2OZEAMYU5nUZMo6um9UH+HYHE=",
|
||||
"lastModified": 1776190523,
|
||||
"narHash": "sha256-qfZWzaWuXfbF487cXj43uT7HWtqF45A+g7g59fOPYsk=",
|
||||
"owner": "catppuccin",
|
||||
"repo": "nix",
|
||||
"rev": "8d8b4fd30aecbf30eef6b1d1977670a597d29494",
|
||||
"rev": "2eefec08414e2f90824bf2b508ea38ef6f295dfa",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
@@ -61,11 +61,11 @@
|
||||
]
|
||||
},
|
||||
"locked": {
|
||||
"lastModified": 1775983377,
|
||||
"narHash": "sha256-ZeRjipGQnVtQ/6batI+yVOrL853FZsL0m9A63OaSfgM=",
|
||||
"lastModified": 1776184304,
|
||||
"narHash": "sha256-No6QGBmIv5ChiwKCcbkxjdEQ/RO2ZS1gD7SFy6EZ7rc=",
|
||||
"owner": "nix-community",
|
||||
"repo": "home-manager",
|
||||
"rev": "e0ca734ffc85d25297715e98010b93303fa165c4",
|
||||
"rev": "3c7524c68348ef79ce48308e0978611a050089b2",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
@@ -173,28 +173,7 @@
|
||||
"lazyvim": "lazyvim",
|
||||
"nix-darwin": "nix-darwin",
|
||||
"nixos-wsl": "nixos-wsl",
|
||||
"nixpkgs": "nixpkgs_2",
|
||||
"sops-nix": "sops-nix"
|
||||
}
|
||||
},
|
||||
"sops-nix": {
|
||||
"inputs": {
|
||||
"nixpkgs": [
|
||||
"nixpkgs"
|
||||
]
|
||||
},
|
||||
"locked": {
|
||||
"lastModified": 1775971308,
|
||||
"narHash": "sha256-VKp9bhVSm0bT6JWctFy06ocqxGGnWHi1NfoE90IgIcY=",
|
||||
"owner": "Mic92",
|
||||
"repo": "sops-nix",
|
||||
"rev": "31ac5fe5d015f76b54058c69fcaebb66a55871a4",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
"owner": "Mic92",
|
||||
"repo": "sops-nix",
|
||||
"type": "github"
|
||||
"nixpkgs": "nixpkgs_2"
|
||||
}
|
||||
},
|
||||
"systems": {
|
||||
|
||||
@@ -19,11 +19,6 @@
|
||||
inputs.nixpkgs.follows = "nixpkgs";
|
||||
};
|
||||
|
||||
sops-nix = {
|
||||
url = "github:Mic92/sops-nix";
|
||||
inputs.nixpkgs.follows = "nixpkgs";
|
||||
};
|
||||
|
||||
catppuccin = {
|
||||
url = "github:catppuccin/nix";
|
||||
inputs.nixpkgs.follows = "nixpkgs";
|
||||
@@ -42,7 +37,7 @@
|
||||
mylib = import ./lib { inherit inputs; };
|
||||
in
|
||||
{
|
||||
# ── macOS hosts ─────────────────────────────────────
|
||||
# ── macOS 主机 ──────────────────────────────────────
|
||||
darwinConfigurations = {
|
||||
mac-mini = mylib.mkDarwin {
|
||||
hostname = "awesome-mac-mini";
|
||||
@@ -59,7 +54,7 @@
|
||||
};
|
||||
};
|
||||
|
||||
# ── NixOS hosts (WSL on Windows PC) ─────────────────
|
||||
# ── NixOS 主机(Windows PC 上的 WSL)──────────────
|
||||
nixosConfigurations = {
|
||||
wsl = mylib.mkNixos {
|
||||
hostname = "awesome-wsl";
|
||||
@@ -72,14 +67,19 @@
|
||||
};
|
||||
};
|
||||
|
||||
# ── Packages ────────────────────────────────────────
|
||||
packages = nixpkgs.lib.genAttrs [ "aarch64-darwin" "x86_64-linux" ] (system: {
|
||||
comment-checker =
|
||||
(import nixpkgs {
|
||||
# ── 自定义包 ─────────────────────────────────────────
|
||||
packages = nixpkgs.lib.genAttrs [ "aarch64-darwin" "x86_64-linux" ] (
|
||||
system:
|
||||
let
|
||||
pkgs = import nixpkgs {
|
||||
inherit system;
|
||||
overlays = [ self.overlays.default ];
|
||||
}).comment-checker;
|
||||
});
|
||||
};
|
||||
in
|
||||
{
|
||||
inherit (pkgs) comment-checker;
|
||||
}
|
||||
);
|
||||
|
||||
# ── Overlays ───────────────────────────────────────
|
||||
overlays.default = import ./overlays;
|
||||
|
||||
+16
-18
@@ -10,54 +10,52 @@
|
||||
inputs.catppuccin.homeModules.catppuccin
|
||||
./shell
|
||||
./dev
|
||||
./theme.nix
|
||||
./secrets.nix
|
||||
];
|
||||
|
||||
catppuccin = {
|
||||
enable = true;
|
||||
flavor = "mocha";
|
||||
};
|
||||
|
||||
home = {
|
||||
username = username;
|
||||
homeDirectory = if pkgs.stdenv.isDarwin then "/Users/${username}" else "/home/${username}";
|
||||
stateVersion = "24.11";
|
||||
stateVersion = "25.11";
|
||||
};
|
||||
|
||||
# ── User-level packages ────────────────────────────
|
||||
home.packages = with pkgs; [
|
||||
# Modern CLI replacements
|
||||
# 现代 CLI 替代工具
|
||||
dust # du
|
||||
duf # df
|
||||
procs # ps
|
||||
sd # sed
|
||||
xh # curl/httpie
|
||||
jq # JSON
|
||||
yq # YAML
|
||||
wget
|
||||
|
||||
# System info
|
||||
# 系统信息
|
||||
fastfetch
|
||||
tealdeer # tldr
|
||||
|
||||
# File management
|
||||
# 文件管理
|
||||
gomi
|
||||
ouch # 压缩/解压
|
||||
|
||||
# Nix tools
|
||||
# Nix 工具
|
||||
nix-output-monitor # nom
|
||||
nvd # nix version diff
|
||||
nh # nix helper
|
||||
nvd # Nix 版本对比
|
||||
nh # Nix 辅助工具
|
||||
just
|
||||
|
||||
# Secrets management
|
||||
sops
|
||||
age
|
||||
|
||||
# AI coding agent
|
||||
# AI 编程代理
|
||||
opencode
|
||||
comment-checker
|
||||
skills
|
||||
|
||||
# Misc
|
||||
# 其他
|
||||
ffmpeg
|
||||
pandoc
|
||||
];
|
||||
|
||||
# XDG directories
|
||||
xdg.enable = true;
|
||||
}
|
||||
|
||||
+4
-8
@@ -1,14 +1,12 @@
|
||||
{ ... }:
|
||||
_:
|
||||
|
||||
{
|
||||
programs.git = {
|
||||
enable = true;
|
||||
signing.format = null;
|
||||
settings = {
|
||||
user = {
|
||||
name = "imbytecat";
|
||||
email = "imbytecat@gmail.com";
|
||||
};
|
||||
user.name = "imbytecat";
|
||||
user.email = "imbytecat@gmail.com";
|
||||
merge.conflictstyle = "zdiff3";
|
||||
pull.rebase = true;
|
||||
push.autoSetupRemote = true;
|
||||
@@ -36,9 +34,7 @@
|
||||
nerdFontsVersion = "3";
|
||||
showBottomLine = false;
|
||||
};
|
||||
git.pagers = [
|
||||
{ pager = "delta --paging=never"; }
|
||||
];
|
||||
git.pagers = [ { pager = "delta --paging=never"; } ];
|
||||
update.method = "never";
|
||||
disableStartupPopups = true;
|
||||
};
|
||||
|
||||
+21
-17
@@ -2,18 +2,16 @@
|
||||
|
||||
{
|
||||
home.packages = with pkgs; [
|
||||
# ── Language runtimes ──
|
||||
# Node.js: 默认跟随 nixpkgs,当前 unstable 为 v24.14.0
|
||||
# 如需固定 LTS 版本,改为: nodejs_22 或 nodejs_20
|
||||
# ── 语言运行时 ──
|
||||
nodejs
|
||||
go
|
||||
bun
|
||||
python3
|
||||
|
||||
# ── Package management / version management ──
|
||||
mise
|
||||
# ── 包管理 / 版本管理 ──
|
||||
uv
|
||||
|
||||
# ── LSP servers ──
|
||||
# ── LSP 服务器 ──
|
||||
bash-language-server
|
||||
gopls
|
||||
typescript-language-server
|
||||
@@ -21,25 +19,31 @@
|
||||
vue-language-server
|
||||
dockerfile-language-server
|
||||
lua-language-server
|
||||
nixd # Nix LSP
|
||||
just-lsp # Justfile LSP
|
||||
nixd
|
||||
just-lsp
|
||||
|
||||
# ── Linter / Formatter ──
|
||||
# ── 代码检查 / 格式化 ──
|
||||
biome
|
||||
ruff
|
||||
shellcheck
|
||||
shfmt
|
||||
nixfmt # nix formatter
|
||||
statix # nix linter
|
||||
nixfmt
|
||||
statix
|
||||
stylua
|
||||
|
||||
# ── Code intelligence ──
|
||||
# ── 代码智能 ──
|
||||
ast-grep
|
||||
];
|
||||
|
||||
# ── mise config ──────────────────────────────────────
|
||||
xdg.configFile."mise/config.toml".text = ''
|
||||
[settings]
|
||||
trusted_config_paths = ["/"]
|
||||
'';
|
||||
# ── mise ─────────────────────────────────────────────
|
||||
programs.mise = {
|
||||
enable = true;
|
||||
enableFishIntegration = true;
|
||||
globalConfig = {
|
||||
settings = {
|
||||
trusted_config_paths = [ "/" ];
|
||||
all_compile = false;
|
||||
};
|
||||
};
|
||||
};
|
||||
}
|
||||
|
||||
+3
-3
@@ -1,7 +1,7 @@
|
||||
{ ... }:
|
||||
_:
|
||||
|
||||
{
|
||||
# Disable catppuccin/nix neovim integration — LazyVim manages its own colorscheme
|
||||
# 禁用 catppuccin/nix 的 Neovim 集成 — LazyVim 自行管理配色方案
|
||||
catppuccin.nvim.enable = false;
|
||||
|
||||
programs.neovim = {
|
||||
@@ -22,7 +22,7 @@
|
||||
lang.docker.enable = true;
|
||||
};
|
||||
|
||||
# Catppuccin Mocha colorscheme (managed by LazyVim, not catppuccin/nix)
|
||||
# Catppuccin Mocha 配色方案(由 LazyVim 管理,非 catppuccin/nix)
|
||||
plugins = {
|
||||
colorscheme = ''
|
||||
return {
|
||||
|
||||
@@ -1,30 +0,0 @@
|
||||
{ config, ... }:
|
||||
|
||||
{
|
||||
sops = {
|
||||
age.sshKeyPaths = [ "${config.home.homeDirectory}/.ssh/id_ed25519" ];
|
||||
defaultSopsFile = ../secrets/secrets.yaml;
|
||||
defaultSopsFormat = "yaml";
|
||||
|
||||
secrets = {
|
||||
ai_gateway_base_url = { };
|
||||
ai_gateway_api_key = { };
|
||||
exa_api_key = { };
|
||||
context7_api_key = { };
|
||||
};
|
||||
};
|
||||
|
||||
programs.fish.interactiveShellInit = ''
|
||||
# sops-nix secrets → env vars
|
||||
for pair in \
|
||||
AI_GATEWAY_BASE_URL:${config.sops.secrets.ai_gateway_base_url.path} \
|
||||
AI_GATEWAY_API_KEY:${config.sops.secrets.ai_gateway_api_key.path} \
|
||||
EXA_API_KEY:${config.sops.secrets.exa_api_key.path} \
|
||||
CONTEXT7_API_KEY:${config.sops.secrets.context7_api_key.path}
|
||||
set -l parts (string split : $pair)
|
||||
if test -r $parts[2]
|
||||
set -gx $parts[1] (cat $parts[2])
|
||||
end
|
||||
end
|
||||
'';
|
||||
}
|
||||
@@ -1,6 +1,7 @@
|
||||
{
|
||||
imports = [
|
||||
./fish.nix
|
||||
./ghostty.nix
|
||||
./starship.nix
|
||||
./tools.nix
|
||||
];
|
||||
|
||||
+104
-23
@@ -1,51 +1,132 @@
|
||||
{ ... }:
|
||||
|
||||
{
|
||||
config,
|
||||
pkgs,
|
||||
lib,
|
||||
...
|
||||
}:
|
||||
|
||||
let
|
||||
envTpl = "${config.xdg.configHome}/op-env/env.tpl";
|
||||
envCache = "${config.xdg.cacheHome}/op-env/env.fish";
|
||||
in
|
||||
{
|
||||
# ── 1Password 环境变量模板 ─────────────────────────────
|
||||
# 仅包含 op:// 引用 — 无真实密钥,可安全提交
|
||||
# 放在 ~/.config/op 之外 — 该目录必须是 700 权限且属于 op CLI
|
||||
xdg.configFile."op-env/env.tpl".text = ''
|
||||
set -gx AI_GATEWAY_BASE_URL "{{ op://Developer/AI Gateway API/URL }}"
|
||||
set -gx AI_GATEWAY_API_KEY "{{ op://Developer/AI Gateway API/credential }}"
|
||||
set -gx EXA_API_KEY "{{ op://Developer/Exa API/credential }}"
|
||||
set -gx CONTEXT7_API_KEY "{{ op://Developer/Context7 API/credential }}"
|
||||
'';
|
||||
|
||||
programs.fish = {
|
||||
enable = true;
|
||||
|
||||
shellAbbrs = {
|
||||
# Navigation
|
||||
# 导航(一次性命令,无需记录历史)
|
||||
".." = "cd ..";
|
||||
"..." = "cd ../..";
|
||||
};
|
||||
|
||||
# File listing (eza)
|
||||
ls = "eza --icons --group-directories-first";
|
||||
ll = "eza -la --icons --git --group-directories-first";
|
||||
la = "eza -a --icons --group-directories-first";
|
||||
lt = "eza --tree --level=2 --icons";
|
||||
shellAliases = {
|
||||
# 文件列表(eza)— 基础别名(ls/la/lt)来自 programs.eza
|
||||
ll = "eza -lh";
|
||||
lla = "eza -lah --time-style=long-iso";
|
||||
|
||||
# Tools
|
||||
cat = "bat --paging=never";
|
||||
rm = "gomi";
|
||||
lg = "lazygit";
|
||||
vi = "nvim";
|
||||
|
||||
# Network
|
||||
http = "xh";
|
||||
|
||||
};
|
||||
|
||||
interactiveShellInit = ''
|
||||
# No greeting
|
||||
set -g fish_greeting
|
||||
|
||||
# PATH
|
||||
fish_add_path $HOME/go/bin $HOME/.bun/bin
|
||||
${lib.optionalString pkgs.stdenv.isDarwin ''fish_add_path "/Applications/Visual Studio Code.app/Contents/Resources/app/bin"''}
|
||||
|
||||
# mise
|
||||
mise activate fish | source
|
||||
|
||||
# Sudo: double Escape to prepend sudo
|
||||
# 双击 Escape 在命令前插入 sudo
|
||||
bind \e\e 'fish_commandline_prepend sudo'
|
||||
|
||||
# WSL clipboard
|
||||
# WSL 剪贴板
|
||||
if set -q WSL_DISTRO_NAME
|
||||
alias pbcopy clip.exe
|
||||
alias pbpaste "powershell.exe -noprofile -c Get-Clipboard"
|
||||
end
|
||||
|
||||
# User-local overrides
|
||||
# Windows Terminal:发送 OSC 9;9 使新标签页/窗格在同一目录打开
|
||||
function __wt_osc9_9 --on-variable PWD
|
||||
if test -n "$WT_SESSION"
|
||||
printf "\e]9;9;%s\e\\" (wslpath -w "$PWD")
|
||||
end
|
||||
end
|
||||
|
||||
# 1Password → 环境变量(本地缓存,启动时不联网)
|
||||
# 启动时仅加载缓存;手动执行 op-env-refresh 拉取/更新
|
||||
# 通过 OP_SERVICE_ACCOUNT_TOKEN 认证(在 ~/.config/fish/local.fish 中设置)
|
||||
function op-env-refresh --description "Fetch secrets from 1Password and cache locally"
|
||||
if not type -q op
|
||||
echo "op-env: op CLI not found in PATH" >&2
|
||||
return 1
|
||||
end
|
||||
if not set -q OP_SERVICE_ACCOUNT_TOKEN; or test -z "$OP_SERVICE_ACCOUNT_TOKEN"
|
||||
echo "op-env: OP_SERVICE_ACCOUNT_TOKEN is not set" >&2
|
||||
return 1
|
||||
end
|
||||
if not test -f "${envTpl}"
|
||||
echo "op-env: template not found: ${envTpl}" >&2
|
||||
return 1
|
||||
end
|
||||
set -l cache_dir (path dirname "${envCache}")
|
||||
if not mkdir -p "$cache_dir"; or not chmod 700 "$cache_dir"
|
||||
echo "op-env: cannot prepare cache dir: $cache_dir" >&2
|
||||
return 1
|
||||
end
|
||||
set -l tmp (mktemp "$cache_dir/.tmp.XXXXXX")
|
||||
or begin
|
||||
echo "op-env: mktemp failed" >&2
|
||||
return 1
|
||||
end
|
||||
if not op inject --in-file "${envTpl}" > "$tmp"
|
||||
command rm -f "$tmp"
|
||||
echo "op-env: inject failed; old cache kept" >&2
|
||||
return 1
|
||||
end
|
||||
# 替换缓存前记录旧变量名
|
||||
set -l old_vars
|
||||
if test -f "${envCache}"
|
||||
set old_vars (string match -rg 'set -gx (\S+)' < "${envCache}")
|
||||
end
|
||||
if not mv "$tmp" "${envCache}"
|
||||
command rm -f "$tmp"
|
||||
echo "op-env: cannot replace cache file" >&2
|
||||
return 1
|
||||
end
|
||||
for var in $old_vars
|
||||
set -e $var
|
||||
end
|
||||
if not source "${envCache}"
|
||||
echo "op-env: cache written but could not be sourced" >&2
|
||||
return 1
|
||||
end
|
||||
echo "op-env: refreshed"
|
||||
end
|
||||
|
||||
function op-env-clear --description "Clear cached secrets"
|
||||
if test -f "${envCache}"
|
||||
for var in (string match -rg 'set -gx (\S+)' < "${envCache}")
|
||||
set -e $var
|
||||
end
|
||||
command rm -f "${envCache}"
|
||||
end
|
||||
echo "op-env: cleared"
|
||||
end
|
||||
|
||||
# 加载缓存的密钥(即时,不联网)
|
||||
if test -f "${envCache}"
|
||||
source "${envCache}"
|
||||
end
|
||||
|
||||
# 用户本地配置(OP_SERVICE_ACCOUNT_TOKEN、机器特定覆盖)
|
||||
if test -f ~/.config/fish/local.fish
|
||||
source ~/.config/fish/local.fish
|
||||
end
|
||||
|
||||
@@ -0,0 +1,13 @@
|
||||
{ pkgs, ... }:
|
||||
|
||||
{
|
||||
programs.ghostty = {
|
||||
enable = pkgs.stdenv.isDarwin;
|
||||
package = null; # 通过 Homebrew cask 安装
|
||||
settings = {
|
||||
font-family = "Maple Mono NF CN";
|
||||
font-size = 14;
|
||||
shell-integration-features = "cursor,sudo,title,ssh-env,ssh-terminfo";
|
||||
};
|
||||
};
|
||||
}
|
||||
+24
-16
@@ -18,10 +18,11 @@
|
||||
"$git_branch"
|
||||
"$git_status"
|
||||
"[](fg:yellow bg:green)"
|
||||
"$nodejs"
|
||||
"$python"
|
||||
"$bun"
|
||||
"$golang"
|
||||
"$nix_shell"
|
||||
"$nodejs"
|
||||
"$python"
|
||||
"[](fg:green bg:sapphire)"
|
||||
"$docker_context"
|
||||
"[](fg:sapphire bg:lavender)"
|
||||
@@ -38,6 +39,7 @@
|
||||
symbols = {
|
||||
Linux = "";
|
||||
Macos = "";
|
||||
NixOS = "";
|
||||
Windows = "";
|
||||
};
|
||||
};
|
||||
@@ -55,11 +57,11 @@
|
||||
truncation_length = 3;
|
||||
truncation_symbol = "…/";
|
||||
substitutions = {
|
||||
Developer = " ";
|
||||
Documents = " ";
|
||||
Downloads = " ";
|
||||
Music = " ";
|
||||
Pictures = " ";
|
||||
Developer = "";
|
||||
Documents = "";
|
||||
Downloads = "";
|
||||
Music = "";
|
||||
Pictures = "";
|
||||
};
|
||||
};
|
||||
|
||||
@@ -74,17 +76,10 @@
|
||||
format = "[[($all_status$ahead_behind )](fg:crust bg:yellow)]($style)";
|
||||
};
|
||||
|
||||
nodejs = {
|
||||
symbol = "";
|
||||
bun = {
|
||||
symbol = "";
|
||||
style = "bg:green";
|
||||
format = "[[ $symbol( $version) ](fg:crust bg:green)]($style)";
|
||||
detect_extensions = [ ];
|
||||
};
|
||||
|
||||
python = {
|
||||
symbol = "";
|
||||
style = "bg:green";
|
||||
format = "[[ $symbol( $version)(\\($virtualenv\\)) ](fg:crust bg:green)]($style)";
|
||||
};
|
||||
|
||||
golang = {
|
||||
@@ -99,6 +94,19 @@
|
||||
format = "[[ $symbol$state( \\($name\\)) ](fg:crust bg:green)]($style)";
|
||||
};
|
||||
|
||||
nodejs = {
|
||||
symbol = "";
|
||||
style = "bg:green";
|
||||
format = "[[ $symbol( $version) ](fg:crust bg:green)]($style)";
|
||||
detect_extensions = [ ];
|
||||
};
|
||||
|
||||
python = {
|
||||
symbol = "";
|
||||
style = "bg:green";
|
||||
format = "[[ $symbol( $version)(\\($virtualenv\\)) ](fg:crust bg:green)]($style)";
|
||||
};
|
||||
|
||||
docker_context = {
|
||||
symbol = "";
|
||||
style = "bg:sapphire";
|
||||
|
||||
+10
-11
@@ -19,7 +19,7 @@
|
||||
];
|
||||
};
|
||||
|
||||
# ── Atuin (shell history) ────────────────────────────
|
||||
# ── Atuin(Shell 历史记录)─────────────────────────────
|
||||
programs.atuin = {
|
||||
enable = true;
|
||||
enableFishIntegration = true;
|
||||
@@ -33,11 +33,11 @@
|
||||
};
|
||||
};
|
||||
|
||||
# ── Zoxide (smart cd) ───────────────────────────────
|
||||
# ── Zoxide(智能 cd)──────────────────────────────────
|
||||
programs.zoxide = {
|
||||
enable = true;
|
||||
enableFishIntegration = true;
|
||||
options = [ "--cmd cd" ]; # cd/cdi instead of z/zi
|
||||
options = [ "--cmd cd" ]; # 用 cd/cdi 替代 z/zi
|
||||
};
|
||||
|
||||
# ── Direnv + nix-direnv ─────────────────────────────
|
||||
@@ -50,7 +50,7 @@
|
||||
};
|
||||
};
|
||||
|
||||
# ── Bat (cat replacement) ───────────────────────────
|
||||
# ── Bat(cat 替代)────────────────────────────────────
|
||||
programs.bat = {
|
||||
enable = true;
|
||||
extraPackages = with pkgs.bat-extras; [
|
||||
@@ -59,26 +59,25 @@
|
||||
];
|
||||
};
|
||||
|
||||
# ── Eza (ls replacement) ────────────────────────────
|
||||
# ── Eza(ls 替代)─────────────────────────────────────
|
||||
programs.eza = {
|
||||
enable = true;
|
||||
enableFishIntegration = false; # we use custom abbrs in fish.nix
|
||||
enableFishIntegration = true;
|
||||
git = true;
|
||||
icons = "auto";
|
||||
extraOptions = [
|
||||
"--color=always"
|
||||
"--group-directories-first"
|
||||
];
|
||||
};
|
||||
|
||||
# ── Yazi (file manager) ─────────────────────────────
|
||||
# ── Yazi(文件管理器)────────────────────────────────
|
||||
programs.yazi = {
|
||||
enable = true;
|
||||
enableFishIntegration = true;
|
||||
shellWrapperName = "y";
|
||||
};
|
||||
|
||||
# ── Btop (system monitor) ───────────────────────────
|
||||
# ── Btop(系统监控)──────────────────────────────────
|
||||
programs.btop = {
|
||||
enable = true;
|
||||
settings = {
|
||||
@@ -86,10 +85,10 @@
|
||||
};
|
||||
};
|
||||
|
||||
# ── Zellij (terminal multiplexer) ────────────────────
|
||||
# ── Zellij(终端复用器)──────────────────────────────
|
||||
programs.zellij = {
|
||||
enable = true;
|
||||
enableFishIntegration = true;
|
||||
enableFishIntegration = false;
|
||||
settings = {
|
||||
show_startup_tips = false;
|
||||
};
|
||||
|
||||
@@ -1,8 +0,0 @@
|
||||
{ ... }:
|
||||
|
||||
{
|
||||
catppuccin = {
|
||||
enable = true;
|
||||
flavor = "mocha";
|
||||
};
|
||||
}
|
||||
@@ -1,13 +1,13 @@
|
||||
{ ... }:
|
||||
|
||||
{
|
||||
# ── Mac Mini specific ─────────────────────────────────
|
||||
# Always plugged in — 24/7 server role
|
||||
# ── Mac Mini 专属配置 ────────────────────────────────
|
||||
# 常驻供电 — 全天候服务器角色
|
||||
|
||||
# Touch ID for sudo
|
||||
# Touch ID 验证 sudo
|
||||
security.pam.services.sudo_local.touchIdAuth = true;
|
||||
|
||||
# ── Never sleep ─────────────────────────────────────
|
||||
# ── 禁止睡眠 ────────────────────────────────────────
|
||||
power.sleep.computer = "never";
|
||||
power.sleep.display = "never";
|
||||
power.sleep.harddisk = "never";
|
||||
@@ -15,17 +15,17 @@
|
||||
power.restartAfterPowerFailure = true;
|
||||
power.restartAfterFreeze = true;
|
||||
|
||||
# ── Wake on LAN ──────────────────────────────────
|
||||
# ── 网络唤醒(WoL)─────────────────────────────────
|
||||
networking.wakeOnLan.enable = true;
|
||||
|
||||
# ── Screen Sharing (VNC) & pmset ─────────────────
|
||||
# ── 屏幕共享(VNC)& pmset ──────────────────────────
|
||||
system.activationScripts.postActivation.text = ''
|
||||
# VNC
|
||||
launchctl enable system/com.apple.screensharing
|
||||
launchctl load -w /System/Library/LaunchDaemons/com.apple.screensharing.plist 2>/dev/null || true
|
||||
# Disable Power Nap
|
||||
# 禁用 Power Nap
|
||||
pmset -a powernap 0
|
||||
'';
|
||||
|
||||
system.stateVersion = 5;
|
||||
system.stateVersion = 6;
|
||||
}
|
||||
|
||||
@@ -1,11 +1,16 @@
|
||||
{ ... }:
|
||||
|
||||
{
|
||||
# ── MacBook Air specific ──────────────────────────────
|
||||
# Portable — battery-conscious settings
|
||||
# ── MacBook Air 专属配置 ─────────────────────────────
|
||||
# 便携设备 — 注意电池续航
|
||||
|
||||
# Touch ID for sudo
|
||||
# Touch ID 验证 sudo
|
||||
security.pam.services.sudo_local.touchIdAuth = true;
|
||||
|
||||
system.stateVersion = 5;
|
||||
# ── 刘海屏适配 ──────────────────────────────────────
|
||||
homebrew.casks = [
|
||||
"thaw" # 刘海屏菜单栏管理工具
|
||||
];
|
||||
|
||||
system.stateVersion = 6;
|
||||
}
|
||||
|
||||
+10
-2
@@ -1,11 +1,19 @@
|
||||
{ username, ... }:
|
||||
{ lib, username, ... }:
|
||||
|
||||
{
|
||||
# ── Shell ─────────────────────────────────────────────
|
||||
# 移除 NixOS 默认别名(ls/ll/l)— 由 Home Manager eza 管理
|
||||
environment.shellAliases = lib.mkForce { };
|
||||
|
||||
# ── WSL ──────────────────────────────────────────────
|
||||
wsl = {
|
||||
enable = true;
|
||||
defaultUser = username;
|
||||
interop.register = true;
|
||||
};
|
||||
|
||||
system.stateVersion = "24.11";
|
||||
# ── nix-ld (VSCode Remote, etc.) ────────────────────
|
||||
programs.nix-ld.enable = true;
|
||||
|
||||
system.stateVersion = "25.11";
|
||||
}
|
||||
|
||||
+9
-8
@@ -17,7 +17,7 @@ rebuild host:
|
||||
# Rebuild and switch to new system configuration
|
||||
[linux]
|
||||
[group('build')]
|
||||
rebuild host="wsl":
|
||||
rebuild host:
|
||||
sudo nixos-rebuild switch --flake .#{{host}}
|
||||
|
||||
# Check configs evaluate without errors
|
||||
@@ -27,6 +27,12 @@ check:
|
||||
@nix eval .#darwinConfigurations.mac-mini.system > /dev/null && echo "mac-mini: ok"
|
||||
@nix eval .#darwinConfigurations.macbook-air.system > /dev/null && echo "macbook-air: ok"
|
||||
|
||||
# Rollback to previous system generation
|
||||
[linux]
|
||||
[group('build')]
|
||||
rollback:
|
||||
sudo nixos-rebuild switch --rollback
|
||||
|
||||
# Check configs evaluate without errors
|
||||
[linux]
|
||||
[group('build')]
|
||||
@@ -66,15 +72,10 @@ clean:
|
||||
|
||||
############################################################################
|
||||
#
|
||||
# Secrets & tooling
|
||||
# Tooling
|
||||
#
|
||||
############################################################################
|
||||
|
||||
# Edit encrypted secrets
|
||||
[group('tools')]
|
||||
secrets:
|
||||
sops secrets/secrets.yaml
|
||||
|
||||
# Generate .vscode/settings.json with LSP option completion
|
||||
[macos]
|
||||
[group('tools')]
|
||||
@@ -85,6 +86,6 @@ lsp host:
|
||||
# Generate .vscode/settings.json with LSP option completion
|
||||
[linux]
|
||||
[group('tools')]
|
||||
lsp host="wsl":
|
||||
lsp host:
|
||||
@jq --arg h "{{host}}" '."nix.serverSettings".nixd.options = {"nixos":{"expr":"(builtins.getFlake (toString ./.)).nixosConfigurations.\($h).options"},"home-manager":{"expr":"(builtins.getFlake (toString ./.)).nixosConfigurations.\($h).options.home-manager.users.type.getSubOptions []"}}' .vscode/settings.base.json > .vscode/settings.json
|
||||
@echo "Generated .vscode/settings.json for {{host}}"
|
||||
+19
-6
@@ -3,14 +3,17 @@
|
||||
let
|
||||
inherit (inputs.nixpkgs) lib;
|
||||
|
||||
# Shared home-manager configuration block
|
||||
sshKeys = [
|
||||
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIDRTOo48gzzRGT+bF9dzJCFJu61YgsQVONFtxU9kTPIg"
|
||||
];
|
||||
|
||||
# 共享的 Home Manager 配置块
|
||||
homeManagerConfig = username: {
|
||||
home-manager = {
|
||||
useGlobalPkgs = true;
|
||||
useUserPackages = true;
|
||||
backupFileExtension = "bak";
|
||||
sharedModules = [
|
||||
inputs.sops-nix.homeManagerModules.sops
|
||||
inputs.lazyvim.homeManagerModules.default
|
||||
];
|
||||
extraSpecialArgs = {
|
||||
@@ -21,7 +24,7 @@ let
|
||||
};
|
||||
in
|
||||
{
|
||||
# ── NixOS host builder ──────────────────────────────
|
||||
# ── NixOS 主机构建器 ─────────────────────────────────
|
||||
mkNixos =
|
||||
{
|
||||
hostname,
|
||||
@@ -32,7 +35,12 @@ in
|
||||
lib.nixosSystem {
|
||||
inherit system;
|
||||
specialArgs = {
|
||||
inherit inputs hostname username;
|
||||
inherit
|
||||
inputs
|
||||
hostname
|
||||
username
|
||||
sshKeys
|
||||
;
|
||||
};
|
||||
modules = [
|
||||
../modules/shared
|
||||
@@ -45,7 +53,7 @@ in
|
||||
++ extraModules;
|
||||
};
|
||||
|
||||
# ── nix-darwin host builder ─────────────────────────
|
||||
# ── nix-darwin 主机构建器 ────────────────────────────
|
||||
mkDarwin =
|
||||
{
|
||||
hostname,
|
||||
@@ -56,7 +64,12 @@ in
|
||||
inputs.nix-darwin.lib.darwinSystem {
|
||||
inherit system;
|
||||
specialArgs = {
|
||||
inherit inputs hostname username;
|
||||
inherit
|
||||
inputs
|
||||
hostname
|
||||
username
|
||||
sshKeys
|
||||
;
|
||||
};
|
||||
modules = [
|
||||
../modules/shared
|
||||
|
||||
+29
-26
@@ -1,37 +1,33 @@
|
||||
{ pkgs, username, ... }:
|
||||
{
|
||||
pkgs,
|
||||
username,
|
||||
sshKeys,
|
||||
...
|
||||
}:
|
||||
|
||||
{
|
||||
# ── Primary user (required by nix-darwin) ──────────
|
||||
system.primaryUser = username;
|
||||
|
||||
# ── Shell ──────────────────────────────────────────
|
||||
programs.fish.enable = true;
|
||||
# ── 免密 sudo ────────────────────────────────────────
|
||||
security.sudo.extraConfig = ''
|
||||
${username} ALL=(ALL) NOPASSWD:ALL
|
||||
'';
|
||||
|
||||
# ── SSH ───────────────────────────────────────────
|
||||
services.openssh.enable = true;
|
||||
|
||||
# ── User ───────────────────────────────────────────
|
||||
users.knownUsers = [ username ];
|
||||
users.users.${username} = {
|
||||
home = "/Users/${username}";
|
||||
shell = pkgs.fish;
|
||||
uid = 501;
|
||||
openssh.authorizedKeys.keys = [
|
||||
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIDRTOo48gzzRGT+bF9dzJCFJu61YgsQVONFtxU9kTPIg"
|
||||
];
|
||||
openssh.authorizedKeys.keys = sshKeys;
|
||||
};
|
||||
|
||||
# ── Fonts ──────────────────────────────────────────
|
||||
fonts.packages = with pkgs; [
|
||||
maple-mono.NF-CN-unhinted
|
||||
nerd-fonts.symbols-only
|
||||
];
|
||||
|
||||
# ── macOS system preferences ───────────────────────
|
||||
# ── macOS 系统偏好设置 ────────────────────────────────
|
||||
system.defaults = {
|
||||
LaunchServices.LSQuarantine = false;
|
||||
dock = {
|
||||
autohide = true;
|
||||
autohide-delay = 0.0;
|
||||
autohide-time-modifier = 0.15;
|
||||
show-recents = false;
|
||||
mru-spaces = false;
|
||||
wvous-tl-corner = 1;
|
||||
@@ -39,35 +35,40 @@
|
||||
wvous-bl-corner = 1;
|
||||
wvous-br-corner = 1;
|
||||
};
|
||||
finder = {
|
||||
AppleShowAllExtensions = true;
|
||||
FXPreferredViewStyle = "clmv";
|
||||
};
|
||||
finder.FXPreferredViewStyle = "clmv";
|
||||
NSGlobalDomain = {
|
||||
AppleShowAllExtensions = true;
|
||||
InitialKeyRepeat = 15;
|
||||
KeyRepeat = 2;
|
||||
};
|
||||
CustomUserPreferences."ch.sudo.cyberduck" = {
|
||||
# 永久禁用捐赠提示(日期设为遥远的未来)
|
||||
"donate.reminder.date" = 253402300799000;
|
||||
};
|
||||
};
|
||||
|
||||
# ── Homebrew ───────────────────────────────────────
|
||||
homebrew = {
|
||||
enable = true;
|
||||
greedyCasks = true; # always upgrade casks even if they auto-update
|
||||
greedyCasks = true; # 即使 cask 自动更新也始终升级
|
||||
# 已废弃:Homebrew 将于 2026-09 后移除 --no-quarantine
|
||||
# 待所有 cask 通过 Gatekeeper(签名且公证)后移除此项
|
||||
caskArgs.no_quarantine = true;
|
||||
|
||||
taps = [
|
||||
"goooler/repo"
|
||||
];
|
||||
|
||||
brews = [
|
||||
"mole" # broken in nixpkgs
|
||||
"mole"
|
||||
];
|
||||
|
||||
# GUI apps
|
||||
# GUI 应用
|
||||
casks = [
|
||||
"1password"
|
||||
"brave-browser"
|
||||
"cherry-studio"
|
||||
"cyberduck"
|
||||
"dbeaver-community"
|
||||
"discord"
|
||||
"feishu"
|
||||
@@ -83,6 +84,7 @@
|
||||
"raycast"
|
||||
"spotify"
|
||||
"telegram-desktop"
|
||||
"tencent-meeting"
|
||||
"termius"
|
||||
"visual-studio-code"
|
||||
"wechat"
|
||||
@@ -91,6 +93,7 @@
|
||||
|
||||
# Mac App Store
|
||||
masApps = {
|
||||
"iPreview" = 1519213509;
|
||||
"Microsoft Word" = 462054704;
|
||||
"Microsoft Excel" = 462058435;
|
||||
"Microsoft PowerPoint" = 462062816;
|
||||
@@ -101,7 +104,7 @@
|
||||
onActivation = {
|
||||
autoUpdate = true;
|
||||
upgrade = true;
|
||||
cleanup = "zap"; # remove anything not declared above
|
||||
cleanup = "zap"; # 移除所有未声明的内容
|
||||
};
|
||||
};
|
||||
}
|
||||
|
||||
@@ -1,18 +0,0 @@
|
||||
{ pkgs, ... }:
|
||||
|
||||
{
|
||||
# ── System-essential packages ──────────────────────
|
||||
# User-level tools live in home-manager (home/)
|
||||
environment.systemPackages = with pkgs; [
|
||||
curl
|
||||
git
|
||||
vim
|
||||
wget
|
||||
];
|
||||
|
||||
# ── Fonts ──────────────────────────────────────────
|
||||
fonts.packages = with pkgs; [
|
||||
maple-mono.NF-CN-unhinted
|
||||
nerd-fonts.symbols-only
|
||||
];
|
||||
}
|
||||
+17
-12
@@ -1,28 +1,33 @@
|
||||
{ pkgs, username, ... }:
|
||||
{
|
||||
pkgs,
|
||||
username,
|
||||
sshKeys,
|
||||
...
|
||||
}:
|
||||
|
||||
{
|
||||
imports = [
|
||||
./base.nix
|
||||
./docker.nix
|
||||
./locale.nix
|
||||
];
|
||||
|
||||
# ── Default shell ──────────────────────────────────
|
||||
programs.fish.enable = true;
|
||||
environment.systemPackages = with pkgs; [
|
||||
curl
|
||||
git
|
||||
ghostty.terminfo
|
||||
];
|
||||
|
||||
# ── SSH ──────────────────────────────────────────
|
||||
services.openssh.enable = true;
|
||||
i18n = {
|
||||
defaultLocale = "en_US.UTF-8";
|
||||
supportedLocales = [ "en_US.UTF-8/UTF-8" ];
|
||||
};
|
||||
time.timeZone = "Asia/Shanghai";
|
||||
|
||||
# ── Default user ───────────────────────────────────
|
||||
users.users.${username} = {
|
||||
isNormalUser = true;
|
||||
shell = pkgs.fish;
|
||||
extraGroups = [ "wheel" ];
|
||||
openssh.authorizedKeys.keys = [
|
||||
"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIDRTOo48gzzRGT+bF9dzJCFJu61YgsQVONFtxU9kTPIg"
|
||||
];
|
||||
openssh.authorizedKeys.keys = sshKeys;
|
||||
};
|
||||
|
||||
# ── sudo ───────────────────────────────────────────
|
||||
security.sudo.wheelNeedsPassword = false;
|
||||
}
|
||||
|
||||
@@ -8,8 +8,4 @@
|
||||
environment.systemPackages = with pkgs; [
|
||||
docker-compose
|
||||
];
|
||||
|
||||
# WSL 环境下如使用 Docker Desktop,可改为:
|
||||
# wsl.docker-desktop.enable = true;
|
||||
# 并将上面的 virtualisation.docker.enable 设为 false
|
||||
}
|
||||
|
||||
@@ -1,10 +0,0 @@
|
||||
{ ... }:
|
||||
|
||||
{
|
||||
i18n = {
|
||||
defaultLocale = "en_US.UTF-8";
|
||||
supportedLocales = [ "en_US.UTF-8/UTF-8" ];
|
||||
};
|
||||
|
||||
time.timeZone = "Asia/Shanghai";
|
||||
}
|
||||
@@ -1,3 +1,10 @@
|
||||
{
|
||||
imports = [ ./nix.nix ];
|
||||
imports = [
|
||||
./fonts.nix
|
||||
./nix.nix
|
||||
];
|
||||
|
||||
programs.fish.enable = true;
|
||||
programs._1password.enable = true;
|
||||
services.openssh.enable = true;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,8 @@
|
||||
{ pkgs, ... }:
|
||||
|
||||
{
|
||||
fonts.packages = with pkgs; [
|
||||
maple-mono.NF-CN-unhinted
|
||||
nerd-fonts.symbols-only
|
||||
];
|
||||
}
|
||||
@@ -11,7 +11,7 @@
|
||||
warn-dirty = false;
|
||||
};
|
||||
|
||||
# Disable channels — we use flakes exclusively
|
||||
# 禁用 channels — 仅使用 flakes
|
||||
nix.channel.enable = false;
|
||||
|
||||
nixpkgs = {
|
||||
|
||||
@@ -1,19 +0,0 @@
|
||||
ai_gateway_base_url: ENC[AES256_GCM,data:5/F4Tp6O4cYcpV6j00WOk2kXRd9iUorvD2Fl5LWKy9yJgfA=,iv:f09QoozjEEvblSOlDutw3CODju6DlTOKSjgPS5ypfJQ=,tag:ojD9CbG6ZiL3qlUzTcp4/w==,type:str]
|
||||
ai_gateway_api_key: ENC[AES256_GCM,data:bGr4RGGOANmUNY8fZzhdq4/0hdc+3g9adFaNoXTOAF823iZAbtLi6jC7EXVrDJYuTjBH,iv:YLMecyk3yIAcSY63gmEJm7NJcFD9vE0D8zqb1vNJd98=,tag:w1GThmuY3aBNr15VPOtuNg==,type:str]
|
||||
exa_api_key: ENC[AES256_GCM,data:DqZXFCHP1wpzrvXzLtmtooqKV0ljLTmAARWnfyFjm+tDmqMl,iv:7cDwuVudmWkwoI77XX5azmuOUKrUL3akI53wDc5CJks=,tag:BJZl7M0C9EQAnELcrWYN4Q==,type:str]
|
||||
context7_api_key: ENC[AES256_GCM,data:XjwUQSarEtvWA0wnbRDn8QqFxSpCQphpzgTSeK2NVcn7Z0GLTpUkalCcFg==,iv:ttULoAsJ/4PhuE/LIVok7CaekVWO3FHwKGhjUQiG0E0=,tag:Va7wdsz90LF4LWpeQYP6Iw==,type:str]
|
||||
sops:
|
||||
age:
|
||||
- recipient: age1w74wqpmum6xa3mk5p7ya620e8mhn9afdyf30gh3fk44javxsmvssm4hs64
|
||||
enc: |
|
||||
-----BEGIN AGE ENCRYPTED FILE-----
|
||||
YWdlLWVuY3J5cHRpb24ub3JnL3YxCi0+IFgyNTUxOSArK24ySVh3cU1taUlJUENu
|
||||
bnpLRDlwN1JYRGJpNFVpU3ZjbkZrTlBxK2drCkZCcE9ZVWN1YitZZEM4NjRkUjAx
|
||||
Uy9yZ3F4TkRhNEpEMzRPVmM5ZjJmTW8KLS0tIDR1QVlFSkpEY2ZQZWFpOXVVTkR1
|
||||
YUFlVW1IcGpVdjRsMmlmL1lOeEQzY1EKH1K2NomPsote6PGp30ZASKKwQoZi9x5F
|
||||
UWPj6xphWXp/7lFE7XpujKU323tFj7mZ+wRCb77T9QTNbg8zGsUO/A==
|
||||
-----END AGE ENCRYPTED FILE-----
|
||||
lastmodified: "2026-04-11T15:51:24Z"
|
||||
mac: ENC[AES256_GCM,data:x3Os/6i9jdmyIitD2dnz9Dl2GPLDVQlbPfVMRnebixFJ5fX6L0BqPRVVG20FvtCUQSzTMKp5eVZPRtti3wkr5TyQHz/0bz65B7Ucq3ssnpz0Hh/X8JyLRb6dKyRiiE3kIHf82nq+Do5oFUEG95LmRvhvbVdIzdMF/TJNVXOd4DQ=,iv:hIljr/1Y0Ra02Y4PwykNjhhxzxYFeMc1/waSCEy2skA=,tag:NoLozwKMPZVxKAg8g6R3UA==,type:str]
|
||||
unencrypted_suffix: _unencrypted
|
||||
version: 3.12.2
|
||||
Reference in New Issue
Block a user