From 4621ea4674eb6a9290bdb64bbc776ea2aecc4703 Mon Sep 17 00:00:00 2001 From: ilia Date: Sun, 7 Sep 2025 22:17:22 -0400 Subject: [PATCH] Add monitoring and backup roles, enhancing infrastructure management capabilities. Introduce Proxmox VM creation playbook for automated VM provisioning. Update Makefile with new commands for monitoring and backup tasks. Enhance README.md with detailed usage instructions for new features, including automated backups and system monitoring tools. Refactor existing roles for improved organization and clarity, ensuring compatibility across various systems. --- .ansible-lint | 26 ++ .ansible/.lock | 0 Makefile | 41 +- README.md | 453 ++++++++++++--------- collections/requirements.yml | 2 + dev-playbook.yml | 2 + group_vars/all.yml | 2 +- host_vars/{devVM.yml => dev01.yml} | 0 local-playbook.yml | 2 + proxmox-create-vm.yml | 78 ++++ roles/applications/meta/main.yml | 1 - roles/backup/defaults/main.yml | 10 + roles/backup/tasks/main.yml | 50 +++ roles/backup/templates/backup-home.sh.j2 | 31 ++ roles/backup/templates/backup-system.sh.j2 | 43 ++ roles/base/handlers/main.yml | 5 - roles/base/meta/main.yml | 1 - roles/base/tasks/main.yml | 13 +- roles/development/meta/main.yml | 52 --- roles/docker/meta/main.yml | 52 --- roles/maintenance/defaults/main.yml | 18 +- roles/maintenance/meta/main.yml | 52 --- roles/maintenance/tasks/main.yml | 156 ++++++- roles/monitoring/defaults/main.yml | 5 + roles/monitoring/handlers/main.yml | 11 + roles/monitoring/tasks/main.yml | 97 +++++ roles/monitoring/templates/jail.local.j2 | 33 ++ roles/proxmox_vm/defaults/main.yml | 27 ++ roles/proxmox_vm/tasks/main.yml | 77 ++++ roles/shell/files/.zshrc | 63 +++ roles/shell/meta/main.yml | 52 --- roles/shell/tasks/main.yml | 14 + roles/snap/meta/main.yml | 12 - roles/ssh/meta/main.yml | 52 --- roles/tailscale/defaults/main.yml | 2 +- roles/tailscale/handlers/main.yml | 6 +- roles/tailscale/tasks/alpine.yml | 10 +- roles/tailscale/tasks/debian.yml | 11 +- roles/tailscale/tasks/main.yml | 25 +- roles/user/meta/main.yml | 52 --- tailscale-playbook.yml | 7 +- 41 files changed, 1069 insertions(+), 577 deletions(-) create mode 100644 .ansible-lint delete mode 100644 .ansible/.lock rename host_vars/{devVM.yml => dev01.yml} (100%) create mode 100644 proxmox-create-vm.yml delete mode 100644 roles/applications/meta/main.yml create mode 100644 roles/backup/defaults/main.yml create mode 100644 roles/backup/tasks/main.yml create mode 100644 roles/backup/templates/backup-home.sh.j2 create mode 100644 roles/backup/templates/backup-system.sh.j2 delete mode 100644 roles/base/meta/main.yml delete mode 100644 roles/development/meta/main.yml delete mode 100644 roles/docker/meta/main.yml delete mode 100644 roles/maintenance/meta/main.yml create mode 100644 roles/monitoring/defaults/main.yml create mode 100644 roles/monitoring/handlers/main.yml create mode 100644 roles/monitoring/tasks/main.yml create mode 100644 roles/monitoring/templates/jail.local.j2 create mode 100644 roles/proxmox_vm/defaults/main.yml create mode 100644 roles/proxmox_vm/tasks/main.yml delete mode 100644 roles/shell/meta/main.yml delete mode 100644 roles/snap/meta/main.yml delete mode 100644 roles/ssh/meta/main.yml delete mode 100644 roles/user/meta/main.yml diff --git a/.ansible-lint b/.ansible-lint new file mode 100644 index 0000000..9a7f606 --- /dev/null +++ b/.ansible-lint @@ -0,0 +1,26 @@ +# Ansible Lint Configuration +--- +# Exclude patterns +exclude_paths: + - .cache/ + - .github/ + - .ansible/ + +# Skip specific rules +skip_list: + - yaml[line-length] # Allow longer lines in some cases + - name[casing] # Allow mixed case in task names + - args[module] # Skip args rule that causes "file name too long" issues + - var-naming[no-role-prefix] # Allow shorter variable names for readability + - risky-shell-pipe # Allow shell pipes in maintenance scripts + +# Warn instead of error for these +warn_list: + - experimental # Allow experimental features + - jinja[spacing] # Allow flexible jinja spacing + +# Don't try to decrypt vault files during linting +offline: true + +# Verbosity level (0-2) +verbosity: 1 diff --git a/.ansible/.lock b/.ansible/.lock deleted file mode 100644 index e69de29..0000000 diff --git a/Makefile b/Makefile index c3fe69e..3b95b8e 100644 --- a/Makefile +++ b/Makefile @@ -1,4 +1,4 @@ -.PHONY: help bootstrap lint test check apply dev local clean status tailscale tailscale-check tailscale-dev tailscale-status create-vault +.PHONY: help bootstrap lint test check apply dev local clean status tailscale tailscale-check tailscale-dev tailscale-status create-vault create-vm monitoring backup .DEFAULT_GOAL := help ## Colors for output @@ -26,10 +26,12 @@ help: ## Show this help message @echo " make apply # Run on all dev hosts" @echo " make dev HOST=dev01 # Run on specific host" @echo " make local # Run local playbook" - @echo " make maintenance # Run maintenance on all hosts" - @echo " make maintenance GROUP=dev # Run maintenance on dev group" - @echo " make maintenance HOST=dev01 # Run maintenance on specific host" - @echo " make maintenance CHECK=true # Dry-run maintenance on all hosts" + @echo " make maintenance # Run maintenance on all hosts" + @echo " make maintenance GROUP=dev # Run maintenance on dev group" + @echo " make maintenance HOST=dev01 # Run maintenance on specific host" + @echo " make maintenance CHECK=true # Dry-run maintenance on all hosts" + @echo " make maintenance VERBOSE=true # Run with verbose output" + @echo " make maintenance-verbose GROUP=dev # Verbose maintenance on dev group" @echo "" bootstrap: ## Install required collections and dependencies @@ -110,7 +112,7 @@ security: ## Run only security-related roles ansible-playbook dev-playbook.yml --tags security # Unified maintenance target with intelligent parameter detection -maintenance: ## Run maintenance (usage: make maintenance [GROUP=dev] [HOST=dev01] [SERIAL=1] [CHECK=true]) +maintenance: ## Run maintenance (usage: make maintenance [GROUP=dev] [HOST=dev01] [SERIAL=1] [CHECK=true] [VERBOSE=true]) @$(MAKE) _maintenance-run _maintenance-run: @@ -150,6 +152,11 @@ _maintenance-run: echo "$(YELLOW)Running maintenance on $$DESCRIPTION...$(RESET)"; \ fi; \ \ + if [ "$(VERBOSE)" = "true" ]; then \ + ANSIBLE_CMD="$$ANSIBLE_CMD -v"; \ + echo "$(BLUE)Running with verbose output...$(RESET)"; \ + fi; \ + \ if [ -n "$(GROUP)" ] && [ "$(GROUP)" != "dev" ] && [ "$(GROUP)" != "local" ]; then \ echo "$(BLUE)Available groups: dev, gitea, portainer, homepage, ansible, local$(RESET)"; \ fi; \ @@ -166,6 +173,9 @@ maintenance-all: ## Run maintenance on all hosts (legacy alias) maintenance-check: ## Dry-run maintenance (legacy alias, usage: make maintenance-check [GROUP=dev]) @$(MAKE) maintenance CHECK=true GROUP=$(GROUP) +maintenance-verbose: ## Run maintenance with verbose output (usage: make maintenance-verbose [GROUP=dev]) + @$(MAKE) maintenance VERBOSE=true GROUP=$(GROUP) + docker: ## Install/configure Docker only @echo "$(YELLOW)Running Docker setup...$(RESET)" ansible-playbook dev-playbook.yml --tags docker @@ -304,8 +314,6 @@ ifndef HOST endif ansible-vault edit host_vars/$(HOST).yml - - test-connectivity: ## Test network connectivity and SSH access to all hosts @echo "$(BOLD)Connectivity Test$(RESET)" @if [ -n "$(CURRENT_HOST)" ]; then \ @@ -364,4 +372,19 @@ endif create-vault: ## Create encrypted vault file for secrets (passwords, auth keys, etc.) @echo "$(YELLOW)Creating vault file for storing secrets...$(RESET)" ansible-vault create group_vars/all/vault.yml - @echo "$(GREEN)✓ Vault file created. Add your secrets here (e.g. vault_tailscale_auth_key)$(RESET)" \ No newline at end of file + @echo "$(GREEN)✓ Vault file created. Add your secrets here (e.g. vault_tailscale_auth_key)$(RESET)" + +create-vm: ## Create Ansible controller VM on Proxmox + @echo "$(YELLOW)Creating Ansible controller VM on Proxmox...$(RESET)" + ansible-playbook proxmox-create-vm.yml --ask-vault-pass + @echo "$(GREEN)✓ VM creation complete$(RESET)" + +monitoring: ## Install monitoring tools on all machines + @echo "$(YELLOW)Installing monitoring tools...$(RESET)" + ansible-playbook -i hosts dev-playbook.yml --tags monitoring + @echo "$(GREEN)✓ Monitoring installation complete$(RESET)" + +backup: ## Set up automated backups on all machines + @echo "$(YELLOW)Setting up automated backups...$(RESET)" + ansible-playbook -i hosts dev-playbook.yml --tags backup + @echo "$(GREEN)✓ Backup setup complete$(RESET)" \ No newline at end of file diff --git a/README.md b/README.md index 79f680d..2e6835f 100644 --- a/README.md +++ b/README.md @@ -1,31 +1,42 @@ -# Ansible Development Environment Setup +# Ansible Infrastructure Management -This Ansible playbook automates the setup of development environments across multiple machines. +This Ansible project provides comprehensive infrastructure automation for development environments, server management, and VM provisioning across multiple machines and platforms. ## 🏗️ Architecture ### Host Groups - `dev`: Development machines (dev01, bottom, debianDesktopVM) -- `gitea`: Gitea server -- `portainer`: Portainer container management -- `homepage`: Homepage dashboard +- `gitea`: Gitea server (Alpine Linux) +- `portainer`: Portainer container management (Alpine Linux) +- `homepage`: Homepage dashboard (Debian) - `ansible`: Ansible control node +- `local`: Local machine management ### Roles -#### Core Roles -- **`maintenance`**: System updates, package cleanup, and reboots +#### Core Infrastructure Roles +- **`maintenance`**: System updates, package cleanup, and automated reboots - **`base`**: Core system packages, security tools, and system hardening +- **`ssh`**: SSH server hardening and firewall configuration +- **`user`**: User management and configuration + +#### Development & Shell Roles - **`development`**: Development tools (git, nodejs, build-essential, python3) - **`shell`**: Shell configuration (zsh + oh-my-zsh + powerlevel10k) - **`docker`**: Docker CE installation and user configuration -- **`ssh`**: SSH server and firewall configuration -- **`user`**: User management #### Application Roles - **`applications`**: Desktop applications (Brave, LibreOffice, Redshift, Evince) - **`snap`**: Snap daemon and snap applications (VSCode, Cursor) +#### Network & Monitoring Roles +- **`tailscale`**: VPN mesh networking across all machines +- **`monitoring`**: System monitoring tools and scripts +- **`backup`**: Automated backup solutions (✨ NEW) + +#### Infrastructure Roles +- **`proxmox_vm`**: Proxmox VM creation and management (✨ NEW) + ## 🚀 Usage ### Quick Start with Makefile (Recommended) @@ -36,7 +47,7 @@ make bootstrap # Test everything make test -# Dry run to see what would change +# Dry run to see what would change make check # Apply to all development hosts @@ -49,6 +60,53 @@ make dev HOST=dev01 make local ``` +### New Infrastructure Features + +#### Proxmox VM Creation (✨ NEW) +```bash +# Create new VMs on Proxmox +make create-vm + +# Or manually: +ansible-playbook proxmox-create-vm.yml +``` + +#### Automated Backups (✨ NEW) +```bash +# Deploy backup system +make backup + +# Includes: +# - Daily home directory backups (2:00 AM) +# - Daily system config backups (2:30 AM) +# - 7-day retention for home, 30-day for system +# - Automated cleanup and logging +``` + +#### System Monitoring (✨ NEW) +```bash +# Deploy monitoring tools +make monitoring + +# Includes: +# - Advanced system monitoring (btop, iotop, nethogs) +# - Custom monitoring scripts +# - System information dashboards +# - Tailscale network status integration +``` + +#### Tailscale VPN Network +```bash +# Deploy Tailscale across all machines +make tailscale + +# Check Tailscale status +make tailscale-status + +# Deploy to development machines only +make tailscale-dev +``` + ### Prerequisites (Manual Setup) ```bash # Install required collections @@ -56,10 +114,9 @@ ansible-galaxy collection install -r collections/requirements.yml ``` ### Vault Password Setup -Host variables are encrypted with Ansible Vault. You have two options: +Host variables and sensitive data are encrypted with Ansible Vault: #### Option 1: Vault Password File (Recommended) -Create a vault password file: ```bash # Create the vault password file echo "your_vault_password" > ~/.ansible-vault-pass @@ -67,49 +124,53 @@ chmod 600 ~/.ansible-vault-pass ``` #### Option 2: Interactive Password Prompt -Use `--ask-vault-pass` with each command to be prompted for the vault password. +Use `--ask-vault-pass` with each command. -### Basic Setup +### Vault Configuration +Create vault files with encrypted secrets: ```bash -# Run on all development machines (with vault password file) -ansible-playbook dev-playbook.yml +# Create/edit vault files +make create-vault +make edit-vault HOST=dev01 -# Run on all development machines (interactive vault password) -ansible-playbook dev-playbook.yml --ask-vault-pass - -# Run on specific host -ansible-playbook dev-playbook.yml --limit dev01 - -# Skip reboots for specific host -ansible-playbook dev-playbook.yml --limit bottom +# Required vault variables: +# - vault_tailscale_auth_key: "tskey-auth-your-key" +# - vault_proxmox_host: "proxmox-server-ip" +# - vault_proxmox_user: "root@pam" +# - vault_proxmox_password: "proxmox-password" +# - vault_vm_cipassword: "vm-user-password" +# - vault_ssh_public_key: "ssh-ed25519 AAAA..." ``` ### Selective Execution with Tags #### Using Makefile (Recommended) ```bash -# Security-related roles only -make security +# Infrastructure roles +make security # Security-related roles only +make monitoring # Monitoring tools only +make backup # Backup system only -# Development tools only -make docker -make shell +# Development tools +make docker # Docker installation only +make shell # Shell configuration only +make apps # Applications only -# Applications only -make apps +# Network services +make tailscale # VPN network setup +make tailscale-status # Check VPN status # Maintenance (unified system) make maintenance # All hosts make maintenance GROUP=dev # Specific group -make maintenance HOST=dev01 # Specific host +make maintenance HOST=dev01 # Specific host make maintenance CHECK=true # Dry-run all hosts make maintenance GROUP=dev SERIAL=1 # Serial execution -# Check connectivity -make status - -# Get detailed help -make help +# Infrastructure management +make create-vm # Create new Proxmox VMs +make status # Check connectivity +make facts # Gather system facts ``` #### Manual Commands @@ -117,49 +178,25 @@ make help # Security-related roles only ansible-playbook dev-playbook.yml --tags security -# Development tools only +# Development tools only ansible-playbook dev-playbook.yml --tags development,docker -# Applications only -ansible-playbook dev-playbook.yml --tags apps +# Network services +ansible-playbook tailscale-playbook.yml + +# Infrastructure provisioning +ansible-playbook proxmox-create-vm.yml # Skip maintenance ansible-playbook dev-playbook.yml --skip-tags maintenance ``` -### Skip Reboots -Add `skip_reboot=true` to host variables: -```ini -[dev] -bottom ansible_host=10.0.10.156 ansible_user=beast skip_reboot=true -``` - -### Debug Output -Control debug information display with the `ansible_debug_output` variable: - -```bash -# Default: No debug output (clean, production-ready output) -ansible-playbook dev-playbook.yml --limit dev01 - -# Enable debug output (shows detailed status information) -ansible-playbook dev-playbook.yml --limit dev01 -e "ansible_debug_output=true" - -# Set permanently in group_vars/all.yml -ansible_debug_output: true -``` - -### Dry Run and Testing -```bash -# Using Makefile -make test # Lint + syntax check -make check # Dry run all hosts -make check-local # Dry run localhost -make quick # Test + check workflow - -# Manual commands -ansible-playbook dev-playbook.yml --check # Check what would change -ansible-playbook dev-playbook.yml -v # Verbose output -``` +### Playbook Overview +- **`dev-playbook.yml`**: Complete development environment setup +- **`local-playbook.yml`**: Local machine configuration +- **`tailscale-playbook.yml`**: VPN network deployment +- **`proxmox-create-vm.yml`**: VM provisioning on Proxmox +- **`maintenance-playbook.yml`**: System maintenance operations ## 🔧 Configuration @@ -168,11 +205,23 @@ ansible-playbook dev-playbook.yml -v # Verbose output - `locale`: System locale (default: en_US.UTF-8) - `ansible_debug_output`: Show debug information (default: false) - `fail2ban_bantime`: Ban duration in seconds -- `fail2ban_findtime`: Time window for failures +- `fail2ban_findtime`: Time window for failures - `fail2ban_maxretry`: Max failures before ban +### Tailscale Configuration +- `tailscale_auth_key`: Authentication key (stored in vault) +- `tailscale_accept_routes`: Accept subnet routes (default: true) +- `tailscale_accept_dns`: Accept DNS settings (default: true) +- `tailscale_ssh`: Enable SSH access through Tailscale (default: true) + +### Backup Configuration (`roles/backup/defaults/main.yml`) +- `backup_enable_cron`: Enable automated backups (default: true) +- `backup_retention_days_home`: Home backup retention (default: 7) +- `backup_retention_days_system`: System backup retention (default: 30) +- `backup_users`: Users to backup (default: ['master', 'beast', 'ladmin', 'user']) + ### SSH Configuration (`roles/ssh/defaults/main.yml`) -The SSH role provides comprehensive security hardening: +Comprehensive security hardening: - `ssh_port`: SSH port (default: 22) - `ssh_permit_root_login`: Root login setting (default: 'no') - `ssh_password_authentication`: Password auth (default: 'no') @@ -180,32 +229,16 @@ The SSH role provides comprehensive security hardening: - `ssh_allowed_users`: Restrict to specific users (default: []) - `ssh_allowed_groups`: Restrict to specific groups (default: ['sudo', 'ssh']) -Override any setting in your host or group variables: -```yaml -# Example: Custom SSH port -ssh_port: 2222 - -# Example: Allow specific users -ssh_allowed_users: ['admin', 'deploy'] -``` - -### Host Variables (`host_vars/`) -- `skip_reboot`: Skip automatic reboots -- Encrypted variables for sensitive data +### Proxmox VM Configuration (`roles/proxmox_vm/defaults/main.yml`) +- `vm_memory`: RAM allocation (default: 8192MB) +- `vm_cores`: CPU cores (default: 2) +- `vm_disk_size`: Disk size (default: 20G) +- `vm_iso`: Ubuntu Server ISO (default: ubuntu-24.04-live-server-amd64.iso) +- `vm_ciuser`: Default user (default: master) ## 🛡️ Security Features -### Fail2ban Configuration -- SSH brute force protection -- Configurable ban times and retry limits -- Email notifications (configured in template) - -### UFW Firewall -- Deny-by-default policy -- SSH access allowed -- Automatic enablement - -### SSH Hardening +### Comprehensive SSH Hardening - Modern cryptographic algorithms (ChaCha20-Poly1305, AES-256-GCM) - Secure key exchange (Curve25519, DH Group 16) - Disabled password authentication @@ -213,10 +246,21 @@ ssh_allowed_users: ['admin', 'deploy'] - User/group access restrictions - Configuration validation and automatic backup -### System Hardening -- Timezone and locale configuration -- Security package installation -- Modern CLI tools and system monitoring +### Fail2ban Integration +- SSH brute force protection +- Configurable ban times and retry limits +- Email notifications + +### UFW Firewall +- Deny-by-default policy +- SSH access allowed +- Automatic enablement + +### Tailscale VPN Security +- Zero-trust mesh networking +- End-to-end encryption +- SSH access through secure tunnel +- Subnet routing capabilities ## 📦 Installed Packages @@ -234,11 +278,24 @@ ssh_allowed_users: ['admin', 'deploy'] - `brave-browser`, `libreoffice`, `evince`, `redshift` - `code` (VSCode), `cursor` (via snap) -### Docker +### Docker & Containers - Docker CE with all components - Docker Compose - User added to docker group +### Backup Tools (✨ NEW) +- `rsync`, `borgbackup`, `rclone`, `restic` +- Automated backup scripts and cron jobs + +### Monitoring Tools (✨ NEW) +- `htop`, `iotop`, `nethogs`, `btop` +- Custom system information scripts +- Network monitoring utilities + +### VPN & Network +- `tailscale` - Mesh VPN networking +- Network utilities and monitoring + ## 🔧 Modern CLI Tools The base role installs modern replacements for traditional Unix tools: @@ -249,7 +306,7 @@ The base role installs modern replacements for traditional Unix tools: rg "pattern" files/ # ripgrep - faster than grep fd "filename" # fd-find - intuitive find replacement -# Data processing +# Data processing jq '.key' file.json # JSON processor and formatter yq '.key' file.yaml # YAML processor and formatter @@ -257,70 +314,76 @@ yq '.key' file.yaml # YAML processor and formatter btop # Modern system monitor (better than htop) tree directory/ # Directory structure visualization -# File operations +# File operations tree -L 2 # Limit tree depth rg -i "case insensitive" # Case-insensitive search fd -e yml # Find only YAML files jq -r '.items[].name' # Raw JSON output ``` -### Integration Examples -```bash -# DevOps workflows -kubectl get pods -o json | jq '.items[].metadata.name' -docker ps --format json | jq '.Names' -rg "ansible.builtin" roles/ --type yaml -fd "main.yml" roles/ -x cat -``` - -## 🔄 Maintenance +## 🔄 Maintenance & Operations ### Unified Maintenance System -The maintenance system provides a single, intelligent command for all maintenance operations: - ```bash # Basic usage make maintenance # Run on all hosts -make maintenance GROUP=dev # Run on specific group +make maintenance GROUP=dev # Run on specific group make maintenance HOST=dev01 # Run on specific host # Advanced options make maintenance CHECK=true # Dry-run (safe testing) make maintenance GROUP=dev SERIAL=1 # One host at a time make maintenance GROUP=local # Local machine (auto-sudo) - -# Legacy support (still works) -make maintenance-all # Same as: make maintenance -make maintenance-check GROUP=dev # Same as: make maintenance GROUP=dev CHECK=true ``` -### Available Host Groups -- `dev`: Development machines (dev01, bottom, debianDesktopVM) -- `gitea`: Gitea server -- `portainer`: Portainer container management -- `homepage`: Homepage dashboard -- `ansible`: Ansible control node -- `local`: Localhost (with automatic sudo handling) - -### Maintenance Features -The maintenance role handles: -- Package updates (`apt upgrade`) -- Unused package removal (`apt autoremove`) -- Cache cleanup (`apt autoclean`) -- Conditional reboots (respects `skip_reboot` setting) -- System information reporting -- Intelligent sudo password handling - -### Direct Ansible Commands +### Backup Operations (✨ NEW) ```bash -# Using the dedicated maintenance playbook -ansible-playbook maintenance-playbook.yml -e "target_group=dev" -ansible-playbook maintenance-playbook.yml --limit "dev01" -ansible-playbook maintenance-playbook.yml --check --diff # Dry-run +# Deploy backup system +make backup -# Using tags with development playbook -ansible-playbook dev-playbook.yml --tags maintenance -ansible-playbook dev-playbook.yml --skip-tags maintenance +# Manual backup operations +sudo /opt/backups/scripts/backup-home.sh # Run home backup +sudo /opt/backups/scripts/backup-system.sh # Run system backup + +# Check backup logs +tail -f /var/log/backups/home.log +tail -f /var/log/backups/system.log +``` + +### Monitoring Operations (✨ NEW) +```bash +# Deploy monitoring tools +make monitoring + +# Use monitoring scripts +/usr/local/bin/monitoring/sysinfo # System information dashboard +/usr/local/bin/monitoring/netinfo # Network information + +# System monitoring +btop # Interactive system monitor +``` + +### Tailscale Network Management +```bash +# Deploy VPN network +make tailscale + +# Check status across all machines +make tailscale-status + +# Manual Tailscale commands +tailscale status # Check connection status +tailscale ip # Show Tailscale IP +tailscale netcheck # Network connectivity check +``` + +### Infrastructure Provisioning (✨ NEW) +```bash +# Create new VMs on Proxmox +make create-vm + +# Custom VM creation +ansible-playbook proxmox-create-vm.yml -e "vm_name=new-server vm_id=111" ``` ## 🐛 Troubleshooting @@ -330,31 +393,32 @@ ansible-playbook dev-playbook.yml --skip-tags maintenance 1. **SSH Connection Issues** - Check `ansible.cfg` SSH settings - Verify host keys and user permissions + - Test Tailscale connectivity: `tailscale ping hostname` -2. **Package Installation Failures** - - Run with `-v` for verbose output - - Check internet connectivity on target hosts +2. **Vault Access Issues** + - Verify vault password file: `~/.ansible-vault-pass` + - Test vault decryption: `ansible-vault view host_vars/hostname.yml` -3. **Reboot Issues** - - Use `skip_reboot=true` for problematic hosts - - Check maintenance role handlers +3. **Tailscale Connection Issues** + - Check service status: `sudo systemctl status tailscaled` + - Verify auth key in vault + - Check firewall: `sudo ufw status` -4. **SSH Configuration Issues** - - Original config backed up to `/etc/ssh/sshd_config.backup` - - Test SSH config: `sudo sshd -t` - - Check SSH service: `sudo systemctl status ssh` - - Verify public key authentication is working before applying +4. **Proxmox VM Creation Issues** + - Verify Proxmox credentials in vault + - Check ISO availability: `pvesm list local --content iso` + - Ensure sufficient resources on Proxmox node -5. **Modern CLI Tools Missing** - - Check if snap is installed: `snap --version` - - For fd command: Symlink created at `/usr/local/bin/fd` - - Alternative: Use `fdfind` directly on Ubuntu systems +5. **Backup Issues** + - Check backup directories: `ls -la /opt/backups/` + - Review logs: `tail -f /var/log/backups/*.log` + - Verify cron jobs: `sudo crontab -l` ### Debug Commands ```bash # Using Makefile make status # Test connectivity to all hosts -make facts # Gather facts from all hosts +make facts # Gather facts from all hosts make debug # Run with debug output make verbose # Run with verbose output @@ -364,16 +428,13 @@ ansible dev -m setup # Check facts ansible-playbook dev-playbook.yml --tags base # Run specific role # Verify installations -ansible dev -m shell -a "jq --version" # Check jq installation -ansible dev -m shell -a "rg --version" # Check ripgrep installation -ansible dev -m shell -a "fd --version" # Check fd installation -ansible dev -m shell -a "sudo sshd -t" # Validate SSH config +ansible dev -m shell -a "tailscale status" # Check Tailscale +ansible dev -m shell -a "docker --version" # Check Docker +ansible dev -m shell -a "sudo sshd -t" # Validate SSH config ``` ## 🛠️ Makefile Workflows -The included `Makefile` provides convenient shortcuts for common operations: - ### Development Workflow ```bash make bootstrap # Install collections @@ -382,10 +443,19 @@ make check # Dry run make apply # Deploy to all hosts ``` +### Infrastructure Management +```bash +make create-vm # Provision new VMs +make tailscale # Deploy VPN network +make monitoring # Deploy monitoring +make backup # Deploy backup system +``` + ### Host-Specific Operations ```bash make dev HOST=dev01 # Deploy to specific host make edit-vault HOST=dev01 # Edit encrypted host variables +make tailscale-dev # Deploy Tailscale to dev hosts only ``` ### Maintenance and Utilities @@ -398,30 +468,35 @@ make install-tools # Install recommended CLI tools locally Run `make help` for the complete list of available commands. ## 📝 File Structure -``` ansible/ -├── ansible.cfg # Enhanced Ansible configuration -├── Makefile # Workflow automation with unified maintenance -├── hosts # Inventory file -├── dev-playbook.yml # Main development playbook -├── local-playbook.yml # Local machine setup +├── ansible.cfg # Enhanced Ansible configuration +├── Makefile # Workflow automation with unified maintenance +├── hosts # Inventory file +├── dev-playbook.yml # Main development playbook +├── local-playbook.yml # Local machine setup +├── tailscale-playbook.yml # VPN network deployment +├── proxmox-create-vm.yml # VM provisioning playbook ├── maintenance-playbook.yml # Dedicated maintenance playbook ├── collections/ -│ └── requirements.yml # Required Ansible collections +│ └── requirements.yml # Required Ansible collections ├── group_vars/ -│ └── all.yml # Global variables -├── host_vars/ # Host-specific variables (encrypted) +│ └── all.yml # Global variables and Tailscale config +├── host_vars/ # Host-specific variables (encrypted) └── roles/ - ├── maintenance/ # System maintenance - ├── base/ # Core system setup - ├── development/ # Development tools - ├── shell/ # Shell configuration (zsh + oh-my-zsh) - ├── docker/ # Docker installation - ├── ssh/ # SSH hardening and configuration - ├── user/ # User management - ├── applications/ # Desktop applications - └── snap/ # Snap applications -``` +├── maintenance/ # System maintenance +├── base/ # Core system setup +├── development/ # Development tools +├── shell/ # Shell configuration (zsh + oh-my-zsh) +├── docker/ # Docker installation +├── ssh/ # SSH hardening and configuration +├── user/ # User management +├── applications/ # Desktop applications +├── snap/ # Snap applications +├── tailscale/ # VPN mesh networking +├── monitoring/ # System monitoring tools +├── backup/ # Automated backup solutions +└── proxmox_vm/ # VM provisioning on Proxmox + ## 🤝 Contributing @@ -429,3 +504,5 @@ ansible/ 2. Update documentation for new roles/tasks 3. Use proper handlers for service restarts 4. Follow existing naming conventions +5. Encrypt sensitive data with ansible-vault +6. Test across different OS distributions (Ubuntu, Debian, Alpine) \ No newline at end of file diff --git a/collections/requirements.yml b/collections/requirements.yml index 2ea3420..eb425bf 100644 --- a/collections/requirements.yml +++ b/collections/requirements.yml @@ -2,5 +2,7 @@ collections: - name: community.general version: ">=6.0.0" + - name: community.proxmox + version: ">=1.0.0" - name: ansible.posix version: ">=1.4.0" diff --git a/dev-playbook.yml b/dev-playbook.yml index 17389cb..53d098c 100644 --- a/dev-playbook.yml +++ b/dev-playbook.yml @@ -13,6 +13,8 @@ - { role: applications, tags: ['applications', 'apps'] } - { role: snap, tags: ['snap', 'apps'] } - { role: tailscale, tags: ['tailscale', 'vpn'] } + - { role: monitoring, tags: ['monitoring'] } + # - { role: backup, tags: ['backup'] } pre_tasks: - name: Update apt cache diff --git a/group_vars/all.yml b/group_vars/all.yml index 3180239..7ba15c1 100644 --- a/group_vars/all.yml +++ b/group_vars/all.yml @@ -29,4 +29,4 @@ tailscale_auth_key: "{{ vault_tailscale_auth_key | default('') }}" tailscale_accept_routes: true tailscale_accept_dns: true tailscale_ssh: true -tailscale_hostname: "{{ inventory_hostname }}" \ No newline at end of file +tailscale_hostname: "{{ inventory_hostname }}" diff --git a/host_vars/devVM.yml b/host_vars/dev01.yml similarity index 100% rename from host_vars/devVM.yml rename to host_vars/dev01.yml diff --git a/local-playbook.yml b/local-playbook.yml index eec0665..782ac9b 100644 --- a/local-playbook.yml +++ b/local-playbook.yml @@ -14,6 +14,8 @@ - { role: applications, tags: ['applications', 'apps'] } - { role: snap, tags: ['snap', 'apps'] } - { role: tailscale, tags: ['tailscale', 'vpn'] } + - { role: monitoring, tags: ['monitoring'] } + # - { role: backup, tags: ['backup'] } pre_tasks: - name: Update apt cache diff --git a/proxmox-create-vm.yml b/proxmox-create-vm.yml new file mode 100644 index 0000000..5669f73 --- /dev/null +++ b/proxmox-create-vm.yml @@ -0,0 +1,78 @@ +--- +- name: Create Ansible Controller VM on Proxmox + hosts: localhost + connection: local + gather_facts: false + + vars: + # Proxmox connection (store credentials in vault) + proxmox_host: "{{ vault_proxmox_host }}" + proxmox_user: "{{ vault_proxmox_user }}" + proxmox_node: "{{ vault_proxmox_node | default('pve') }}" + + # VM specs matching your current setup + vm_name: "ansible-control" + vm_id: 110 + vm_memory: 8192 # 8GB (match current working setup) + vm_cores: 2 # 2 cores + vm_sockets: 1 + vm_disk_size: "32G" # Bigger than current 8G + vm_storage: "local-lvm" + vm_network_bridge: "vmbr0" + + # Ubuntu Server 24.04 LTS + vm_iso: "ubuntu-24.04-live-server-amd64.iso" + vm_iso_storage: "local" + + # User configuration + vm_ciuser: "master" + vm_ssh_keys: + - "{{ vault_ssh_public_key }}" # Your SSH public key + vm_ip_config: "dhcp" # or set static: "10.0.10.110/24,gw=10.0.10.1" + + vm_start_after_create: true + + pre_tasks: + - name: Check if VM already exists + community.general.proxmox_kvm: + api_host: "{{ proxmox_host }}" + api_user: "{{ proxmox_user }}" + api_password: "{{ vault_proxmox_password }}" + vmid: "{{ vm_id }}" + state: current + register: vm_check + failed_when: false + + - name: Display VM status + ansible.builtin.debug: + msg: | + VM {{ vm_name }} ({{ vm_id }}): {{ 'Already exists' if vm_check.status is defined else 'Will be created' }} + + roles: + - { role: proxmox_vm, when: vm_check.status is not defined } + + post_tasks: + - name: Wait for VM to be accessible via SSH + ansible.builtin.wait_for: + host: "{{ vm_ip_config.split('/')[0] if '/' in vm_ip_config else 'ansible-control.local' }}" + port: 22 + timeout: 300 + when: + - vm_check.status is not defined + - vm_start_after_create | bool + - vm_ip_config != "dhcp" + + - name: Display next steps + ansible.builtin.debug: + msg: | + 🎉 Ansible Controller VM Created Successfully! + + Next steps: + 1. The VM should be starting up now + 2. Wait a few minutes for Ubuntu installation to complete + 3. SSH to the VM: ssh {{ vm_ciuser }}@[VM-IP] + 4. Run the local-playbook.yml to set it up as an Ansible controller + + To find the VM IP (if using DHCP): + - Check Proxmox web interface + - Or run: qm guest cmd {{ vm_id }} network-get-interfaces diff --git a/roles/applications/meta/main.yml b/roles/applications/meta/main.yml deleted file mode 100644 index 32cf5dd..0000000 --- a/roles/applications/meta/main.yml +++ /dev/null @@ -1 +0,0 @@ -dependencies: [] diff --git a/roles/backup/defaults/main.yml b/roles/backup/defaults/main.yml new file mode 100644 index 0000000..cceafce --- /dev/null +++ b/roles/backup/defaults/main.yml @@ -0,0 +1,10 @@ +--- +# Backup role defaults +backup_enable_cron: true +backup_retention_days_home: 7 +backup_retention_days_system: 30 +backup_users: + - master + - beast + - ladmin + - user diff --git a/roles/backup/tasks/main.yml b/roles/backup/tasks/main.yml new file mode 100644 index 0000000..800434b --- /dev/null +++ b/roles/backup/tasks/main.yml @@ -0,0 +1,50 @@ +--- +- name: Install backup tools + ansible.builtin.apt: + name: + - rsync + - borgbackup + - rclone + - restic + state: present + +- name: Create backup directories + ansible.builtin.file: + path: "{{ item }}" + state: directory + mode: '0755' + loop: + - /opt/backups + - /opt/backups/scripts + - /var/log/backups + +- name: Deploy backup script for home directories + ansible.builtin.template: + src: backup-home.sh.j2 + dest: /opt/backups/scripts/backup-home.sh + mode: '0755' + +- name: Deploy backup script for system configs + ansible.builtin.template: + src: backup-system.sh.j2 + dest: /opt/backups/scripts/backup-system.sh + mode: '0755' + +- name: Create backup cron jobs + ansible.builtin.cron: + name: "{{ item.name }}" + job: "{{ item.job }}" + minute: "{{ item.minute }}" + hour: "{{ item.hour }}" + day: "{{ item.day | default('*') }}" + user: root + loop: + - name: "Daily home backup" + job: "/opt/backups/scripts/backup-home.sh >> /var/log/backups/home.log 2>&1" + minute: "0" + hour: "2" + - name: "Daily system config backup" + job: "/opt/backups/scripts/backup-system.sh >> /var/log/backups/system.log 2>&1" + minute: "30" + hour: "2" + when: backup_enable_cron | default(true) | bool diff --git a/roles/backup/templates/backup-home.sh.j2 b/roles/backup/templates/backup-home.sh.j2 new file mode 100644 index 0000000..0b4e1b5 --- /dev/null +++ b/roles/backup/templates/backup-home.sh.j2 @@ -0,0 +1,31 @@ +#!/bin/bash +# Home directory backup script +# Generated by Ansible + +DATE=$(date +%Y%m%d_%H%M%S) +BACKUP_DIR="/opt/backups/home" +LOG_FILE="/var/log/backups/home.log" + +echo "$(date): Starting home backup" >> "$LOG_FILE" + +# Create backup directory +mkdir -p "$BACKUP_DIR" + +# Backup each user's home directory +{% for user in backup_users | default(['master', 'beast', 'ladmin', 'user']) %} +if [ -d "/home/{{ user }}" ]; then + echo "$(date): Backing up /home/{{ user }}" >> "$LOG_FILE" + rsync -av --delete \ + --exclude='.cache' \ + --exclude='.local/share/Trash' \ + --exclude='snap' \ + --exclude='.docker' \ + /home/{{ user }}/ \ + "$BACKUP_DIR/{{ user }}_$DATE/" >> "$LOG_FILE" 2>&1 +fi +{% endfor %} + +# Keep only last 7 days of backups +find "$BACKUP_DIR" -type d -name "*_20*" -mtime +7 -exec rm -rf {} \; 2>/dev/null + +echo "$(date): Home backup completed" >> "$LOG_FILE" \ No newline at end of file diff --git a/roles/backup/templates/backup-system.sh.j2 b/roles/backup/templates/backup-system.sh.j2 new file mode 100644 index 0000000..d21d888 --- /dev/null +++ b/roles/backup/templates/backup-system.sh.j2 @@ -0,0 +1,43 @@ +#!/bin/bash +# System configuration backup script +# Generated by Ansible + +DATE=$(date +%Y%m%d_%H%M%S) +BACKUP_DIR="/opt/backups/system" +LOG_FILE="/var/log/backups/system.log" + +echo "$(date): Starting system backup" >> "$LOG_FILE" + +# Create backup directory +mkdir -p "$BACKUP_DIR/$DATE" + +# Backup important system directories +for dir in /etc /var/lib/dpkg /var/lib/apt/extended_states; do + if [ -d "$dir" ]; then + echo "$(date): Backing up $dir" >> "$LOG_FILE" + rsync -av "$dir" "$BACKUP_DIR/$DATE/" >> "$LOG_FILE" 2>&1 + fi +done + +# Backup crontabs +if [ -d /var/spool/cron/crontabs ]; then + cp -r /var/spool/cron/crontabs "$BACKUP_DIR/$DATE/" +fi + +# Create system info snapshot +{ + echo "=== System Info ===" + uname -a + lsb_release -a 2>/dev/null + echo "" + echo "=== Installed Packages ===" + dpkg --get-selections + echo "" + echo "=== Services ===" + systemctl list-unit-files --type=service --state=enabled +} > "$BACKUP_DIR/$DATE/system-info.txt" + +# Keep only last 30 days of system backups +find "$BACKUP_DIR" -type d -name "20*" -mtime +30 -exec rm -rf {} \; 2>/dev/null + +echo "$(date): System backup completed" >> "$LOG_FILE" \ No newline at end of file diff --git a/roles/base/handlers/main.yml b/roles/base/handlers/main.yml index c0a890a..881b00e 100644 --- a/roles/base/handlers/main.yml +++ b/roles/base/handlers/main.yml @@ -1,11 +1,6 @@ --- # handlers file for base -- name: Restart fail2ban - ansible.builtin.systemd: - name: fail2ban - state: restarted - - name: Reload ufw ansible.builtin.command: ufw reload changed_when: false diff --git a/roles/base/meta/main.yml b/roles/base/meta/main.yml deleted file mode 100644 index 32cf5dd..0000000 --- a/roles/base/meta/main.yml +++ /dev/null @@ -1 +0,0 @@ -dependencies: [] diff --git a/roles/base/tasks/main.yml b/roles/base/tasks/main.yml index f1d548d..f44c36e 100644 --- a/roles/base/tasks/main.yml +++ b/roles/base/tasks/main.yml @@ -11,12 +11,7 @@ # Network and admin tools - net-tools - ufw - - fail2ban - mailutils - # Monitoring tools - - iotop - - nethogs - - logwatch # Modern CLI tools - jq - ripgrep @@ -27,7 +22,6 @@ community.general.snap: name: - yq - - btop state: present - name: Create fd symlink (Ubuntu uses fd-find) @@ -37,12 +31,7 @@ state: link when: ansible_distribution == "Ubuntu" -- name: Configure fail2ban - ansible.builtin.template: - src: jail.local.j2 - dest: /etc/fail2ban/jail.local - mode: '0644' - notify: restart fail2ban +# fail2ban configuration moved to monitoring role # UFW enablement moved to ssh role to avoid lockout diff --git a/roles/development/meta/main.yml b/roles/development/meta/main.yml deleted file mode 100644 index 1755f40..0000000 --- a/roles/development/meta/main.yml +++ /dev/null @@ -1,52 +0,0 @@ -galaxy_info: - author: ansible-user - description: Development tools and environment setup role - company: Personal - - # If the issue tracker for your role is not on github, uncomment the - # next line and provide a value - # issue_tracker_url: http://example.com/issue/tracker - - # Choose a valid license ID from https://spdx.org - some suggested licenses: - # - BSD-3-Clause (default) - # - MIT - # - GPL-2.0-or-later - # - GPL-3.0-only - # - Apache-2.0 - # - CC-BY-4.0 - license: MIT - - min_ansible_version: "2.9" - - # If this a Container Enabled role, provide the minimum Ansible Container version. - # min_ansible_container_version: - - # - # Provide a list of supported platforms, and for each platform a list of versions. - # If you don't wish to enumerate all versions for a particular platform, use 'all'. - # To view available platforms and versions (or releases), visit: - # https://galaxy.ansible.com/api/v1/platforms/ - # - # platforms: - # - name: Fedora - # versions: - # - all - # - 25 - # - name: SomePlatform - # versions: - # - all - # - 1.0 - # - 7 - # - 99.99 - - galaxy_tags: [] - # List tags for your role here, one per line. A tag is a keyword that describes - # and categorizes the role. Users find roles by searching for tags. Be sure to - # remove the '[]' above, if you add tags to this list. - # - # NOTE: A tag is limited to a single word comprised of alphanumeric characters. - # Maximum 20 tags per role. - -dependencies: [] - # List your role dependencies here, one per line. Be sure to remove the '[]' above, - # if you add dependencies to this list. diff --git a/roles/docker/meta/main.yml b/roles/docker/meta/main.yml deleted file mode 100644 index 96ef253..0000000 --- a/roles/docker/meta/main.yml +++ /dev/null @@ -1,52 +0,0 @@ -galaxy_info: - author: ansible-user - description: Docker installation and configuration role - company: Personal - - # If the issue tracker for your role is not on github, uncomment the - # next line and provide a value - # issue_tracker_url: http://example.com/issue/tracker - - # Choose a valid license ID from https://spdx.org - some suggested licenses: - # - BSD-3-Clause (default) - # - MIT - # - GPL-2.0-or-later - # - GPL-3.0-only - # - Apache-2.0 - # - CC-BY-4.0 - license: MIT - - min_ansible_version: "2.9" - - # If this a Container Enabled role, provide the minimum Ansible Container version. - # min_ansible_container_version: - - # - # Provide a list of supported platforms, and for each platform a list of versions. - # If you don't wish to enumerate all versions for a particular platform, use 'all'. - # To view available platforms and versions (or releases), visit: - # https://galaxy.ansible.com/api/v1/platforms/ - # - # platforms: - # - name: Fedora - # versions: - # - all - # - 25 - # - name: SomePlatform - # versions: - # - all - # - 1.0 - # - 7 - # - 99.99 - - galaxy_tags: [] - # List tags for your role here, one per line. A tag is a keyword that describes - # and categorizes the role. Users find roles by searching for tags. Be sure to - # remove the '[]' above, if you add tags to this list. - # - # NOTE: A tag is limited to a single word comprised of alphanumeric characters. - # Maximum 20 tags per role. - -dependencies: [] - # List your role dependencies here, one per line. Be sure to remove the '[]' above, - # if you add dependencies to this list. diff --git a/roles/maintenance/defaults/main.yml b/roles/maintenance/defaults/main.yml index 4c75e41..7eb56f4 100644 --- a/roles/maintenance/defaults/main.yml +++ b/roles/maintenance/defaults/main.yml @@ -3,13 +3,29 @@ # Package management settings maintenance_update_cache: true # Update apt cache before operations -maintenance_upgrade_packages: true # Perform dist-upgrade +maintenance_upgrade_packages: true # Perform package upgrades +maintenance_upgrade_type: "safe" # safe, full, or dist (safe is more reliable) maintenance_autoremove: true # Remove unused packages maintenance_autoclean: true # Clean apt cache +maintenance_fix_broken: true # Fix broken packages before upgrade + +# Network resilience settings +maintenance_apt_retries: 3 # Number of retries for apt operations +maintenance_apt_retry_delay: 30 # Delay between retries (seconds) +maintenance_cache_retry_delay: 10 # Delay between cache update retries +maintenance_individual_upgrade_fallback: true # Try individual upgrades if bulk fails + +# Timeout settings +maintenance_bulk_upgrade_timeout: 1800 # 30 minutes for bulk upgrade +maintenance_individual_timeout: 600 # 10 minutes per individual package +maintenance_bulk_poll_interval: 30 # Check bulk progress every 30s +maintenance_individual_poll_interval: 15 # Check individual progress every 15s # Reboot handling settings maintenance_check_reboot: true # Check if reboot is required maintenance_allow_reboot: true # Allow automatic reboots +maintenance_reboot_timeout: 300 # Reboot timeout in seconds +maintenance_pre_reboot_delay: 5 # Delay before reboot in seconds # Cache settings maintenance_cache_valid_time: 3600 # Cache valid time in seconds (1 hour) diff --git a/roles/maintenance/meta/main.yml b/roles/maintenance/meta/main.yml deleted file mode 100644 index cff34e4..0000000 --- a/roles/maintenance/meta/main.yml +++ /dev/null @@ -1,52 +0,0 @@ -galaxy_info: - author: ansible-user - description: System maintenance and updates role - company: Personal - - # If the issue tracker for your role is not on github, uncomment the - # next line and provide a value - # issue_tracker_url: http://example.com/issue/tracker - - # Choose a valid license ID from https://spdx.org - some suggested licenses: - # - BSD-3-Clause (default) - # - MIT - # - GPL-2.0-or-later - # - GPL-3.0-only - # - Apache-2.0 - # - CC-BY-4.0 - license: MIT - - min_ansible_version: "2.9" - - # If this a Container Enabled role, provide the minimum Ansible Container version. - # min_ansible_container_version: - - # - # Provide a list of supported platforms, and for each platform a list of versions. - # If you don't wish to enumerate all versions for a particular platform, use 'all'. - # To view available platforms and versions (or releases), visit: - # https://galaxy.ansible.com/api/v1/platforms/ - # - # platforms: - # - name: Fedora - # versions: - # - all - # - 25 - # - name: SomePlatform - # versions: - # - all - # - 1.0 - # - 7 - # - 99.99 - - galaxy_tags: [] - # List tags for your role here, one per line. A tag is a keyword that describes - # and categorizes the role. Users find roles by searching for tags. Be sure to - # remove the '[]' above, if you add tags to this list. - # - # NOTE: A tag is limited to a single word comprised of alphanumeric characters. - # Maximum 20 tags per role. - -dependencies: [] - # List your role dependencies here, one per line. Be sure to remove the '[]' above, - # if you add dependencies to this list. diff --git a/roles/maintenance/tasks/main.yml b/roles/maintenance/tasks/main.yml index 4066136..b72e246 100644 --- a/roles/maintenance/tasks/main.yml +++ b/roles/maintenance/tasks/main.yml @@ -1,27 +1,169 @@ --- -- name: Upgrade all packages +- name: Get list of upgradable packages (for reporting) + ansible.builtin.shell: | + apt list --upgradable 2>/dev/null | grep -v "WARNING" | tail -n +2 | wc -l + args: + executable: /bin/bash + register: maintenance_upgradable_count + changed_when: false + +- name: Display packages to be upgraded + ansible.builtin.debug: + msg: | + 📦 Package Upgrade Summary: + - Total packages to upgrade: {{ maintenance_upgradable_count.stdout | default('0') }} + - Upgrade type: {{ maintenance_upgrade_type }} + - Max retries: {{ maintenance_apt_retries }} + - Retry delay: {{ maintenance_apt_retry_delay }}s + when: ansible_debug_output | default(false) | bool + +- name: Show upgradable packages (first 10) + ansible.builtin.shell: | + apt list --upgradable 2>/dev/null | grep -v "WARNING" | head -10 + args: + executable: /bin/bash + register: maintenance_upgradable_packages_preview + changed_when: false + when: maintenance_upgradable_count.stdout | int > 0 + +- name: Display upgradable packages + ansible.builtin.debug: + msg: | + 📋 Packages to upgrade: + {{ maintenance_upgradable_packages_preview.stdout_lines | join('\n') }} + when: + - maintenance_upgradable_count.stdout | int > 0 + - ansible_debug_output | default(false) | bool + - maintenance_upgradable_packages_preview.stdout_lines is defined + +- name: Update apt cache with retries ansible.builtin.apt: - upgrade: dist + update_cache: "{{ maintenance_update_cache }}" + cache_valid_time: "{{ maintenance_cache_valid_time }}" + retries: "{{ maintenance_apt_retries }}" + delay: "{{ maintenance_cache_retry_delay }}" + register: maintenance_apt_update_result + until: maintenance_apt_update_result is succeeded + when: maintenance_update_cache | bool + +- name: Fix broken packages if any + ansible.builtin.command: + cmd: apt-get --fix-broken install -y # noqa command-instead-of-module + become: true + changed_when: false + failed_when: false + when: maintenance_fix_broken | bool + +- name: Upgrade packages with retries and verbose output + ansible.builtin.apt: + upgrade: "{{ maintenance_upgrade_type }}" + force_apt_get: true + update_cache: false # Already updated above + environment: + DEBIAN_FRONTEND: noninteractive + APT_LISTCHANGES_FRONTEND: none + retries: "{{ maintenance_apt_retries }}" + delay: "{{ maintenance_apt_retry_delay }}" + register: maintenance_apt_upgrade_result + until: maintenance_apt_upgrade_result is succeeded + ignore_errors: true + async: "{{ maintenance_bulk_upgrade_timeout }}" + poll: "{{ maintenance_bulk_poll_interval }}" + no_log: "{{ not (ansible_debug_output | default(false) | bool) }}" + when: maintenance_upgrade_packages | bool + +- name: Fallback to individual package upgrades if full upgrade failed + when: + - maintenance_apt_upgrade_result is failed + - maintenance_individual_upgrade_fallback | bool + block: + - name: Display fallback message + ansible.builtin.debug: + msg: | + ⚠️ Bulk upgrade failed, trying individual package upgrades... + This may take longer but is more reliable for problematic packages. + + - name: Get list of upgradable packages for individual upgrade + ansible.builtin.shell: | + apt list --upgradable 2>/dev/null | grep -v "WARNING" | tail -n +2 | cut -d'/' -f1 + args: + executable: /bin/bash + register: maintenance_upgradable_packages_fallback + changed_when: false + + - name: Display packages for individual upgrade + ansible.builtin.debug: + msg: | + 🔄 Attempting individual upgrade for {{ maintenance_upgradable_packages_fallback.stdout_lines | length }} packages: + {{ maintenance_upgradable_packages_fallback.stdout_lines | join(', ') }} + when: maintenance_upgradable_packages_fallback.stdout_lines | length > 0 + + - name: Upgrade packages individually with progress + ansible.builtin.apt: + name: "{{ item }}" + state: latest # noqa package-latest - This is intentional for maintenance upgrades + force_apt_get: true + environment: + DEBIAN_FRONTEND: noninteractive + APT_LISTCHANGES_FRONTEND: none + loop: "{{ maintenance_upgradable_packages_fallback.stdout_lines | default([]) }}" + loop_control: + label: "📦 Upgrading {{ item }} ({{ ansible_loop.index }}/{{ ansible_loop.length }})" + retries: 2 + delay: 10 + ignore_errors: true + async: "{{ maintenance_individual_timeout }}" + poll: "{{ maintenance_individual_poll_interval }}" + no_log: "{{ not (ansible_debug_output | default(false) | bool) }}" + register: maintenance_individual_upgrade_results + when: maintenance_upgradable_packages_fallback.stdout_lines | length > 0 + + - name: Summary of individual upgrades + ansible.builtin.debug: + msg: | + 📊 Individual Upgrade Results: + - Total attempted: {{ maintenance_individual_upgrade_results.results | length | default(0) }} + - Successful: {{ maintenance_individual_upgrade_results.results | selectattr('changed', 'equalto', true) | list | length | default(0) }} + - Failed: {{ maintenance_individual_upgrade_results.results | selectattr('failed', 'equalto', true) | list | length | default(0) }} + when: + - maintenance_individual_upgrade_results is defined + - maintenance_individual_upgrade_results.results is defined - name: Autoremove unused packages ansible.builtin.apt: autoremove: true + purge: true + retries: 2 + delay: 5 + when: maintenance_autoremove | bool - name: Clean apt cache ansible.builtin.apt: autoclean: true + when: maintenance_autoclean | bool - name: Check if reboot is required ansible.builtin.stat: path: /var/run/reboot-required register: maintenance_reboot_required + when: maintenance_check_reboot | bool + +- name: Display maintenance summary + ansible.builtin.debug: + msg: | + Maintenance Summary: + - Cache update: {{ 'Completed' if maintenance_apt_update_result is succeeded else 'Skipped/Failed' }} + - Package upgrade: {{ 'Completed' if maintenance_apt_upgrade_result is succeeded else 'Failed (fallback may have run)' }} + - Reboot required: {{ 'Yes' if (maintenance_reboot_required.stat.exists | default(false)) else 'No' }} + when: ansible_debug_output | default(false) | bool - name: Reboot if required ansible.builtin.reboot: - msg: "Reboot triggered by Ansible after system changes." - reboot_timeout: "{{ maintenance_reboot_timeout | default(300) }}" - pre_reboot_delay: "{{ maintenance_pre_reboot_delay | default(5) }}" + msg: "Reboot triggered by Ansible after system maintenance." + reboot_timeout: "{{ maintenance_reboot_timeout }}" + pre_reboot_delay: "{{ maintenance_pre_reboot_delay }}" when: - - ansible_facts['pkg_mgr'] == "apt" - - maintenance_reboot_required.stat.exists + - maintenance_check_reboot | bool + - maintenance_allow_reboot | bool + - maintenance_reboot_required.stat.exists | default(false) - not (skip_reboot | default(false) | bool) diff --git a/roles/monitoring/defaults/main.yml b/roles/monitoring/defaults/main.yml new file mode 100644 index 0000000..34ad06f --- /dev/null +++ b/roles/monitoring/defaults/main.yml @@ -0,0 +1,5 @@ +--- +# Monitoring role defaults +monitoring_install_snap_tools: true +monitoring_enable_sysstat: true +monitoring_create_scripts: true diff --git a/roles/monitoring/handlers/main.yml b/roles/monitoring/handlers/main.yml new file mode 100644 index 0000000..4fee7fa --- /dev/null +++ b/roles/monitoring/handlers/main.yml @@ -0,0 +1,11 @@ +--- +- name: restart fail2ban + ansible.builtin.systemd: + name: fail2ban + state: restarted + +- name: restart sysstat + ansible.builtin.systemd: + name: sysstat + state: restarted + enabled: true diff --git a/roles/monitoring/tasks/main.yml b/roles/monitoring/tasks/main.yml new file mode 100644 index 0000000..94c09b0 --- /dev/null +++ b/roles/monitoring/tasks/main.yml @@ -0,0 +1,97 @@ +--- +- name: Install monitoring packages + ansible.builtin.apt: + name: + # System monitoring + - htop + - iotop + - nethogs + - iftop + - ncdu + - dstat + # Log monitoring + - logwatch + - fail2ban + # Network monitoring + - nmap + - tcpdump + - wireshark-common + # Performance monitoring + - sysstat + - atop + state: present + +- name: Install modern monitoring tools via snap + community.general.snap: + name: + - btop + - bandwhich + state: present + +- name: Configure fail2ban + ansible.builtin.template: + src: jail.local.j2 + dest: /etc/fail2ban/jail.local + mode: '0644' + notify: restart fail2ban + +- name: Enable sysstat data collection + ansible.builtin.lineinfile: + path: /etc/default/sysstat + regexp: '^ENABLED=' + line: 'ENABLED="true"' + notify: restart sysstat + +- name: Create monitoring scripts directory + ansible.builtin.file: + path: /usr/local/bin/monitoring + state: directory + mode: '0755' + +- name: Deploy system monitoring script + ansible.builtin.copy: + content: | + #!/bin/bash + # System monitoring dashboard + echo "=== System Overview ===" + echo "Hostname: $(hostname)" + echo "Uptime: $(uptime -p)" + echo "Load: $(uptime | awk -F'load average:' '{print $2}')" + echo "" + echo "=== Memory ===" + free -h + echo "" + echo "=== Disk Usage ===" + df -h / /home 2>/dev/null | grep -v tmpfs + echo "" + echo "=== Top Processes ===" + ps aux --sort=-%cpu | head -6 + echo "" + echo "=== Network Connections ===" + ss -tuln | head -10 + echo "" + if command -v tailscale >/dev/null; then + echo "=== Tailscale Status ===" + tailscale status --peers=false 2>/dev/null || echo "Not connected" + fi + dest: /usr/local/bin/monitoring/sysinfo + mode: '0755' + +- name: Deploy network monitoring script + ansible.builtin.copy: + content: | + #!/bin/bash + # Network monitoring script + echo "=== Network Interface Status ===" + ip addr show | grep -E "(inet |state )" | grep -v 127.0.0.1 + echo "" + echo "=== Route Table ===" + ip route show + echo "" + echo "=== DNS Configuration ===" + cat /etc/resolv.conf | grep nameserver + echo "" + echo "=== Open Ports ===" + ss -tuln | grep LISTEN | sort + dest: /usr/local/bin/monitoring/netinfo + mode: '0755' diff --git a/roles/monitoring/templates/jail.local.j2 b/roles/monitoring/templates/jail.local.j2 new file mode 100644 index 0000000..fdf8e1d --- /dev/null +++ b/roles/monitoring/templates/jail.local.j2 @@ -0,0 +1,33 @@ +[DEFAULT] +# Ban hosts for 1 hour +bantime = 3600 +# Check for repeated failures for 10 minutes +findtime = 600 +# Allow 3 failures before banning +maxretry = 3 + +# Email notifications (uncomment and configure if needed) +destemail = idobkin@gmail.com +sender = idobkin@gmail.com +action = %(action_mwl)s + +[sshd] +enabled = true +port = ssh +filter = sshd +logpath = /var/log/auth.log +maxretry = 3 + +[apache] +enabled = false +port = http,https +filter = apache-auth +logpath = /var/log/apache2/error.log +maxretry = 3 + +[nginx-http-auth] +enabled = false +port = http,https +filter = nginx-http-auth +logpath = /var/log/nginx/error.log +maxretry = 3 diff --git a/roles/proxmox_vm/defaults/main.yml b/roles/proxmox_vm/defaults/main.yml new file mode 100644 index 0000000..bfd53d7 --- /dev/null +++ b/roles/proxmox_vm/defaults/main.yml @@ -0,0 +1,27 @@ +--- +# Proxmox VM defaults based on your current setup +vm_name: "ansible-control" +vm_id: 110 +vm_memory: 8192 # 8GB (match current successful setup) +vm_cores: 2 # 2 cores (perfect for Ansible) +vm_sockets: 1 +vm_disk_size: 20G # Increase from current 6.1GB +vm_storage: "local-lvm" +vm_network_bridge: "vmbr0" +vm_os_type: "l26" # Linux 2.6+ kernel + +# Ubuntu Server ISO +vm_iso: "ubuntu-24.04-live-server-amd64.iso" +vm_iso_storage: "local" + +# Cloud-init settings +vm_ciuser: "master" +vm_cipassword: "" # Set in vault: vault_vm_cipassword +vm_ssh_keys: [] # Add SSH public keys +vm_ip_config: "dhcp" # or "192.168.1.100/24,gw=192.168.1.1" +vm_nameservers: "8.8.8.8 8.8.4.4" + +# VM behavior +vm_start_after_create: true +vm_enable_agent: true +vm_boot_order: "order=scsi0" diff --git a/roles/proxmox_vm/tasks/main.yml b/roles/proxmox_vm/tasks/main.yml new file mode 100644 index 0000000..8eb13d7 --- /dev/null +++ b/roles/proxmox_vm/tasks/main.yml @@ -0,0 +1,77 @@ +--- +# Break down the Proxmox VM creation to avoid "file name too long" error +- name: Set VM configuration facts + ansible.builtin.set_fact: + vm_scsi_config: + scsi0: "{{ vm_storage }}:{{ vm_disk_size }},format=raw" + vm_net_config: + net0: "virtio,bridge={{ vm_network_bridge }},firewall=1" + vm_ide_config: + ide2: "{{ vm_iso_storage }}:cloudinit,format=qcow2" + vm_ipconfig: + ipconfig0: "{{ vm_ip_config }}" + +- name: Create VM on Proxmox + community.general.proxmox_kvm: + # Connection + api_host: "{{ proxmox_host }}" + api_user: "{{ proxmox_user }}" + api_password: "{{ vault_proxmox_password }}" + api_token_id: "{{ proxmox_token_id | default(omit) }}" + api_token_secret: "{{ vault_proxmox_token | default(omit) }}" + + # VM identification + vmid: "{{ vm_id }}" + name: "{{ vm_name }}" + node: "{{ proxmox_node }}" + + # Hardware specs + memory: "{{ vm_memory }}" + cores: "{{ vm_cores }}" + sockets: "{{ vm_sockets }}" + cpu: "host" + + # Storage and network + scsi: "{{ vm_scsi_config }}" + net: "{{ vm_net_config }}" + ide: "{{ vm_ide_config }}" + + # Boot and OS + boot: "{{ vm_boot_order }}" + ostype: "{{ vm_os_type }}" + + # Cloud-init + ciuser: "{{ vm_ciuser }}" + cipassword: "{{ vault_vm_cipassword | default(omit) }}" + sshkeys: "{{ vm_ssh_keys | join('\n') if vm_ssh_keys else omit }}" + ipconfig: "{{ vm_ipconfig }}" + nameserver: "{{ vm_nameservers }}" + + # VM options + agent: "{{ vm_enable_agent | bool }}" + autostart: false + balloon: 0 + state: present + register: vm_creation_result + +- name: Start VM if requested + community.general.proxmox_kvm: + api_host: "{{ proxmox_host }}" + api_user: "{{ proxmox_user }}" + api_password: "{{ vault_proxmox_password }}" + api_token_id: "{{ proxmox_token_id | default(omit) }}" + api_token_secret: "{{ vault_proxmox_token | default(omit) }}" + vmid: "{{ vm_id }}" + node: "{{ proxmox_node }}" + state: started + when: vm_start_after_create | bool + +- name: Display VM creation results + ansible.builtin.debug: + msg: | + VM Created: {{ vm_name }} (ID: {{ vm_id }}) + Memory: {{ vm_memory }}MB + Cores: {{ vm_cores }} + Storage: {{ vm_storage }}:{{ vm_disk_size }} + Network: {{ vm_network_bridge }} + Status: {{ vm_creation_result.msg | default('Created') }} diff --git a/roles/shell/files/.zshrc b/roles/shell/files/.zshrc index 0250ff7..fae36f6 100644 --- a/roles/shell/files/.zshrc +++ b/roles/shell/files/.zshrc @@ -1,3 +1,5 @@ +typeset -g POWERLEVEL9K_INSTANT_PROMPT=quiet + # Enable Powerlevel10k instant prompt. Should stay close to the top of ~/.zshrc. # Initialization code that may require console input (password prompts, [y/n] # confirmations, etc.) must go above this block; everything else may go below. @@ -112,3 +114,64 @@ source $ZSH/oh-my-zsh.sh # To customize prompt, run `p10k configure` or edit ~/.p10k.zsh. [[ ! -f ~/.p10k.zsh ]] || source ~/.p10k.zsh +[ -f ~/.fzf.zsh ] && source ~/.fzf.zsh + +alias reload="source ~/.zshrc && echo 'ZSH config reloaded from ~/.zshrc'" +alias editrc="nano ~/.zshrc" +alias c="clear" +alias ls="ls --color=auto" + +alias ..="cd .." +alias ...="cd ../.." +alias ....="cd ../../.." +alias cd..="cd .." +alias h="cd ~" +alias dc="cd ~/Documents/code" + +# System information +alias df="df -h" # disk usage human readable +alias du="du -h" # directory usage human readable +alias free="free -h" # memory usage human readable + +# Process management +alias ps="ps aux" +alias cpu="lscpu" +alias top="btop" +alias mem="free -m" +alias ports="ss -tulpn" # open ports + +# Network information +alias myip="curl -s http://ipecho.net/plain; echo" +alias localip="ip route get 1.2.3.4 | awk '{print $7}'" + +# Python +alias py="python3" +alias pip="pip3" +alias venv="python3 -m venv" +alias activate="source venv/bin/activate" + +# Docker +alias d="docker" +alias dc="docker-compose" +alias dcu="docker-compose up -d" +alias dcd="docker-compose down" +alias dcb="docker-compose build" +alias dps="docker ps" +alias di="docker images" + +# Date and time +alias now="date +'%Y-%m-%d %H:%M:%S'" +alias today="date +'%Y-%m-%d'" + +# Package management (Debian/Ubuntu) +alias update="sudo apt update && sudo apt upgrade -y" +alias install="sudo apt install" +alias remove="sudo apt remove" +alias search="apt search" + +# Permissions and ownership +alias chmox="chmod +x" +alias own="sudo chown -R $USER:$USER" + +alias nfresh="rm -rf node_modules/ package-lock.json && npm install" + diff --git a/roles/shell/meta/main.yml b/roles/shell/meta/main.yml deleted file mode 100644 index 76f3dba..0000000 --- a/roles/shell/meta/main.yml +++ /dev/null @@ -1,52 +0,0 @@ -galaxy_info: - author: ansible-user - description: Shell configuration and setup role - company: Personal - - # If the issue tracker for your role is not on github, uncomment the - # next line and provide a value - # issue_tracker_url: http://example.com/issue/tracker - - # Choose a valid license ID from https://spdx.org - some suggested licenses: - # - BSD-3-Clause (default) - # - MIT - # - GPL-2.0-or-later - # - GPL-3.0-only - # - Apache-2.0 - # - CC-BY-4.0 - license: MIT - - min_ansible_version: "2.9" - - # If this a Container Enabled role, provide the minimum Ansible Container version. - # min_ansible_container_version: - - # - # Provide a list of supported platforms, and for each platform a list of versions. - # If you don't wish to enumerate all versions for a particular platform, use 'all'. - # To view available platforms and versions (or releases), visit: - # https://galaxy.ansible.com/api/v1/platforms/ - # - # platforms: - # - name: Fedora - # versions: - # - all - # - 25 - # - name: SomePlatform - # versions: - # - all - # - 1.0 - # - 7 - # - 99.99 - - galaxy_tags: [] - # List tags for your role here, one per line. A tag is a keyword that describes - # and categorizes the role. Users find roles by searching for tags. Be sure to - # remove the '[]' above, if you add tags to this list. - # - # NOTE: A tag is limited to a single word comprised of alphanumeric characters. - # Maximum 20 tags per role. - -dependencies: [] - # List your role dependencies here, one per line. Be sure to remove the '[]' above, - # if you add dependencies to this list. diff --git a/roles/shell/tasks/main.yml b/roles/shell/tasks/main.yml index ea47d25..6f221af 100644 --- a/roles/shell/tasks/main.yml +++ b/roles/shell/tasks/main.yml @@ -8,8 +8,22 @@ name: - zsh - tmux + - fzf state: present +- name: Install zsh plugins + ansible.builtin.git: + repo: "{{ item.repo }}" + dest: "/home/{{ shell_target_user }}/.oh-my-zsh/custom/plugins/{{ item.name }}" + version: master + depth: 1 + update: false + become: true + become_user: "{{ shell_target_user }}" + loop: + - { name: "zsh-syntax-highlighting", repo: "https://github.com/zsh-users/zsh-syntax-highlighting.git" } + - { name: "zsh-autosuggestions", repo: "https://github.com/zsh-users/zsh-autosuggestions.git" } + - name: Set zsh as default shell for user ansible.builtin.user: name: "{{ shell_target_user }}" diff --git a/roles/snap/meta/main.yml b/roles/snap/meta/main.yml deleted file mode 100644 index a7ceee0..0000000 --- a/roles/snap/meta/main.yml +++ /dev/null @@ -1,12 +0,0 @@ -galaxy_info: - author: ansible-user - description: Snap package manager configuration role - company: Personal - - license: MIT - - min_ansible_version: "2.9" - - galaxy_tags: [] - -dependencies: [] diff --git a/roles/ssh/meta/main.yml b/roles/ssh/meta/main.yml deleted file mode 100644 index 2f9a0ad..0000000 --- a/roles/ssh/meta/main.yml +++ /dev/null @@ -1,52 +0,0 @@ -galaxy_info: - author: ansible-user - description: SSH configuration and security role - company: Personal - - # If the issue tracker for your role is not on github, uncomment the - # next line and provide a value - # issue_tracker_url: http://example.com/issue/tracker - - # Choose a valid license ID from https://spdx.org - some suggested licenses: - # - BSD-3-Clause (default) - # - MIT - # - GPL-2.0-or-later - # - GPL-3.0-only - # - Apache-2.0 - # - CC-BY-4.0 - license: MIT - - min_ansible_version: "2.9" - - # If this a Container Enabled role, provide the minimum Ansible Container version. - # min_ansible_container_version: - - # - # Provide a list of supported platforms, and for each platform a list of versions. - # If you don't wish to enumerate all versions for a particular platform, use 'all'. - # To view available platforms and versions (or releases), visit: - # https://galaxy.ansible.com/api/v1/platforms/ - # - # platforms: - # - name: Fedora - # versions: - # - all - # - 25 - # - name: SomePlatform - # versions: - # - all - # - 1.0 - # - 7 - # - 99.99 - - galaxy_tags: [] - # List tags for your role here, one per line. A tag is a keyword that describes - # and categorizes the role. Users find roles by searching for tags. Be sure to - # remove the '[]' above, if you add tags to this list. - # - # NOTE: A tag is limited to a single word comprised of alphanumeric characters. - # Maximum 20 tags per role. - -dependencies: [] - # List your role dependencies here, one per line. Be sure to remove the '[]' above, - # if you add dependencies to this list. diff --git a/roles/tailscale/defaults/main.yml b/roles/tailscale/defaults/main.yml index 69eacf4..2657133 100644 --- a/roles/tailscale/defaults/main.yml +++ b/roles/tailscale/defaults/main.yml @@ -17,4 +17,4 @@ tailscale_reset: false # Force reconnection (will logout first) # ENTERPRISE OPTIONS (leave empty for personal use): tailscale_login_server: "" # Custom control server URL -tailscale_operator: "" # Operator user for Tailscale \ No newline at end of file +tailscale_operator: "" # Operator user for Tailscale diff --git a/roles/tailscale/handlers/main.yml b/roles/tailscale/handlers/main.yml index 3ea88df..1dec543 100644 --- a/roles/tailscale/handlers/main.yml +++ b/roles/tailscale/handlers/main.yml @@ -1,13 +1,13 @@ --- -- name: start tailscaled +- name: Start tailscaled ansible.builtin.systemd: name: tailscaled state: started enabled: true become: true -- name: restart tailscaled +- name: Restart tailscaled ansible.builtin.systemd: name: tailscaled state: restarted - become: true \ No newline at end of file + become: true diff --git a/roles/tailscale/tasks/alpine.yml b/roles/tailscale/tasks/alpine.yml index 1e291b0..e40dd24 100644 --- a/roles/tailscale/tasks/alpine.yml +++ b/roles/tailscale/tasks/alpine.yml @@ -1,6 +1,6 @@ --- - name: Install required packages for Alpine - ansible.builtin.apk: + community.general.apk: name: - curl - gnupg @@ -22,20 +22,20 @@ become: true - name: Update apk cache - ansible.builtin.apk: + community.general.apk: update_cache: true become: true - name: Install Tailscale - ansible.builtin.apk: + community.general.apk: name: tailscale state: present become: true - notify: start tailscaled + notify: Start tailscaled - name: Enable and start Tailscale daemon ansible.builtin.service: name: tailscaled enabled: true state: started - become: true \ No newline at end of file + become: true diff --git a/roles/tailscale/tasks/debian.yml b/roles/tailscale/tasks/debian.yml index 1a8ecec..1579f70 100644 --- a/roles/tailscale/tasks/debian.yml +++ b/roles/tailscale/tasks/debian.yml @@ -7,12 +7,15 @@ become: true - name: Determine repository codename - set_fact: + ansible.builtin.set_fact: tailscale_repo_codename: "{{ 'jammy' if ansible_distribution == 'Ubuntu' else 'bookworm' }}" - name: Add Tailscale repository ansible.builtin.apt_repository: - repo: "deb [signed-by=/usr/share/keyrings/tailscale-archive-keyring.gpg] https://pkgs.tailscale.com/stable/{{ 'ubuntu' if ansible_distribution == 'Ubuntu' else 'debian' }} {{ tailscale_repo_codename }} main" + repo: >- + deb [signed-by=/usr/share/keyrings/tailscale-archive-keyring.gpg] + https://pkgs.tailscale.com/stable/{{ 'ubuntu' if ansible_distribution == 'Ubuntu' else 'debian' }} + {{ tailscale_repo_codename }} main state: present filename: tailscale become: true @@ -27,11 +30,11 @@ name: tailscale state: present become: true - notify: start tailscaled + notify: Start tailscaled - name: Enable and start Tailscale daemon ansible.builtin.systemd: name: tailscaled enabled: true state: started - become: true \ No newline at end of file + become: true diff --git a/roles/tailscale/tasks/main.yml b/roles/tailscale/tasks/main.yml index d7ca488..857ae82 100644 --- a/roles/tailscale/tasks/main.yml +++ b/roles/tailscale/tasks/main.yml @@ -1,31 +1,32 @@ --- - name: Include OS-specific installation tasks - include_tasks: "{{ ansible_os_family | lower }}.yml" + ansible.builtin.include_tasks: "{{ ansible_os_family | lower }}.yml" - name: Fail if not running on supported OS - fail: + ansible.builtin.fail: msg: "This role only supports Ubuntu, Debian, and Alpine systems" when: ansible_os_family not in ["Debian", "Alpine"] - name: Check if Tailscale is already connected - command: tailscale status --json + ansible.builtin.command: tailscale status --json register: tailscale_status failed_when: false changed_when: false - name: Parse Tailscale status - set_fact: + ansible.builtin.set_fact: tailscale_connected: "{{ (tailscale_status.stdout | from_json).BackendState == 'Running' if tailscale_status.rc == 0 else false }}" - name: Reset Tailscale if requested - command: tailscale logout - when: + ansible.builtin.command: tailscale logout + when: - tailscale_reset | bool - tailscale_connected | bool - notify: restart tailscaled + notify: Restart tailscaled + changed_when: true - name: Connect to Tailscale network - command: > + ansible.builtin.command: > tailscale up {{ '--auth-key=' + tailscale_auth_key if tailscale_auth_key else '' }} {{ '--hostname=' + tailscale_hostname if tailscale_hostname else '' }} @@ -41,10 +42,10 @@ changed_when: tailscale_up_result.rc == 0 - name: Display Tailscale status - command: tailscale status - register: final_status + ansible.builtin.command: tailscale status + register: tailscale_final_status changed_when: false - name: Show Tailscale connection status - debug: - msg: "{{ final_status.stdout_lines }}" \ No newline at end of file + ansible.builtin.debug: + msg: "{{ tailscale_final_status.stdout_lines }}" diff --git a/roles/user/meta/main.yml b/roles/user/meta/main.yml deleted file mode 100644 index 29d44f1..0000000 --- a/roles/user/meta/main.yml +++ /dev/null @@ -1,52 +0,0 @@ -galaxy_info: - author: ansible-user - description: User account management role - company: Personal - - # If the issue tracker for your role is not on github, uncomment the - # next line and provide a value - # issue_tracker_url: http://example.com/issue/tracker - - # Choose a valid license ID from https://spdx.org - some suggested licenses: - # - BSD-3-Clause (default) - # - MIT - # - GPL-2.0-or-later - # - GPL-3.0-only - # - Apache-2.0 - # - CC-BY-4.0 - license: MIT - - min_ansible_version: "2.9" - - # If this a Container Enabled role, provide the minimum Ansible Container version. - # min_ansible_container_version: - - # - # Provide a list of supported platforms, and for each platform a list of versions. - # If you don't wish to enumerate all versions for a particular platform, use 'all'. - # To view available platforms and versions (or releases), visit: - # https://galaxy.ansible.com/api/v1/platforms/ - # - # platforms: - # - name: Fedora - # versions: - # - all - # - 25 - # - name: SomePlatform - # versions: - # - all - # - 1.0 - # - 7 - # - 99.99 - - galaxy_tags: [] - # List tags for your role here, one per line. A tag is a keyword that describes - # and categorizes the role. Users find roles by searching for tags. Be sure to - # remove the '[]' above, if you add tags to this list. - # - # NOTE: A tag is limited to a single word comprised of alphanumeric characters. - # Maximum 20 tags per role. - -dependencies: [] - # List your role dependencies here, one per line. Be sure to remove the '[]' above, - # if you add dependencies to this list. diff --git a/tailscale-playbook.yml b/tailscale-playbook.yml index a000152..be9d387 100644 --- a/tailscale-playbook.yml +++ b/tailscale-playbook.yml @@ -7,6 +7,7 @@ vars: # Variables are set in group_vars/all.yml # Override here if needed or pass via: --extra-vars "tailscale_auth_key=your_key" + tailscale_auth_key: "{{ vault_tailscale_auth_key | default('') }}" pre_tasks: - name: Update package cache (Debian/Ubuntu) @@ -22,10 +23,10 @@ ansible.builtin.debug: msg: | Tailscale has been installed and configured on {{ inventory_hostname }}. - + To connect this machine to your Tailscale network: 1. If you provided an auth key, the machine should already be connected 2. If no auth key was provided, run: sudo tailscale up 3. Check status with: tailscale status - - Remember to authorize the machine in your Tailscale admin console if needed. \ No newline at end of file + + Remember to authorize the machine in your Tailscale admin console if needed.