---
- name: Service Inventory and Documentation Generator
  hosts: all
  gather_facts: yes
  vars:
    inventory_timestamp: "{{ ansible_date_time.iso8601 }}"
    inventory_dir: "/tmp/service_inventory"
    documentation_dir: "/tmp/service_docs"

  tasks:
    - name: Create inventory directories
      file:
        path: "{{ item }}"
        state: directory
        mode: '0755'
      loop:
        - "{{ inventory_dir }}"
        - "{{ documentation_dir }}"
      delegate_to: localhost
      run_once: true

    - name: Check if Docker is available
      shell: command -v docker >/dev/null 2>&1
      register: docker_available
      changed_when: false
      ignore_errors: yes

    - name: Skip Docker tasks if not available
      set_fact:
        skip_docker: "{{ docker_available.rc != 0 }}"

    - name: Discover running services
      shell: |
        echo "=== SERVICE DISCOVERY ==="

        # System services (systemd)
        if command -v systemctl >/dev/null 2>&1; then
          echo "SYSTEMD_SERVICES:"
          systemctl list-units --type=service --state=active --no-legend | head -20 | while read service rest; do
            port_info=""
            # Try to extract port information from service files
            if systemctl show "$service" --property=ExecStart 2>/dev/null | grep -qE ":[0-9]+"; then
              port_info=$(systemctl show "$service" --property=ExecStart 2>/dev/null | grep -oE ":[0-9]+" | head -1)
            fi
            echo "$service$port_info"
          done
          echo ""
        fi

        # Synology services (if available)
        if command -v synoservice >/dev/null 2>&1; then
          echo "SYNOLOGY_SERVICES:"
          synoservice --list 2>/dev/null | grep -E "^\[.*\].*running" | head -20
          echo ""
        fi

        # Network services (listening ports)
        echo "NETWORK_SERVICES:"
        if command -v netstat >/dev/null 2>&1; then
          netstat -tuln 2>/dev/null | grep LISTEN | head -20
        elif command -v ss >/dev/null 2>&1; then
          ss -tuln 2>/dev/null | grep LISTEN | head -20
        fi
        echo ""
      register: system_services
      changed_when: false

    - name: Discover Docker services
      shell: |
        if ! command -v docker >/dev/null 2>&1; then
          echo "Docker not available"
          exit 0
        fi

        echo "=== DOCKER SERVICE DISCOVERY ==="

        # Get detailed container information
        docker ps --format "table {{.Names}}\t{{.Image}}\t{{.Status}}\t{{.Ports}}" 2>/dev/null | while IFS=$'\t' read name image status ports; do
          if [ "$name" != "NAMES" ]; then
            echo "CONTAINER: $name"
            echo "  Image: $image"
            echo "  Status: $status"
            echo "  Ports: $ports"

            # Try to get more details
            labels=$(docker inspect "$name" --format '{{range $key, $value := .Config.Labels}}{{$key}}={{$value}}{{"\n"}}{{end}}' 2>/dev/null | head -5)
            if [ -n "$labels" ]; then
              echo "  Labels:"
              echo "$labels" | sed 's/^/    /'
            fi

            # Check for health status
            health=$(docker inspect "$name" --format '{{.State.Health.Status}}' 2>/dev/null)
            if [ "$health" != "<no value>" ] && [ -n "$health" ]; then
              echo "  Health: $health"
            fi

            echo ""
          fi
        done
      register: docker_services
      changed_when: false
      when: not skip_docker

    - name: Analyze service configurations
      shell: |
        echo "=== CONFIGURATION ANALYSIS ==="

        # Find common configuration directories
        config_dirs="/etc /opt /home/*/config /volume1/docker"

        echo "Configuration directories found:"
        for dir in $config_dirs; do
          if [ -d "$dir" ]; then
            # Look for common config files
            find "$dir" -maxdepth 3 -name "*.conf" -o -name "*.yaml" -o -name "*.yml" -o -name "*.json" -o -name "*.env" 2>/dev/null | head -10 | while read config_file; do
              if [ -r "$config_file" ]; then
                echo "  $config_file"
              fi
            done
          fi
        done
        echo ""

        # Docker Compose files
        echo "Docker Compose files:"
        find /opt /home -name "docker-compose*.yml" -o -name "compose*.yml" 2>/dev/null | head -10 | while read compose_file; do
          echo "  $compose_file"
          # Extract service names
          services=$(grep -E "^  [a-zA-Z0-9_-]+:" "$compose_file" 2>/dev/null | sed 's/://g' | sed 's/^  //' | head -5)
          if [ -n "$services" ]; then
            echo "    Services: $(echo $services | tr '\n' ' ')"
          fi
        done
      register: config_analysis
      changed_when: false

    - name: Detect web interfaces and APIs
      shell: |
        echo "=== WEB INTERFACE DETECTION ==="

        # Common web interface ports
        web_ports="80 443 8080 8443 3000 5000 8000 9000 9090 3001 8081 8082 8083 8084 8085"

        for port in $web_ports; do
          # Check if port is listening
          if netstat -tuln 2>/dev/null | grep -q ":$port " || ss -tuln 2>/dev/null | grep -q ":$port "; then
            echo "Port $port is active"

            # Try to detect service type
            if curl -s -m 3 -I "http://localhost:$port" 2>/dev/null | head -1 | grep -q "200\|301\|302"; then
              server_header=$(curl -s -m 3 -I "http://localhost:$port" 2>/dev/null | grep -i "server:" | head -1)
              title=$(curl -s -m 3 "http://localhost:$port" 2>/dev/null | grep -i "<title>" | head -1 | sed 's/<[^>]*>//g' | xargs)

              echo "  HTTP Response: OK"
              if [ -n "$server_header" ]; then
                echo "  $server_header"
              fi
              if [ -n "$title" ]; then
                echo "  Title: $title"
              fi

              # Check for common API endpoints
              for endpoint in /api /health /status /metrics /version; do
                if curl -s -m 2 "http://localhost:$port$endpoint" >/dev/null 2>&1; then
                  echo "  API endpoint: http://localhost:$port$endpoint"
                  break
                fi
              done
            fi
            echo ""
          fi
        done
      register: web_interfaces
      changed_when: false
      ignore_errors: yes

    - name: Generate service catalog
      set_fact:
        service_catalog:
          timestamp: "{{ inventory_timestamp }}"
          hostname: "{{ inventory_hostname }}"
          system_info:
            os: "{{ ansible_distribution }} {{ ansible_distribution_version }}"
            kernel: "{{ ansible_kernel }}"
            architecture: "{{ ansible_architecture }}"
          services:
            system: "{{ system_services.stdout }}"
            docker: "{{ docker_services.stdout if not skip_docker else 'Docker not available' }}"
            configurations: "{{ config_analysis.stdout }}"
            web_interfaces: "{{ web_interfaces.stdout }}"

    - name: Display service inventory
      debug:
        msg: |

          ==========================================
          📋 SERVICE INVENTORY - {{ inventory_hostname }}
          ==========================================

          🖥️  SYSTEM INFO:
          - OS: {{ service_catalog.system_info.os }}
          - Kernel: {{ service_catalog.system_info.kernel }}
          - Architecture: {{ service_catalog.system_info.architecture }}

          🔧 SYSTEM SERVICES:
          {{ service_catalog.services.system }}

          🐳 DOCKER SERVICES:
          {{ service_catalog.services.docker }}

          ⚙️  CONFIGURATIONS:
          {{ service_catalog.services.configurations }}

          🌐 WEB INTERFACES:
          {{ service_catalog.services.web_interfaces }}

          ==========================================

    - name: Generate JSON service inventory
      copy:
        content: |
          {
            "timestamp": "{{ service_catalog.timestamp }}",
            "hostname": "{{ service_catalog.hostname }}",
            "system_info": {
              "os": "{{ service_catalog.system_info.os }}",
              "kernel": "{{ service_catalog.system_info.kernel }}",
              "architecture": "{{ service_catalog.system_info.architecture }}"
            },
            "services": {
              "system": {{ service_catalog.services.system | to_json }},
              "docker": {{ service_catalog.services.docker | to_json }},
              "configurations": {{ service_catalog.services.configurations | to_json }},
              "web_interfaces": {{ service_catalog.services.web_interfaces | to_json }}
            }
          }
        dest: "{{ inventory_dir }}/{{ inventory_hostname }}_inventory_{{ ansible_date_time.epoch }}.json"
      delegate_to: localhost

    - name: Generate Markdown documentation
      copy:
        content: |
          # Service Documentation - {{ inventory_hostname }}

          **Generated:** {{ inventory_timestamp }}
          **System:** {{ service_catalog.system_info.os }} ({{ service_catalog.system_info.architecture }})

          ## 🔧 System Services

          ```
          {{ service_catalog.services.system }}
          ```

          ## 🐳 Docker Services

          ```
          {{ service_catalog.services.docker }}
          ```

          ## ⚙️ Configuration Files

          ```
          {{ service_catalog.services.configurations }}
          ```

          ## 🌐 Web Interfaces & APIs

          ```
          {{ service_catalog.services.web_interfaces }}
          ```

          ## 📊 Quick Stats

          - **Hostname:** {{ inventory_hostname }}
          - **OS:** {{ service_catalog.system_info.os }}
          - **Kernel:** {{ service_catalog.system_info.kernel }}
          - **Architecture:** {{ service_catalog.system_info.architecture }}
          - **Docker Available:** {{ 'Yes' if not skip_docker else 'No' }}

          ---

          *Auto-generated by Ansible service_inventory.yml playbook*
        dest: "{{ documentation_dir }}/{{ inventory_hostname }}_services.md"
      delegate_to: localhost

    - name: Generate consolidated inventory (run once)
      shell: |
        cd "{{ inventory_dir }}"

        echo "# Homelab Service Inventory" > consolidated_inventory.md
        echo "" >> consolidated_inventory.md
        echo "**Generated:** {{ inventory_timestamp }}" >> consolidated_inventory.md
        echo "" >> consolidated_inventory.md

        # Process all JSON files
        for json_file in *_inventory_*.json; do
          if [ -f "$json_file" ]; then
            hostname=$(basename "$json_file" | cut -d'_' -f1)
            echo "## 🖥️ $hostname" >> consolidated_inventory.md
            echo "" >> consolidated_inventory.md

            # Extract key information using basic tools
            if command -v jq >/dev/null 2>&1; then
              os=$(jq -r '.system_info.os' "$json_file" 2>/dev/null || echo "Unknown")
              echo "- **OS:** $os" >> consolidated_inventory.md
              echo "- **File:** [$json_file](./$json_file)" >> consolidated_inventory.md
              echo "- **Documentation:** [${hostname}_services.md](../service_docs/${hostname}_services.md)" >> consolidated_inventory.md
            else
              echo "- **File:** [$json_file](./$json_file)" >> consolidated_inventory.md
            fi
            echo "" >> consolidated_inventory.md
          fi
        done

        echo "---" >> consolidated_inventory.md
        echo "*Auto-generated by Ansible service_inventory.yml playbook*" >> consolidated_inventory.md
      delegate_to: localhost
      run_once: true

    - name: Summary message
      debug:
        msg: |

          📋 Service inventory complete for {{ inventory_hostname }}
          📄 JSON Report: {{ inventory_dir }}/{{ inventory_hostname }}_inventory_{{ ansible_date_time.epoch }}.json
          📖 Markdown Doc: {{ documentation_dir }}/{{ inventory_hostname }}_services.md
          📚 Consolidated: {{ inventory_dir }}/consolidated_inventory.md

          💡 Use this playbook regularly to maintain up-to-date service documentation
          💡 JSON files can be consumed by monitoring systems or dashboards
