From 09bc9da6d9e8481ffaabdcb00314073bca41cc5d Mon Sep 17 00:00:00 2001
From: m3tm3re
Date: Sun, 26 Apr 2026 14:10:54 +0200
Subject: [PATCH] chore: complete AGENTS.md documentation
- Add comprehensive project documentation to AGENTS.md
- Remove stale docs from docs/ directory
- Update agent configs (agents.nix, pi.nix)
- Update python.nix language config
- Update .gitignore
---
.gitignore | 5 +
AGENTS.md | 485 ++++++------
docs/AGENIX-GUIDE.md | 191 -----
.../2026-04-26-home-profile-restructuring.md | 727 ------------------
docs/plans/2026-04-27-missing-packages.md | 259 -------
home/coding/agents/agents.nix | 3 +-
home/coding/agents/pi.nix | 20 +-
home/coding/languages/python.nix | 13 +-
8 files changed, 281 insertions(+), 1422 deletions(-)
delete mode 100644 docs/AGENIX-GUIDE.md
delete mode 100644 docs/plans/2026-04-26-home-profile-restructuring.md
delete mode 100644 docs/plans/2026-04-27-missing-packages.md
diff --git a/.gitignore b/.gitignore
index f10a974..1953c13 100644
--- a/.gitignore
+++ b/.gitignore
@@ -38,3 +38,8 @@ opencode.json
.cache
.pi*
.worktrees/
+
+# Beads / Dolt files (added by bd init)
+.dolt/
+*.db
+.beads-credential-key
diff --git a/AGENTS.md b/AGENTS.md
index 69ede44..77acb08 100644
--- a/AGENTS.md
+++ b/AGENTS.md
@@ -1,274 +1,299 @@
-# NIXOS CONFIGURATION KNOWLEDGE BASE
+# Agent Instructions
-**Generated:** 2025-12-31 16:13:40 UTC
-**Commit:** ebc8291
-**Branch:** HEAD
+This project uses **bd** (beads) for issue tracking. Run `bd prime` for full workflow context.
-## OVERVIEW
-Personal NixOS configuration managing 6 hosts (4 servers, 2 desktops) using flakes, agenix secrets, and feature-based home-manager setup.
+## Quick Reference
-## STRUCTURE
-```
-./
-├── flake.nix # Main entry: host definitions, inputs, outputs
-├── secrets.nix # Agenix public key mappings
-├── hosts/
-│ ├── common/ # Shared: base config, users, extraServices, ports
-│ ├── m3-atlas/ # Server: 20+ containerized services with Traefik
-│ ├── m3-helios/ # Server: AdGuard, internal routing
-│ ├── m3-ares/ # Desktop: NVIDIA GPU, Btrfs
-│ ├── m3-kratos/ # Desktop: AMD GPU, ZFS
-│ └── m3-aether/ # Cloud VM
-├── home/
-│ ├── common/ # Home-manager base config
-│ ├── features/ # Modular feature toggles (cli, desktop, coding)
-│ └── m3tam3re/ # Per-host user configs
-├── modules/ # Custom NixOS/home-manager modules
-├── overlays/ # Package overlays (stable, locked, pinned, master)
-├── pkgs/ # Custom package definitions
-└── secrets/ # Agenix encrypted .age files (19 secrets)
+```bash
+bd ready # Find available work
+bd show # View issue details
+bd update --claim # Claim work atomically
+bd close # Complete work
+bd dolt push # Push beads data to remote
```
-## WHERE TO LOOK
+## Non-Interactive Shell Commands
-| Task | Location | Notes |
-|------|----------|-------|
-| Add new host | `flake.nix` + `hosts//` | Copy template from m3-atlas (server) or m3-ares (desktop) |
-| Add service to m3-atlas | `hosts/m3-atlas/services/` | See containers/ for Podman + Traefik pattern |
-| Configure desktop features | `home/features/desktop/` | Feature toggles with mkEnableOption |
-| Add CLI tool | `home/features/cli/` | Fish + Nushell integration expected |
-| Manage secrets | `secrets.nix` + `agenix -e` | SSH keys defined in secrets.nix |
-| Define ports | `hosts/common/ports.nix` | Centralized port registry |
-| Add user | `hosts/common/users/` | Shared across all hosts |
-| Custom packages | `pkgs/default.nix` | Exposed via flake outputs |
+**ALWAYS use non-interactive flags** with file operations to avoid hanging on confirmation prompts.
-## CONVENTIONS
+Shell commands like `cp`, `mv`, and `rm` may be aliased to include `-i` (interactive) mode on some systems, causing the agent to hang indefinitely waiting for y/n input.
-### Secrets (agenix)
-- **Create**: `agenix -e secrets/.age` after adding keys to `secrets.nix`
-- **Reference**: `config.age.secrets..path` in service configs
-- **Pattern**: Service env files use `environmentFiles = [config.age.secrets.-env.path]`
+**Use these forms instead:**
-### Service Organization
-- **Native services**: `hosts//services/.nix`
-- **Containers**: `hosts//services/containers/.nix`
-- **Traefik integration**: All m3-atlas services include dynamic config for SSL + routing
-- **Networking**: Containers use dedicated `web` network (10.89.0.0/24) with static IPs
+```bash
+# Force overwrite without prompting
+cp -f source dest # NOT: cp source dest
+mv -f source dest # NOT: mv source dest
+rm -f file # NOT: rm file
-### Port Management
-- **Registry**: All ports defined in `hosts/common/ports.nix`
-- **Access**: `config.m3ta.ports.get "service-name"`
-- **Convention**: Internal services use 3000-3020 range
+# For recursive operations
+rm -rf directory # NOT: rm -r directory
+cp -rf source dest # NOT: cp -r source dest
+```
-### Home-Manager Features
-- **Enable**: `features...enable = true` in user config
-- **Categories**: `cli`, `desktop`, `coding`
-- **Pattern**: Features are opt-in modules with default.nix aggregators
+**Other commands that may prompt:**
-### Multiple nixpkgs Inputs
-- **stable**: 25.11 release
-- **locked/pinned**: Specific commits for compatibility
-- **master**: Bleeding edge
-- **m3ta-nixpkgs**: Custom local overlay at `path:/home/m3tam3re/p/nix/nixpkgs`
+- `scp` - use `-o BatchMode=yes` for non-interactive
+- `ssh` - use `-o BatchMode=yes` to fail instead of prompting
+- `apt-get` - use `-y` flag
+- `brew` - use `HOMEBREW_NO_AUTO_UPDATE=1` env var
-## CODING RULES
+
-This project uses coding rules from the AGENTS repository (`inputs.agents`) plus project-specific conventions.
+## Beads Issue Tracker
-### Standard Rules (AGENTS repo)
+This project uses **bd (beads)** for issue tracking. Run `bd prime` to see full workflow context and commands.
-| Rule | Source | Purpose |
-|------|--------|---------|
-| `languages/nix.md` | AGENTS/rules/ | Nix language conventions, flake patterns |
-| `concerns/coding-style.md` | AGENTS/rules/ | General coding principles |
-| `concerns/naming.md` | AGENTS/rules/ | Naming conventions per language |
-| `concerns/documentation.md` | AGENTS/rules/ | Documentation standards |
-| `concerns/testing.md` | AGENTS/rules/ | Testing guidelines |
-| `concerns/git-workflow.md` | AGENTS/rules/ | Commit message format, branch naming |
-| `concerns/project-structure.md` | AGENTS/rules/ | Project layout conventions |
+### Quick Reference
-### NixOS-Config Specific Rules
+```bash
+bd ready # Find available work
+bd show # View issue details
+bd update --claim # Claim work
+bd close # Complete work
+```
-#### Project Structure
+### Rules
+
+- Use `bd` for ALL task tracking — do NOT use TodoWrite, TaskCreate, or markdown TODO lists
+- Run `bd prime` for detailed command reference and session close protocol
+- Use `bd remember` for persistent knowledge — do NOT use MEMORY.md files
+
+## Session Completion
+
+**When ending a work session**, you MUST complete ALL steps below. Work is NOT complete until `git push` succeeds.
+
+**MANDATORY WORKFLOW:**
+
+1. **File issues for remaining work** - Create issues for anything that needs follow-up
+2. **Run quality gates** (if code changed) - Tests, linters, builds
+3. **Update issue status** - Close finished work, update in-progress items
+4. **PUSH TO REMOTE** - This is MANDATORY:
+ ```bash
+ git pull --rebase
+ bd dolt push
+ git push
+ git status # MUST show "up to date with origin"
+ ```
+5. **Clean up** - Clear stashes, prune remote branches
+6. **Verify** - All changes committed AND pushed
+7. **Hand off** - Provide context for next session
+
+**CRITICAL RULES:**
+
+- Work is NOT complete until `git push` succeeds
+- NEVER stop before pushing - that leaves work stranded locally
+- NEVER say "ready to push when you are" - YOU must push
+- If push fails, resolve and retry until it succeeds
+
+
+# Project Agent
+
+**Workspace Path:** `/home/m3tam3re/p/NIX/nixos-config`
+_(Note to Pi: Your file write/edit tools run in a different directory by default. You MUST use absolute paths starting with the Workspace Path above for ALL file operations!)_
+
+**Generated:** 2026-04-26
+
+---
+
+## Stack
+
+| Component | Version/Source |
+| ---------------- | --------------------------------- |
+| **Nixpkgs** | nixos-unstable + 25.05 stable |
+| **Home Manager** | github:nix-community/home-manager |
+| **Agenix** | github:ryantm/agenix |
+| **Disko** | github:nix-community/disko |
+| **NUR** | github:nix-community/NUR |
+| **Formatter** | alejandra |
+| **Linters** | statix, deadnix |
+| **IDE** | nixd |
+| **Hermes Agent** | NousResearch/hermes-agent |
+| **LLM Agents** | numtide/llm-agents.nix |
+
+---
+
+## Structure
```
nixos-config/
-├── flake.nix # Entry point
-├── hosts/ # Host-specific NixOS configs
-│ ├── common/ # Shared: ports, users, base config
-│ ├── m3-atlas/ # Server with Traefik hub
-│ ├── m3-helios/ # AdGuard DNS
-│ ├── m3-ares/ # Desktop (NVIDIA)
-│ └── m3-kratos/ # Desktop (AMD)
-├── home/ # Home-manager configs
-│ ├── common/ # Shared home config
-│ ├── features/ # Feature modules (cli, desktop, coding)
-│ └── m3tam3re/ # User-specific configs
-├── modules/ # Custom NixOS/HM modules
-├── overlays/ # Package overlays
-├── pkgs/ # Custom packages
-└── secrets/ # Agenix encrypted secrets
+├── flake.nix # Entry point: hosts, overlays, dev shells
+├── coding-rules.json # Opencode rules configuration
+│
+├── hosts/ # Per-host NixOS configurations
+│ ├── common/ # Shared across all hosts
+│ │ ├── users/ # User definitions
+│ │ ├── ports.nix # Network ports config
+│ │ └── extraServices/ # Common service toggles
+│ ├── m3-ares/ # Main desktop
+│ ├── m3-atlas/ # Desktop with disko
+│ ├── m3-helios/ # Desktop with disko
+│ ├── m3-hermes/ # Desktop with disko + hermes-agent
+│ └── m3-kratos/ # Server with NUR
+│
+├── modules/ # Reusable NixOS/home-manager modules
+│ ├── nixos/ # NixOS-specific modules
+│ │ └── default.nix # Imports common + service configs
+│ └── home-manager/ # Home-manager configurations
+│
+├── home/ # Per-user, per-host home configs
+│ └── m3tam3re/
+│ └── m3-daedalus.nix
+│
+├── overlays/ # Package overlays
+│ ├── default.nix # Stable/locked/master branches
+│ └── mods/ # Package modifications
+│
+├── pkgs/ # Custom packages
+│
+├── secrets/ # Encrypted secrets (agenix)
+│ └── secrets.nix
+│
+├── .opencode-rules/ # Opencode AI rules
+│ ├── concerns/ # Coding style rules
+│ ├── languages/nix.md # Nix conventions
+│ └── USAGE.md
+│
+└── .pi/ # Agent configuration
```
-#### Naming Conventions
+---
-| Type | Convention | Example |
-|------|------------|---------|
-| Hosts | mythological-names | `m3-atlas`, `m3-helios` |
-| Files | hyphen-case | `my-service.nix` |
-| Variables | camelCase | `portHelpers`, `serviceConfig` |
-| Options | m3ta.* | `config.m3ta.ports.get` |
-| Packages | lowercase-hyphen | `hyprpaper-random` |
+## Commands
-#### Nix Module Pattern
+| Action | Command | Notes |
+| -------------------- | ---------------------------------------------------------------------- | ------------------------------------------------- |
+| **Enter dev shell** | `nix develop` | Includes alejandra, nixd, agenix, statix, deadnix |
+| **Build host** | `sudo nixos-rebuild switch --flake .#m3-ares` | Replace hostname as needed |
+| **Dry run build** | `sudo nixos-rebuild dry-run --flake .#m3-ares` | Validate without applying |
+| **List hosts** | `nix flake show` | Shows all NixOS configurations |
+| **Update flake** | `sudo nixos-rebuild switch --flake .#m3-ares --update-input nixpkgs` | Update specific input |
+| **Format code** | `alejandra .` | Run before committing |
+| **Check lint** | `statix check .` | Run statix for antipatterns |
+| **Remove dead code** | `deadnix -w .` | Clean up unused let bindings |
+| **Build ISO** | `nix build .#nixosConfigurations.m3-ares.config.system.build.isoImage` | Generate install ISO |
+
+---
+
+## Conventions
+
+### Formatting & Style
+
+- **Formatter:** `alejandra` (mandatory, run before commits)
+- **Indentation:** 2 spaces (alejandra default)
+- **Variables:** camelCase (e.g., `maxRetryAttempts`)
+- **Types/Modules:** PascalCase (e.g., `MyService`)
+- **Constants:** UPPER_SNAKE_CASE (e.g., `MAX_RETRIES`)
+- **Files:** hyphen-case (e.g., `my-file.nix`)
+
+### Nix Module Patterns
```nix
{ config, lib, pkgs, ... }:
-with lib; let
- cfg = config.m3ta.myModule;
-in {
- options.m3ta.myModule = {
- enable = mkEnableOption "my module";
- };
-
- config = mkIf cfg.enable {
- # Configuration here
+{
+ options.myService.enable = lib.mkEnableOption "my service";
+ config = lib.mkIf config.myService.enable {
+ services.myService.enable = true;
};
}
```
-#### Anti-Patterns (Never Do)
+### Conditionals
-| Don't | Do Instead |
-|-------|------------|
-| Hardcode ports | `config.m3ta.ports.get "service"` |
-| Skip secrets.nix update | Add keys first, then `agenix -e` |
-| Containers outside web network | `--network=web --ip=10.89.0.N` |
-| Skip Traefik for public services | Configure dynamic config |
-| Bypass extraServices flags | Use feature flags properly |
-| Use `fetchTarball` | Use flake inputs |
-| Use `with pkgs;` in modules | Explicit `pkgs.package` |
-
-### Formatting & Linting
-
-```bash
-# Format (alejandra)
-nix fmt
-
-# Lint (statix, deadnix - only in dev shell)
-nix develop
-statix check .
-deadnix .
-
-# Validate flake
-nix flake check
-```
-
-### Commit Conventions
-
-Format: `: `
-
-Types: `feat`, `fix`, `docs`, `style`, `refactor`, `chore`
-
-Examples:
-- `feat: add new host m3-hermes`
-- `fix: resolve port conflict in mem0 module`
-- `docs: update AGENTS.md with new service`
-- `style: format nix files`
-- `refactor: simplify port management`
-- `chore: update nixpkgs inputs`
-
-### Tools in Dev Shell
-
-| Tool | Purpose |
-|------|---------|
-| `alejandra` | Nix code formatter |
-| `nixd` | Nix language server |
-| `statix` | Nix linter |
-| `deadnix` | Find dead code |
-| `agenix` | Secret management |
-
-## COMMANDS
-```bash
-# Build/deploy specific host
-sudo nixos-rebuild switch --flake .#m3-ares
-
-# Build/deploy current host
-sudo nixos-rebuild switch --flake .#$(uname -n)
-
-# Home-manager update
-home-manager --flake . switch
-
-# Update all flake inputs
-nix flake update
-
-# Add/edit secret
-agenix -e secrets/.age
-
-# Infrastructure shell (OpenTofu)
-nix develop .#infraShell
-
-# Check configuration (no activation)
-nixos-rebuild dry-build --flake .#
-```
-
-## TRAEFIK PATTERNS (m3-atlas only)
-
-### SSL Termination
-- **Provider**: Godaddy DNS challenge
-- **Cert storage**: `/var/lib/traefik/acme.json`
-- **Config**: `hosts/m3-atlas/services/traefik.nix`
-
-### Service Integration Template
```nix
-services.traefik.dynamicConfigOptions.http = {
- services..loadBalancer.servers = [{ url = "http://127.0.0.1:"; }];
- routers. = {
- rule = "Host(`.m3ta.dev`)";
- service = "";
- tls.certResolver = "godaddy";
- };
-};
+config = lib.mkMerge [
+ (lib.mkIf cfg.enable { ... })
+ (lib.mkIf cfg.extraConfig { ... })
+];
```
-### Container Pattern
-- **Network**: `--network=web --ip=10.89.0.`
-- **Ports**: Bind localhost only (`127.0.0.1::`)
-- **Database access**: `--add-host=mysql:10.89.0.1` (gateway IP)
+### Anti-Patterns (AVOID)
-## HOST ROLES
+- **Never use `with pkgs;`** — always use explicit package references
+- **Never use `builtins.fetchTarball`** — use flake inputs instead
+- **Never use `import `** — always use inputs
+- **Never use `builtins.getAttr/hasAttr`** — use `lib.attrByPath` or `lib.optionalAttrs`
+- **Avoid anonymous functions in config** — extract to named lets
-| Host | Type | Hardware | Purpose |
-|------|------|----------|---------|
-| m3-atlas | Server | x86_64, disko | 20+ services, Traefik hub, PostgreSQL, MySQL |
-| m3-helios | Server | x86_64, disko | AdGuard DNS, internal routing |
-| m3-ares | Desktop | NVIDIA, Btrfs | Personal workstation, n8n, PostgreSQL |
-| m3-kratos | Desktop | AMD, ZFS | Workstation, mem0, PostgreSQL |
-| m3-aether | Cloud | QEMU | General purpose VM |
-| m3-daedalus | Laptop | home-only | Portable (no full NixOS config) |
+### Imports
-## ANTI-PATTERNS (THIS PROJECT)
+- Use flake inputs for dependencies (e.g., `inputs.home-manager.nixosModules.home-manager`)
+- Import relative paths with `./` or `../`
+- Never use absolute paths in imports
-- **DON'T** add secrets to `secrets/` without updating `secrets.nix` public keys
-- **DON'T** hardcode ports - use `config.m3ta.ports.get` or add to registry
-- **DON'T** create containers outside the `web` network on m3-atlas
-- **DON'T** skip Traefik config for public-facing services on m3-atlas
-- **DON'T** bypass extraServices flags - use `hosts/common/extraServices/` pattern
-- **DON'T** commit unencrypted secrets or test with real credentials
+### Secrets
-## UNIQUE TO THIS CONFIG
+- Secrets managed via **agenix** in `secrets/` directory
+- Never commit plaintext secrets
+- Use `.nix` extension for secret files
-- **Custom m3ta-nixpkgs**: Local overlay for unreleased/patched packages
-- **extraServices abstraction**: Boolean flags to toggle Podman, Ollama, virtualisation per host
-- **Mythological naming**: All hosts named after Greek mythology
-- **Dual domain strategy**: New services on `m3ta.dev`, legacy redirects from `m3tam3re.com`
-- **Per-host nixpkgs versions**: Different hosts can use different nixpkgs commits via specialArgs
-- **Container IP registry**: Static IP assignments in 10.89.0.0/24 subnet for predictable networking
+---
-## NOTES
+## Key Files
-- m3-atlas is the service hub - most complex configuration
-- Secrets require host SSH keys defined in `secrets.nix` before `agenix -e` works
-- Fish and Nushell both configured - choose per-user with shell aliases
-- Color scheme (Dracula) applied via nix-colors across all visual tools
-- See subdirectory AGENTS.md for deep dives on containers, desktop features, CLI tools
+| File | Purpose |
+| ---------------------------------- | ------------------------------------------------------------------------------------------ |
+| `flake.nix` | Central entry point defining all hosts, overlays, packages, dev shells, and nixpkgs config |
+| `hosts/common/default.nix` | Shared Nix settings, nixpkgs overlays, home-manager integration, user defaults |
+| `hosts/m3-ares/default.nix` | Main desktop host configuration, imports common + service modules |
+| `hosts/m3-ares/configuration.nix` | Desktop environment config (Hyprland, display, audio, etc.) |
+| `hosts/m3-ares/programs.nix` | CLI tools, dev tools, shell configs |
+| `hosts/m3-ares/services/` | Service-specific configs (firewall, printing, etc.) |
+| `modules/nixos/default.nix` | Orchestrates common + configuration imports |
+| `overlays/default.nix` | Package version overrides (stable/locked/master branches) |
+| `.opencode-rules/languages/nix.md` | Nix-specific conventions and patterns |
+
+---
+
+## What to Avoid
+
+1. **Don't modify `flake.lock`** directly — use `nix flake update`
+2. **Don't use impure operations** — this is a pure flake-based config
+3. **Don't commit without formatting** — always run `alejandra .` first
+4. **Don't add packages to hosts directly** — prefer adding to overlays or using NUR
+5. **Don't hardcode paths** — use `inputs` and relative imports
+6. **Don't create monolithic modules** — keep functions under 20 lines
+7. **Don't skip the dry-run** — always test with `--dry-run` before switching
+8. **Don't use lib.mkDefault lightly** — understand the precedence implications
+
+---
+
+## Notes
+
+### Adding a New Host
+
+1. Add entry to `flake.nix` → `nixosConfigurations`
+2. Create directory in `hosts/` with:
+ - `default.nix` — imports common + specific configs
+ - `configuration.nix` — host-specific system config
+ - `hardware-configuration.nix` — from `nixos-generate-config`
+ - `programs.nix`, `services/`, `secrets.nix` as needed
+3. Run `sudo nixos-generate-config --dir ./hosts/new-host` first time
+
+### Adding a New Package
+
+1. For simple packages: add to appropriate overlay in `overlays/default.nix`
+2. For complex packages: create in `pkgs/` directory
+3. For upstream packages: use NUR or add as flake input
+
+### Development Workflow
+
+1. Edit config files
+2. Run `alejandra .` to format
+3. Run `statix check .` for linting
+4. Run `sudo nixos-rebuild dry-run --flake .#m3-ares`
+5. If successful: `sudo nixos-rebuild switch --flake .#m3-ares`
+
+### Remote Building
+
+```bash
+# Build on remote machine
+nix copy --to ssh://user@host .#nixosConfigurations.m3-ares.config.system.build.toplevel
+ssh user@host 'sudo nixos-rebuild switch --flake /nix/store/...-closure'
+```
+
+### Home Manager
+
+- Home configs live in `home/m3tam3re/`
+- Use `home-manager.users.m3tam3re` in host config
+- Access via `config.home-manager.users.m3tam3re`
diff --git a/docs/AGENIX-GUIDE.md b/docs/AGENIX-GUIDE.md
deleted file mode 100644
index 0d888db..0000000
--- a/docs/AGENIX-GUIDE.md
+++ /dev/null
@@ -1,191 +0,0 @@
-# Agenix Secret Management Guide
-
-A guide for creating and managing encrypted secrets using agenix in the nixos-config project.
-
-## Prerequisites
-
-- SSH key pair (ed25519 or rsa) in `~/.ssh/`
-- Access to the nixos-config repository
-- Secret added to `secrets.nix` with appropriate public keys
-
----
-
-## Creating a New Secret
-
-### Step 1: Add Secret to secrets.nix
-
-Edit `secrets.nix` and add a new entry:
-
-```nix
-"secrets/.age".publicKeys = systems ++ users;
-```
-
-Where:
-- `` is the desired filename (without `.age`)
-- `systems` = hosts that can decrypt this secret
-- `users` = users that can decrypt this secret
-
-Example:
-```nix
-"secrets/my-service-api-key.age".publicKeys = systems ++ users;
-```
-
-### Step 2: Create the Encrypted Secret
-
-Navigate to the nixos-config directory:
-
-```bash
-cd ~/p/NIX/nixos-config
-```
-
-Generate a secure random token (if needed):
-
-```bash
-head -c 32 /dev/urandom | base64 | tr -d '\n'
-```
-
-Or use a specific value:
-
-```bash
-echo -n "your-secret-value-here" > /tmp/token.txt
-```
-
-Encrypt and create the secret file:
-
-```bash
-cat /tmp/token.txt | RULES=./secrets.nix nix develop . --command sh -c 'agenix -e secrets/.age'
-```
-
-The `-e` flag encrypts stdin content into the age file. If no stdin is provided, agenix opens your editor.
-
-### Step 3: Verify the Secret
-
-Decrypt to verify:
-
-```bash
-RULES=./secrets.nix nix develop . --command agenix -d secrets/.age
-```
-
-You should see your secret value printed to stdout.
-
-### Step 4: Use in NixOS Configuration
-
-Reference the secret in your service config:
-
-```nix
-{ config, ... }:
-
-{
- # For environment files
- environmentFiles = [ config.age.secrets."my-secret-name".path ];
-
- # For file-based secrets
- environmentFile = config.age.secrets."my-secret-name".path;
-}
-```
-
-The secret will be available at `/run/agenix/` when the system builds.
-
----
-
-## Common Patterns
-
-### Token-Based Registration (e.g., Tuwunel)
-
-```nix
-# secrets.nix
-"secrets/tuwunel-registration-token.age".publicKeys = systems ++ users;
-```
-
-```nix
-# services/tuwunel.nix
-settings.global = {
- allow_registration = true;
- registration_token_file = config.age.secrets."tuwunel-registration-token".path;
-};
-```
-
-### API Keys via Environment Files
-
-```nix
-# secrets.nix
-"secrets/my-service-env.age".publicKeys = systems ++ users;
-```
-
-Create `my-service-env.age` containing:
-```
-MY_SERVICE_API_KEY=your-key-here
-DATABASE_URL=postgres://...
-```
-
-Reference in config:
-```nix
-environmentFiles = [ config.age.secrets."my-service-env".path ];
-```
-
-### File-Based Secrets
-
-For binary files or specific file paths:
-
-```nix
-settings = {
- tls.cert = config.age.secrets."tls-cert".path;
- tls.key = config.age.secrets."tls-key".path;
-};
-```
-
----
-
-## Agenix Command Reference
-
-| Command | Description |
-|---------|-------------|
-| `agenix -e ` | Edit/create encrypted secret (opens editor or uses stdin) |
-| `agenix -d ` | Decrypt and print to stdout |
-| `agenix -r` | Re-encrypt all secrets (after changing public keys) |
-| `agenix --validate-config` | Validate secrets.nix syntax |
-
-### Environment Variables
-
-| Variable | Default | Description |
-|----------|---------|-------------|
-| `RULES` | `./secrets.nix` | Path to secrets.nix file |
-| `EDITOR` | `$EDITOR` | Editor for interactive editing |
-
----
-
-## Troubleshooting
-
-### "No identity found to decrypt"
-
-**Cause**: No SSH private key available.
-
-**Solution**: Ensure your private key is in `~/.ssh/`:
-- `~/.ssh/id_rsa`
-- `~/.ssh/id_ed25519`
-- Or specify with `-i /path/to/private/key`
-
-### "Failed to find config root"
-
-**Cause**: Agenix can't find `secrets.nix`.
-
-**Solution**: Use `RULES=./secrets.nix` or run from the nixos-config directory.
-
-### Rekeying Secrets
-
-After adding new public keys to `secrets.nix`, re-encrypt all secrets:
-
-```bash
-cd ~/p/NIX/nixos-config
-RULES=./secrets.nix nix develop . --command agenix -r
-```
-
----
-
-## Security Notes
-
-- Never commit plaintext secrets to git
-- Always use `secrets.nix` for encryption keys
-- Include only necessary hosts/users in public keys
-- Rotate secrets periodically
-- Use `agenix -r` after modifying public keys
diff --git a/docs/plans/2026-04-26-home-profile-restructuring.md b/docs/plans/2026-04-26-home-profile-restructuring.md
deleted file mode 100644
index e7627ee..0000000
--- a/docs/plans/2026-04-26-home-profile-restructuring.md
+++ /dev/null
@@ -1,727 +0,0 @@
-# Home Profile Restructuring Implementation Plan
-
-> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking.
-
-**Goal:** Restructure nixos-config/home/ from host-based to profile-based organization with clear separation between base, coding, profiles, desktop, and server layers.
-
-**Architecture:** Three-layer model: Base (always loaded) → Coding (profile-independent) → Profiles/Context (freely combinable with constraints). Desktop and Server contexts are mutually exclusive.
-
-**Tech Stack:** NixOS, Home Manager, Nix flakes
-
----
-
-## File Structure
-
-```
-home/
-├── base/ # IMMER geladen
-│ ├── default.nix
-│ ├── shell/
-│ │ ├── default.nix
-│ │ ├── nushell.nix # PRIMARY Shell
-│ │ └── starship.nix
-│ ├── cli-tools/
-│ │ ├── default.nix
-│ │ ├── fzf.nix
-│ │ ├── zellij.nix
-│ │ ├── nitch.nix
-│ │ └── television.nix
-│ └── secrets/
-│ └── secrets.nix
-│
-├── coding/ # Profil-unabhängig
-│ ├── default.nix
-│ ├── editor/
-│ │ ├── default.nix
-│ │ └── neovim.nix # Basis NeoVim (aus nixpkgs referenziert)
-│ ├── lsp/
-│ │ ├── default.nix
-│ │ └── servers.nix
-│ ├── git/
-│ │ └── git.nix
-│ └── agents/
-│ └── agents.nix # Agent-System (aus nixpkgs referenziert)
-│
-├── profiles/ # FREI KOMBINIERBAR
-│ ├── gaming/
-│ │ ├── default.nix
-│ │ ├── steam.nix
-│ │ └── gamescope.nix
-│ │
-│ └── media/
-│ ├── default.nix
-│ ├── obs.nix
-│ ├── ffmpeg.nix
-│ ├── yt-dlp.nix
-│ ├── kdenlive.nix
-│ └── handbrake.nix
-│
-├── desktop/ # NUR wenn context=desktop
-│ ├── default.nix
-│ ├── wm/
-│ │ ├── default.nix
-│ │ ├── hyprland.nix
-│ │ ├── wayland.nix
-│ │ └── rofi.nix
-│ ├── apps/
-│ │ ├── default.nix
-│ │ ├── obsidian.nix
-│ │ ├── office.nix
-│ │ ├── webapps.nix
-│ │ └── crypto.nix
-│ └── theme/
-│ ├── default.nix
-│ ├── fonts.nix
-│ ├── theme.nix
-│ └── wallpapers.nix
-│
-└── server/
- └── default.nix
-```
-
-**Key Integration Points:**
-
-| Component | Source | Notes |
-|-----------|--------|-------|
-| NeoVim Config | `inputs.m3ta-nixpkgs.pkgs.neovim-config` | Custom package in nixpkgs |
-| OpenCode Desktop | `inputs.m3ta-nixpkgs.pkgs.opencode-desktop` | Custom package |
-| Agent-System | `inputs.m3ta-nixpkgs.homeModules.coding.agents` | OpenCode, Claude Code, Pi |
-| Zed Editor | `inputs.m3ta-nixpkgs.homeModules.coding.editors` | Desktop-only via Zed Remote |
-| Editor Module | `inputs.m3ta-nixpkgs.homeModules.coding.editors` | NeoVim (base) + Zed (desktop) |
-
----
-
-## Phase 1: Create New Structure
-
-### Task 1: Create Directory Structure
-
-**Files:**
-
-- Create: `home/base/default.nix`
-- Create: `home/base/shell/default.nix`
-- Create: `home/base/shell/nushell.nix`
-- Create: `home/base/shell/starship.nix`
-- Create: `home/base/cli-tools/default.nix`
-- Create: `home/base/cli-tools/fzf.nix`
-- Create: `home/base/cli-tools/zellij.nix`
-- Create: `home/base/cli-tools/nitch.nix`
-- Create: `home/base/cli-tools/television.nix`
-- Create: `home/base/secrets/secrets.nix`
-- Create: `home/coding/default.nix`
-- Create: `home/coding/editor/default.nix`
-- Create: `home/coding/editor/neovim.nix`
-- Create: `home/coding/lsp/default.nix`
-- Create: `home/coding/lsp/servers.nix`
-- Create: `home/coding/git/git.nix`
-- Create: `home/coding/agents/agents.nix`
-- Create: `home/profiles/gaming/default.nix`
-- Create: `home/profiles/gaming/steam.nix`
-- Create: `home/profiles/gaming/gamescope.nix`
-- Create: `home/profiles/media/default.nix`
-- Create: `home/profiles/media/obs.nix`
-- Create: `home/profiles/media/ffmpeg.nix`
-- Create: `home/profiles/media/yt-dlp.nix`
-- Create: `home/profiles/media/kdenlive.nix`
-- Create: `home/profiles/media/handbrake.nix`
-- Create: `home/desktop/default.nix`
-- Create: `home/desktop/wm/default.nix`
-- Create: `home/desktop/wm/hyprland.nix`
-- Create: `home/desktop/wm/wayland.nix`
-- Create: `home/desktop/wm/rofi.nix`
-- Create: `home/desktop/apps/default.nix`
-- Create: `home/desktop/apps/obsidian.nix`
-- Create: `home/desktop/apps/office.nix`
-- Create: `home/desktop/apps/webapps.nix`
-- Create: `home/desktop/apps/crypto.nix`
-- Create: `home/desktop/theme/default.nix`
-- Create: `home/desktop/theme/fonts.nix`
-- Create: `home/desktop/theme/theme.nix`
-- Create: `home/desktop/theme/wallpapers.nix`
-- Create: `home/server/default.nix`
-- Modify: `home/default.nix` (Hauptaggregator)
-
-- [ ] **Step 1: Create home/base/default.nix**
-
-```nix
-# home/base/default.nix
-# Basis-Konfiguration: Shell + CLI-Tools + Secrets
-# Wird IMMER geladen (kein enable-Flag)
-
-{ inputs, lib, pkgs, ... }:
-
-{
- imports = [
- ./shell
- ./cli-tools
- ./secrets
- ];
-}
-```
-
-- [ ] **Step 2: Create home/base/shell/default.nix**
-
-```nix
-# home/base/shell/default.nix
-{ inputs, lib, pkgs, ... }:
-
-{
- imports = [
- ./nushell.nix
- ./starship.nix
- ];
-}
-```
-
-- [ ] **Step 3: Create home/base/shell/nushell.nix**
-
-Migrated from: `home/features/cli/nushell.nix`
-
-```nix
-# home/base/shell/nushell.nix
-# Primary shell - Nushell
-{ lib, pkgs, ... }:
-
-{
- programs.nushell = {
- enable = true;
- configFile = ...;
- };
-
- home.packages = with pkgs; [
- nushell
- ];
-}
-```
-
-- [ ] **Step 4: Create home/base/shell/starship.nix**
-
-Migrated from: `home/features/cli/starship.nix`
-
-- [ ] **Step 5: Create home/base/cli-tools/default.nix**
-
-```nix
-# home/base/cli-tools/default.nix
-{ ... }:
-
-{
- imports = [
- ./fzf.nix
- ./zellij.nix
- ./nitch.nix
- ./television.nix
- ];
-}
-```
-
-- [ ] **Step 6: Create CLI tool modules**
-
-Migrate from `home/features/cli/`:
-- `fzf.nix` → `home/base/cli-tools/fzf.nix`
-- `zellij.nix` → `home/base/cli-tools/zellij.nix`
-- `nitch.nix` → `home/base/cli-tools/nitch.nix`
-- `television.nix` → `home/base/cli-tools/television.nix`
-
-- [ ] **Step 7: Create home/base/secrets/secrets.nix**
-
-Migrated from: `home/features/cli/secrets.nix`
-
-- [ ] **Step 8: Create home/coding/default.nix**
-
-```nix
-# home/coding/default.nix
-# Coding-Konfiguration: Editor + LSP + Git + Agents
-# Wird geladen wenn coding Profil aktiviert
-
-{ inputs, lib, pkgs, ... }:
-
-{
- imports = [
- ./editor
- ./lsp
- ./git
- ./agents
- ];
-}
-```
-
-- [ ] **Step 9: Create home/coding/editor/default.nix**
-
-References: `inputs.m3ta-nixpkgs.homeModules.coding.editors`
-
-```nix
-# home/coding/editor/default.nix
-{ inputs, lib, pkgs, ... }:
-
-{
- # Importiert NeoVim (immer) + Zed (desktop)
- imports = [
- inputs.m3ta-nixpkgs.homeModules.coding.editors
- ];
-
- # NeoVim Config Package
- home.packages = [ inputs.m3ta-nixpkgs.packages.${pkgs.system}.neovim-config ];
-}
-```
-
-- [ ] **Step 10: Create home/coding/lsp/default.nix + servers.nix**
-
-Migrate LSP configuration from existing setup
-
-- [ ] **Step 11: Create home/coding/git/git.nix**
-
-```nix
-# home/coding/git/git.nix
-{ lib, pkgs, ... }:
-
-{
- programs.git = {
- enable = true;
- # Git configuration
- };
-}
-```
-
-- [ ] **Step 12: Create home/coding/agents/agents.nix**
-
-References: `inputs.m3ta-nixpkgs.homeModules.coding.agents`
-
-```nix
-# home/coding/agents/agents.nix
-{ inputs, lib, pkgs, ... }:
-
-{
- imports = [
- inputs.m3ta-nixpkgs.homeModules.coding.agents
- ];
-
- # Agent-Konfiguration
- coding.agents.opencode = {
- enable = true;
- agentsInput = inputs.agents;
- # modelOverrides...
- };
-}
-```
-
-- [ ] **Step 13: Create home/profiles/gaming/default.nix**
-
-```nix
-# home/profiles/gaming/default.nix
-# Gaming Profile - frei kombinierbar
-
-{ lib, pkgs, ... }:
-
-{
- imports = [
- ./steam.nix
- ./gamescope.nix
- ];
-}
-```
-
-- [ ] **Step 14: Create gaming profile modules**
-
-- `steam.nix` - Steam + Steam Deck Tools
-- `gamescope.nix` - Gamescope Session
-
-- [ ] **Step 15: Create home/profiles/media/default.nix**
-
-```nix
-# home/profiles/media/default.nix
-# Media Profile - Content Creation / Streaming
-
-{ lib, pkgs, ... }:
-
-{
- imports = [
- ./obs.nix
- ./ffmpeg.nix
- ./yt-dlp.nix
- ./kdenlive.nix
- ./handbrake.nix
- ];
-}
-```
-
-- [ ] **Step 16: Create media profile modules**
-
-Migrate from `home/features/desktop/media.nix`:
-- `obs.nix` - OBS Studio
-- `ffmpeg.nix` - FFmpeg + Tools
-- `yt-dlp.nix` - YouTube Downloader
-- `kdenlive.nix` - Kdenlive Video Editor
-- `handbrake.nix` - HandBrake
-
-- [ ] **Step 17: Create home/desktop/default.nix**
-
-```nix
-# home/desktop/default.nix
-# Desktop-Konfiguration - nur wenn context=desktop
-
-{ lib, pkgs, ... }:
-
-{
- # Zed Remote: Server-Zugriff via SSH
- programs.zed-editor = {
- enable = true;
- # Remote Connections Config
- };
-
- imports = [
- ./wm
- ./apps
- ./theme
- ];
-}
-```
-
-- [ ] **Step 18: Create home/desktop/wm modules**
-
-Migrate from `home/features/desktop/`:
-- `hyprland.nix` → `home/desktop/wm/hyprland.nix`
-- `wayland.nix` → `home/desktop/wm/wayland.nix`
-- `rofi.nix` → `home/desktop/wm/rofi.nix`
-
-- [ ] **Step 19: Create home/desktop/apps modules**
-
-Migrate from `home/features/desktop/`:
-- `obsidian.nix` → `home/desktop/apps/obsidian.nix`
-- `office.nix` → `home/desktop/apps/office.nix`
-- `webapps.nix` → `home/desktop/apps/webapps.nix`
-- `crypto.nix` → `home/desktop/apps/crypto.nix`
-
-- [ ] **Step 20: Create home/desktop/theme modules**
-
-Migrate from `home/features/desktop/`:
-- `fonts.nix` → `home/desktop/theme/fonts.nix`
-- `theme.nix` → `home/desktop/theme/theme.nix`
-- `wallpapers.nix` → `home/desktop/theme/wallpapers.nix`
-
-- [ ] **Step 21: Create home/server/default.nix**
-
-```nix
-# home/server/default.nix
-# Server-Konfiguration - nur wenn context=server
-# Minimal da primär via Zed Remote gearbeitet wird
-
-{ lib, pkgs, ... }:
-
-{
- # Server-spezifische Konfiguration falls nötig
-}
-```
-
-- [ ] **Step 22: Commit Phase 1**
-
-```bash
-git add home/
-git commit -m "feat(home): create new directory structure
-
-- Add base/ with shell, cli-tools, secrets
-- Add coding/ with editor, lsp, git, agents
-- Add profiles/ with gaming, media
-- Add desktop/ with wm, apps, theme
-- Add server/ minimal config
-- Reference m3ta-nixpkgs modules where appropriate"
-```
-
----
-
-## Phase 2: Create Profile System with Constraints
-
-### Task 2: Implement Profile Loader with Mutual Exclusion
-
-**Files:**
-
-- Create: `home/lib/default.nix` (Profile loading utilities)
-- Modify: `flake.nix` (Host-spezifische Home-Config)
-- Modify: `hosts/common/users/home.nix`
-
-- [ ] **Step 1: Create home/lib/default.nix**
-
-```nix
-# home/lib/default.nix
-# Profile loading utilities
-
-{ lib }:
-
-{
- # Generiert Home-Manager Konfiguration basierend auf Profilen
- mkHomeConfig = {
- profiles ? [],
- context ? null, # "desktop" | "server" | null
- }: let
- inherit (lib) optionalAttrs mkIf;
-
- # Profile die immer geladen werden
- baseModules = [ ./base ];
-
- # Profile die optional geladen werden
- profileModules = optionalAttrs (builtins.elem "coding" profiles) [ ./coding ];
-
- # Context-spezifische Module
- contextModules = {
- desktop = [ ./desktop ];
- server = [ ./server ];
- };
-
- # Profile-spezifische Module
- profileSpecific = {
- gaming = [ ./profiles/gaming ];
- media = [ ./profiles/media ];
- };
-
- in {
- imports = baseModules ++ profileModules
- ++ (contextModules.${context} or [])
- ++ (builtins.map (p: ./profiles.${p})
- (builtins.filter (p: builtins.hasAttr p profileSpecific) profiles));
- };
-
- # Assertion: desktop und server schließen sich aus
- mutualExclusiveContexts = builtins.hasAttr "desktop" && builtins.hasAttr "server";
-}
-```
-
-- [ ] **Step 2: Update flake.nix for m3-ares (Desktop)**
-
-```nix
-# hosts/m3-ares/ (Desktop Beispiel)
-{ inputs, lib, pkgs, ... }:
-
-{
- # Home-Manager für m3tam3re auf m3-ares
- home-manager.users.m3tam3re = { config, ... }: {
- # NEU: Profile-System
- m3ta.profiles = [ "coding" "gaming" "media" ]; # Freie Kombination
- m3ta.context = "desktop"; # Schließt "server" aus
-
- # Alternativ: Legacy-Kompatibilität
- # imports = [ ./home ];
- };
-}
-```
-
-- [ ] **Step 3: Update flake.nix for m3-atlas (Server)**
-
-```nix
-# hosts/m3-atlas/ (Server Beispiel)
-{ inputs, lib, pkgs, ... }:
-
-{
- home-manager.users.m3tam3re = { config, ... }: {
- m3ta.profiles = [ "coding" ]; # Nur Coding auf Server
- m3ta.context = "server"; # Schließt "desktop" aus
- };
-}
-```
-
-- [ ] **Step 4: Add assertions in flake.nix**
-
-```nix
-# Validation: Context constraints
-assertion = hostConfig.m3ta.context != "desktop" || hostConfig.m3ta.context != "server"
- || (hostConfig.m3ta.context == null); # Mutually exclusive
-```
-
-- [ ] **Step 5: Commit Phase 2**
-
-```bash
-git add flake.nix hosts/
-git commit -m "feat: implement profile system with constraints
-
-- Add home/lib for profile loading utilities
-- Add m3ta.profiles option (list of profiles)
-- Add m3ta.context option (desktop|server|null)
-- Add mutual exclusion assertion
-- Update m3-ares and m3-atlas as examples"
-```
-
----
-
-## Phase 3: Migrate Existing Configuration
-
-### Task 3: Migrate home/features to new Structure
-
-**Files:**
-
-- Modify: Multiple files in `home/features/` (move content, update paths)
-
-- [ ] **Step 1: Map existing features to new structure**
-
-| Old Location | New Location | Notes |
-|--------------|--------------|-------|
-| `home/features/cli/nushell.nix` | `home/base/shell/nushell.nix` | ✓ Done in Task 1 |
-| `home/features/cli/starship.nix` | `home/base/shell/starship.nix` | ✓ Done in Task 1 |
-| `home/features/cli/fzf.nix` | `home/base/cli-tools/fzf.nix` | ✓ Done in Task 1 |
-| `home/features/cli/zellij.nix` | `home/base/cli-tools/zellij.nix` | ✓ Done in Task 1 |
-| `home/features/cli/nitch.nix` | `home/base/cli-tools/nitch.nix` | ✓ Done in Task 1 |
-| `home/features/cli/television.nix` | `home/base/cli-tools/television.nix` | ✓ Done in Task 1 |
-| `home/features/cli/secrets.nix` | `home/base/secrets/secrets.nix` | ✓ Done in Task 1 |
-| `home/features/coding/opencode.nix` | Reference via `m3ta-nixpkgs` | Update import |
-| `home/features/coding/pi.nix` | Reference via `m3ta-nixpkgs` | Update import |
-| `home/features/desktop/hyprland.nix` | `home/desktop/wm/hyprland.nix` | ✓ Done in Task 1 |
-| `home/features/desktop/wayland.nix` | `home/desktop/wm/wayland.nix` | ✓ Done in Task 1 |
-| `home/features/desktop/rofi.nix` | `home/desktop/wm/rofi.nix` | ✓ Done in Task 1 |
-| `home/features/desktop/obsidian.nix` | `home/desktop/apps/obsidian.nix` | ✓ Done in Task 1 |
-| `home/features/desktop/office.nix` | `home/desktop/apps/office.nix` | ✓ Done in Task 1 |
-| `home/features/desktop/webapps.nix` | `home/desktop/apps/webapps.nix` | ✓ Done in Task 1 |
-| `home/features/desktop/crypto.nix` | `home/desktop/apps/crypto.nix` | ✓ Done in Task 1 |
-| `home/features/desktop/fonts.nix` | `home/desktop/theme/fonts.nix` | ✓ Done in Task 1 |
-| `home/features/desktop/theme.nix` | `home/desktop/theme/theme.nix` | ✓ Done in Task 1 |
-| `home/features/desktop/wallpapers.nix` | `home/desktop/theme/wallpapers.nix` | ✓ Done in Task 1 |
-| `home/features/desktop/media.nix` | `home/profiles/media/*.nix` | Split into modules |
-| `home/features/desktop/gaming.nix` | `home/profiles/gaming/*.nix` | Split into modules |
-
-- [ ] **Step 2: Archive old structure**
-
-```bash
-# After migration, archive old features/
-git mv home/features home/features.old
-```
-
-- [ ] **Step 3: Verify all configurations are imported**
-
-```bash
-# Check that all features are accessible in new structure
-nix flake check
-home-manager dry-activate
-```
-
-- [ ] **Step 4: Commit Phase 3**
-
-```bash
-git add -A
-git commit -m "chore: migrate features to profile structure
-
-- Move all cli features to base/shell and base/cli-tools
-- Move desktop features to desktop/* subdirectories
-- Split media into individual profile modules
-- Split gaming into individual profile modules
-- Archive old features/ directory"
-```
-
----
-
-## Phase 4: Test and Validate
-
-### Task 4: Test Profile Combinations
-
-**Files:**
-
-- Test: Manual testing on m3-ares (Desktop)
-- Test: Manual testing on m3-atlas (Server)
-
-- [ ] **Step 1: Test m3-ares (Desktop with all profiles)**
-
-```bash
-# Build and test on m3-ares
-nixos-rebuild dry-build --flake .#m3-ares
-home-manager dry-activate --flake .#m3tam3re@m3-ares
-```
-
-Expected: Loads base + coding + desktop + gaming + media
-
-- [ ] **Step 2: Test m3-atlas (Server with coding only)**
-
-```bash
-# Build and test on m3-atlas
-nixos-rebuild dry-build --flake .#m3-atlas
-home-manager dry-activate --flake .#m3tam3re@m3-atlas
-```
-
-Expected: Loads base + coding + server (no desktop modules)
-
-- [ ] **Step 3: Test assertion (should fail)**
-
-```nix
-# This SHOULD fail - desktop and server together
-m3ta.context = "desktop";
-m3ta.profiles = [ "coding" ];
-# Nix should throw assertion error
-```
-
-- [ ] **Step 4: Commit Phase 4**
-
-```bash
-git commit -m "test: validate profile combinations on all hosts
-
-- m3-ares: base + coding + desktop + gaming + media ✓
-- m3-atlas: base + coding + server ✓
-- Constraint assertion working ✓"
-```
-
----
-
-## Phase 5: Cleanup
-
-### Task 5: Remove Old Structure
-
-**Files:**
-
-- Delete: `home/features.old/` (after verification)
-
-- [ ] **Step 1: Verify no broken imports**
-
-```bash
-# Search for any references to old paths
-grep -r "home/features" --include="*.nix"
-```
-
-Expected: No results
-
-- [ ] **Step 2: Delete old directory**
-
-```bash
-git rm -rf home/features.old
-```
-
-- [ ] **Step 3: Final format and check**
-
-```bash
-nix fmt
-nix flake check
-```
-
-- [ ] **Step 4: Final commit**
-
-```bash
-git commit -m "chore: remove old features directory
-
-Cleanup complete. New structure:
-- home/base/ (always loaded)
-- home/coding/ (profile-independent)
-- home/profiles/ (gaming, media)
-- home/desktop/ (context=desktop)
-- home/server/ (context=server)"
-```
-
----
-
-## Summary
-
-| Phase | Tasks | Description |
-|-------|-------|-------------|
-| 1 | 1 | Create new directory structure |
-| 2 | 2 | Implement profile system with constraints |
-| 3 | 3 | Migrate existing features |
-| 4 | 4 | Test profile combinations |
-| 5 | 5 | Remove old structure |
-
-**Total:** 5 tasks, ~22 steps
-
-**Expected Duration:** 2-4 hours (depending on migration complexity)
-
----
-
-## Migration Notes
-
-1. **NeoVim Config**: Already in nixpkgs, reference via `inputs.m3ta-nixpkgs.packages.neovim-config`
-
-2. **Agent-System**: Already in nixpkgs, reference via `inputs.m3ta-nixpkgs.homeModules.coding.agents`
-
-3. **Zed Remote**: Desktop-only feature, works via SSH. No server-side installation needed.
-
-4. **Fish Shell**: Removed from base (Nushell is primary). Can be added as optional profile if needed.
-
-5. **Feature Flags**: Old `features.*.enable` options → New profile lists `m3ta.profiles = [ "gaming" "media" ]`
diff --git a/docs/plans/2026-04-27-missing-packages.md b/docs/plans/2026-04-27-missing-packages.md
deleted file mode 100644
index 303aff9..0000000
--- a/docs/plans/2026-04-27-missing-packages.md
+++ /dev/null
@@ -1,259 +0,0 @@
-# Missing Packages Implementation Plan
-
-> **Goal:** Restore missing packages from old configuration to new profile-based structure
-
-**Context:** The home profile restructuring (Task 1-5) moved files but left many packages unaccounted for. This plan categorizes and assigns each package to the appropriate location.
-
----
-
-## Package Categorization
-
-### Base Layer (`home/base/`) — Always Available
-
-These are CLI tools that work on any system (server or desktop):
-
-| Package | Source | Module | Option |
-|---------|--------|--------|--------|
-| `jq` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `ripgrep` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `fd` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `coreutils` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `htop` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `httpie` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `just` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `lazygit` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `lf` | old cli | `home/base/cli-tools/default.nix` | `home/packages` |
-| `tldr` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `trash-cli` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `unzip` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `zip` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `yazi` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `gcc` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `go` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `sqlite` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `sqlite-vec` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `nix-index` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `nix-update` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `progress` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `devenv` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `libnotify` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `basecamp` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `comma` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `fabric-ai` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `llm` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-| `hyprpaper-random` | old cli | `home/base/cli-tools/default.nix` | `home.packages` |
-
-**Note:** `hyprpaper-random` is in base despite being Hyprland-specific. Alternative: move to `desktop/wm/` if it causes issues on non-Hyprland systems.
-
-### Base Programs (CLI Integration)
-
-These are programs with shell integration, placed in `home/base/cli-tools/`:
-
-| Program | Source | Module | Option |
-|---------|--------|--------|--------|
-| `carapace` | old cli | `home/base/cli-tools/default.nix` | `programs.carapace` |
-| `zoxide` | old cli | `home/base/cli-tools/default.nix` | `programs.zoxide` |
-| `bat` | old cli | `home/base/cli-tools/default.nix` | `programs.bat` |
-| `direnv` | old cli | `home/base/cli-tools/default.nix` | `programs.direnv` |
-| `eza` | old cli | `home/base/cli-tools/default.nix` | `programs.eza` |
-| `lf` | old cli | `home/base/cli-tools/default.nix` | `programs.lf` |
-| `zellij-ps` | old cli | `home/base/cli-tools/default.nix` | `cli.zellij-ps` |
-
-### Coding Layer (`home/coding/`) — Developer Tools
-
-| Package | Source | Module | Option |
-|---------|--------|--------|--------|
-| `bruno` | old desktop/coding | `home/coding/packages.nix` | `home.packages` |
-| `insomnia` | old desktop/coding | `home/coding/packages.nix` | `home.packages` |
-| `vim` | - | `home/coding/packages.nix` | `home.packages` |
-
-**New module:** `home/coding/packages.nix` (or inline into `coding/default.nix`)
-
-### Desktop Layer (`home/desktop/`) — Desktop-Specific
-
-| Package | Source | Module | Option |
-|---------|--------|--------|--------|
-| `vibetyper` | old desktop | `home/desktop/apps/default.nix` | `home.packages` |
-| `pomodoro-timer` | old cli | `home/desktop/apps/default.nix` | `home.packages` |
-| `launch-timer` | - | `home/desktop/apps/default.nix` | `home.packages` |
-
-**Note:** `launch-timer` needs investigation - is it a custom script or nixpkgs package?
-
-### Gaming Profile (`home/profiles/gaming/`) — Gaming Only
-
-| Package | Source | Module | Option |
-|---------|--------|--------|--------|
-| `rocmPackages.rocm-smi` | old cli | `home/profiles/gaming/default.nix` | `home.packages` |
-| `rocmPackages.rocminfo` | old cli | `home/profiles/gaming/default.nix` | `home.packages` |
-| `rocmPackages.rocm-runtime` | old cli | `home/profiles/gaming/default.nix` | `home.packages` |
-| `vulkan-tools` | old cli | `home/profiles/gaming/default.nix` | `home.packages` |
-
-**Rationale:** ROCm is for AMD GPUs used in gaming (e.g., ROG Ally, gaming laptops with AMD dGPUs). This keeps server configs clean.
-
-### Media Profile (`home/profiles/media/`) — Media Creation
-
-| Package | Source | Module | Option |
-|---------|--------|--------|--------|
-| `plexamp` | old desktop/media | `home/profiles/media/default.nix` | `home.packages` |
-| `webcord` | old desktop/media | `home/profiles/media/default.nix` | `home.packages` |
-| `unimatrix` | old cli | `home/profiles/media/default.nix` | `home.packages` |
-| `mpv` (config) | old desktop/media | `home/profiles/media/default.nix` | `programs.mpv` |
-
-**Note:** `unimatrix` is a terminal screensaver - fits well with media profile.
-
----
-
-## NOT Needed (Explicitly Removed)
-
-These packages should NOT be added:
-
-| Package | Reason |
-|---------|--------|
-| `wireguard-tools` | No longer needed |
-| `wttrbar` | No longer needed |
-| `nushellPlugins.skim` | No longer needed |
-
----
-
-## Tasks
-
-### Task 1: Update `home/base/cli-tools/default.nix`
-
-Add missing packages to the CLI tools aggregator:
-
-```nix
-home.packages = with pkgs; [
- # Core utilities
- jq ripgrep fd coreutils htop
- # Dev tools
- just lazylib lf tldr devenv
- gcc go sqlite sqlite-vec
- nix-index nix-update progress
- # AI tools
- comma fabric-ai llm
- # Misc
- libnotify basecamp hyprpaper-random
- trash-cli unzip zip yazi
-];
-```
-
-Also add programs: carapace, zoxide, bat, direnv, eza, lf, zellij-ps
-
-### Task 2: Create `home/coding/packages.nix`
-
-New module for coding-specific packages:
-
-```nix
-{ lib, pkgs, ... }:
-
-{
- options.coding.packages = {
- enable = mkEnableOption "additional coding packages";
- };
-
- config = mkIf config.coding.packages.enable {
- home.packages = with pkgs; [
- bruno
- insomnia
- ];
- };
-}
-```
-
-### Task 3: Update `home/profiles/gaming/default.nix`
-
-Add GPU monitoring tools:
-
-```nix
-home.packages = with pkgs; [
- # Gaming utilities
- gamescope gamemode goverlay mangohud protonplus
- # AMD GPU monitoring (ROCm)
- rocmPackages.rocm-smi
- rocmPackages.rocminfo
- rocmPackages.rocm-runtime
- vulkan-tools
-];
-```
-
-### Task 4: Update `home/profiles/media/default.nix`
-
-Add missing media packages:
-
-```nix
-home.packages = with pkgs; [
- # Already present: ffmpeg_6-full, gimp, handbrake, etc.
- # Add missing:
- plexamp
- webcord
- unimatrix
-];
-
-programs.mpv = {
- enable = true;
- bindings = {
- WHEEL_UP = "seek 10";
- WHEEL_DOWN = "seek -10";
- };
- config = {
- profile = "gpu-hq";
- ytdl-format = "bestvideo+bestaudio";
- };
-};
-```
-
-### Task 5: Update Desktop Apps
-
-Add desktop-specific packages to `home/desktop/apps/default.nix`:
-
-```nix
-home.packages = with pkgs; [
- # Already present
- # Add missing:
- pomodoro-timer
- # launch-timer - needs investigation
-];
-```
-
-### Task 6: Update Host Configs
-
-Ensure all desktop hosts import the new modules:
-
-- `home/m3tam3re/m3-ares.nix` - Should have `coding.packages.enable = true`
-- `home/m3tam3re/m3-kratos.nix` - Should have `coding.packages.enable = true`
-
----
-
-## Implementation Order
-
-1. **Task 1** - Base CLI tools (largest impact, affects all hosts)
-2. **Task 2** - Coding packages (small, new module)
-3. **Task 3** - Gaming profile (ROCm)
-4. **Task 4** - Media profile (plexamp, webcord, unimatrix, mpv)
-5. **Task 5** - Desktop apps (vibetyper already present, add pomodoro-timer)
-6. **Task 6** - Host config updates (if needed)
-
----
-
-## Verification
-
-```bash
-nix flake check
-# Should pass with no new errors
-```
-
----
-
-## Summary
-
-| Layer | New Files | Modified Files |
-|-------|-----------|----------------|
-| base/cli-tools | - | `default.nix` |
-| coding | `packages.nix` | `default.nix` |
-| profiles/gaming | - | `default.nix` |
-| profiles/media | - | `default.nix` |
-| desktop/apps | - | `default.nix` |
-
-**Total packages to restore:** ~30
-**Programs to restore:** 7
-**Packages excluded:** 3 (wireguard, wttrbar, nushellPlugins.skim)
diff --git a/home/coding/agents/agents.nix b/home/coding/agents/agents.nix
index e710d06..755e25b 100644
--- a/home/coding/agents/agents.nix
+++ b/home/coding/agents/agents.nix
@@ -63,7 +63,8 @@
home.packages = with pkgs; [
agenix-cli
agent-browser
- pyrefly
+ beads
+ pi
(qmd.override {
vulkanSupport = videoDrivers == ["amdgpu"];
cudaSupport = videoDrivers == ["nvidia"];
diff --git a/home/coding/agents/pi.nix b/home/coding/agents/pi.nix
index 2f431ea..dfd4605 100644
--- a/home/coding/agents/pi.nix
+++ b/home/coding/agents/pi.nix
@@ -32,17 +32,19 @@
settings = {
packages = [
- "npm:@thesethrose/pi-zai-provider"
- "npm:pi-mcp-adapter"
- "npm:pi-subagents"
- "npm:pi-lens"
- "npm:pi-web-access"
- "npm:pi-prompt-template-model"
+ "npm:@dreadedzombie/pi-init"
"npm:@plannotator/pi-extension"
- "npm:pi-powerline-footer"
- "npm:pi-markdown-preview"
- "npm:pi-tool-display"
+ "npm:@thesethrose/pi-zai-provider"
"npm:pi-agent-browser-native"
+ "npm:pi-beads-extension"
+ "npm:pi-lens"
+ "npm:pi-markdown-preview"
+ "npm:pi-mcp-adapter"
+ "npm:pi-powerline-footer"
+ "npm:pi-prompt-template-model"
+ "npm:pi-subagents"
+ "npm:pi-tool-display"
+ "npm:pi-web-access"
"git:github.com/hk-vk/pi-connect"
];
diff --git a/home/coding/languages/python.nix b/home/coding/languages/python.nix
index 11bb67f..50758cf 100644
--- a/home/coding/languages/python.nix
+++ b/home/coding/languages/python.nix
@@ -19,12 +19,15 @@ in {
};
config = mkIf cfg.enable {
- home.packages = [
+ home.packages = with pkgs; [
(pkgs.python3.withPackages (ps:
- with ps; [
- pip
- uv
- ] ++ cfg.extraPackages))
+ with ps;
+ [
+ pip
+ uv
+ ]
+ ++ cfg.extraPackages))
+ pyrefly
];
};
}