From home-lab-ops
Pre-deployment validation for Ansible changes targeting the Proxmox home-lab cluster — catches common mistakes before they become fix commits
npx claudepluginhub infiquetra/infiquetra-claude-plugins --plugin home-lab-opsThis skill uses the workspace's default tool permissions.
You are helping validate Ansible changes for the **olympus** Proxmox cluster before they are deployed. The goal is to catch errors that historically required follow-up fix commits.
Guides Next.js Cache Components and Partial Prerendering (PPR) with cacheComponents enabled. Implements 'use cache', cacheLife(), cacheTag(), revalidateTag(), static/dynamic optimization, and cache debugging.
Migrates code, prompts, and API calls from Claude Sonnet 4.0/4.5 or Opus 4.1 to Opus 4.5, updating model strings on Anthropic, AWS, GCP, Azure platforms.
Automates semantic versioning and release workflow for Claude Code plugins: bumps versions in package.json, marketplace.json, plugin.json; verifies builds; creates git tags, GitHub releases, changelogs.
You are helping validate Ansible changes for the olympus Proxmox cluster before they are deployed. The goal is to catch errors that historically required follow-up fix commits.
Always run validation from the ansible/ directory with vault password available:
cd /path/to/home-lab/ansible
Run syntax-only validation (no connection required):
ansible-playbook --syntax-check -i inventory/hosts.yml proxmox_cluster.yml \
--vault-password-file ~/.vault_pass.txt
ansible-playbook --syntax-check -i inventory/hosts.yml service_vms.yml \
--vault-password-file ~/.vault_pass.txt
ansible-playbook --syntax-check -i inventory/hosts.yml openclaw_cluster.yml \
--vault-password-file ~/.vault_pass.txt
For a specific role or tag only:
ansible-playbook --syntax-check -i inventory/hosts.yml proxmox_cluster.yml \
--tags <role_name> --vault-password-file ~/.vault_pass.txt
Run ansible-lint for best-practice violations:
cd ansible && uv run ansible-lint roles/<role_name>/
uv run ansible-lint playbooks/
Key lint rules to pay attention to:
no-changed-when — shell/command tasks without changed_whenrisky-shell-pipe — shell commands piped without pipefailno-free-form — using free-form module args instead of structured YAMLfqcn-builtins — using short names (e.g. copy) instead of FQCN (ansible.builtin.copy)Test against live hosts without making changes:
# Full playbook dry-run with diff output
ansible-playbook --check --diff -i inventory/hosts.yml proxmox_cluster.yml \
--vault-password-file ~/.vault_pass.txt --tags <role>
# Single host dry-run
ansible-playbook --check --diff -i inventory/hosts.yml proxmox_cluster.yml \
--limit r420.infiquetra.com --vault-password-file ~/.vault_pass.txt
Note: Check mode does not work reliably for tasks that use delegate_to, run_once, or pvecm/pveceph CLI commands — these will show as "skipped" in check mode even though they have real effects.
Verify variables are resolved before referencing them:
# Print all variables for a host (catches undefined vars before runtime)
ansible -i inventory/hosts.yml r420.infiquetra.com -m debug \
-a "var=hostvars[inventory_hostname]" --vault-password-file ~/.vault_pass.txt
For template validation, test Jinja2 rendering:
ansible -i inventory/hosts.yml all -m debug \
-a "msg={{ your_variable }}" --vault-password-file ~/.vault_pass.txt
Before finalizing, review the common mistakes catalog (references/common-mistakes.md) and manually verify the change doesn't exhibit any of the known patterns extracted from the fix commit history.
When reviewing Ansible changes, check:
become: true on all tasks that run as root (pvecm, pveceph, ceph, systemctl)delegate_to: "{{ proxmox_master }}" on all cluster-wide operations (pvecm join, ceph init)run_once: true paired with delegate_to when creating global resourcesserial: 1 on node-join and OSD-add plays (prevents race conditions)when: not ansible_check_mode on tasks that can't run in check modechanged_when: false or changed_when: result.rc != 0 on shell/command tasksignore_errors: false — only use ignore_errors: true when genuinely OK to faildefaults/main.yml for every variable used in tasks{{ vault_var }} exist in the encrypted vault file