"""
IP Analysis Module
Enhanced IP analysis with better geolocation, advanced port scanning, and comprehensive analysis
"""

import asyncio
import aiohttp
import socket
import json
import time
import re
import ssl
import subprocess
import platform
from urllib.parse import urlparse
from fake_useragent import UserAgent
from colorama import Fore, Style
import ipaddress
import threading
from concurrent.futures import ThreadPoolExecutor

class IPAnalyzer:
    """IP analysis module"""
    
    def __init__(self):
        self.ua = UserAgent()
        self.session = None
        self.timeout = 15  # Increased timeout
        self.max_retries = 5  # More retries
        
        # Enhanced geolocation APIs
        self.geo_apis = [
            {
                "name": "ip-api",
                "url": "http://ip-api.com/json/{}?fields=status,message,country,countryCode,region,regionName,city,zip,lat,lon,timezone,isp,org,as,query",
                "reliable": True
            },
            {
                "name": "ipinfo",
                "url": "https://ipinfo.io/{}/json",
                "reliable": True
            },
            {
                "name": "ipgeolocation",
                "url": "https://api.ipgeolocation.io/ipgeo?apiKey=free&ip={}",
                "reliable": False
            },
            {
                "name": "abstractapi",
                "url": "https://ipgeolocation.abstractapi.com/v1/?api_key=free&ip_address={}",
                "reliable": False
            }
        ]
        
        # Enhanced port categories for better analysis
        self.port_categories = {
            "web": [80, 443, 8080, 8443, 8000, 8888, 9000, 3000, 5000, 7000],
            "mail": [25, 587, 465, 993, 143, 995, 110, 995],
            "ftp": [21, 22, 990, 2121],
            "database": [3306, 5432, 1433, 1521, 27017, 6379, 28017],
            "remote": [22, 23, 3389, 5900, 5985, 54321],
            "infrastructure": [53, 123, 161, 389, 445, 636, 993, 1701],
            "security": [8081, 8082, 9200, 9999],
            "iot": [1883, 8883, 5683, 5222, 8083],
            "gaming": [25565, 27015, 27016, 27005, 7777, 27020],
            "voip": [5060, 5061, 5062, 3478, 3480],
            "proxy": [3128, 8080, 1080, 8888, 8118]
        }
        
        # Service detection patterns
        self.service_patterns = {
            22: {"name": "SSH", "description": "Secure Shell"},
            23: {"name": "Telnet", "description": "Telnet Protocol"},
            25: {"name": "SMTP", "description": "Simple Mail Transfer"},
            53: {"name": "DNS", "description": "Domain Name System"},
            80: {"name": "HTTP", "description": "Hypertext Transfer"},
            110: {"name": "POP3", "description": "Post Office Protocol"},
            143: {"name": "IMAP", "description": "Internet Message Access"},
            443: {"name": "HTTPS", "description": "HTTP Secure"},
            993: {"name": "IMAPS", "description": "IMAP Secure"},
            995: {"name": "POP3S", "description": "POP3 Secure"},
            3306: {"name": "MySQL", "description": "MySQL Database"},
            5432: {"name": "PostgreSQL", "description": "PostgreSQL Database"},
            6379: {"name": "Redis", "description": "Redis Cache"},
            8080: {"name": "HTTP-Alt", "description": "Alternative HTTP"},
            8443: {"name": "HTTPS-Alt", "description": "Alternative HTTPS"}
        }
        
        # VPN/Proxy detection patterns
        self.vpn_patterns = [
            r'vpn', r'proxy', r'tunnel', r'gateway', r'exit', r'node',
            r'hosting', r'datacenter', r'cloud', r'server', r'vps'
        ]
        
        # Cache for results
        self.geo_cache = {}
        
        # VPN/Proxy indicators for detection
        self.vpn_indicators = [
            'vpn', 'proxy', 'tor', 'exit', 'relay', 'node', 'server', 'hosting',
            'cloud', 'aws', 'azure', 'google', 'digitalocean', 'vultr', 'linode',
            'ovh', 'hetzner', 'rackspace', 'ibm', 'oracle', 'alibaba', 'tencent'
        ]
        
        # Quick scan ports (most common)
        self.quick_scan_ports = [21, 22, 23, 25, 53, 80, 110, 143, 443, 993, 995, 8080, 8443]
        
        # Suspicious port combinations
        self.suspicious_combinations = [
            [22, 80],      # SSH + Web (common for compromised servers)
            [3389, 80],    # RDP + Web (suspicious if not corporate)
            [1433, 3306],  # Multiple databases
            [21, 23, 80],  # FTP + Telnet + Web (old insecure setup)
            [445, 3389],   # SMB + RDP (Windows attack surface)
        ]
    
    def validate_ip(self, ip):
        """Enhanced IP validation with detailed analysis"""
        try:
            ip_obj = ipaddress.ip_address(ip)
            
            # Check IP type
            ip_type = "IPv4" if isinstance(ip_obj, ipaddress.IPv4Address) else "IPv6"
            
            # Check if private
            is_private = ip_obj.is_private
            
            # Check if loopback
            is_loopback = ip_obj.is_loopback
            
            # Check if multicast
            is_multicast = ip_obj.is_multicast
            
            # Check if reserved
            is_reserved = ip_obj.is_reserved
            
            # Check if link-local
            is_link_local = ip_obj.is_link_local
            
            return {
                "valid": True,
                "ip": str(ip_obj),
                "type": ip_type,
                "is_private": is_private,
                "is_loopback": is_loopback,
                "is_multicast": is_multicast,
                "is_reserved": is_reserved,
                "is_link_local": is_link_local,
                "version": ip_obj.version
            }
            
        except ValueError:
            return {
                "valid": False,
                "error": "Invalid IP address format"
            }
    
    async def analyze_ip_enhanced(self, ip, verbose=False):
        """Enhanced IP analysis with comprehensive features"""
        # First validate the IP
        validation = self.validate_ip(ip)
        if not validation["valid"]:
            return {"error": validation["error"], "valid": False}
        
        
        results = {
            "ip_address": ip,
            "timestamp": time.time(),
            "validation": validation,
            "analysis": {}
        }
        
        try:
            # Enhanced geolocation
            if verbose:
                print(f"{Fore.CYAN}[*] Performing enhanced geolocation...{Style.RESET_ALL}")
            geo_results = await self.perform_enhanced_geolocation(ip)
            results["analysis"]["geolocation"] = geo_results
            
            if verbose and geo_results.get("consensus"):
                location = geo_results["consensus"]
                print(f"{Fore.GREEN}[+] Location: {location.get('city', 'Unknown')}, {location.get('country', 'Unknown')} - ISP: {location.get('isp', 'Unknown')} (confidence: {location.get('consensus_confidence', 0):.2f}){Style.RESET_ALL}")
            
            # Enhanced reverse DNS
            if verbose:
                print(f"{Fore.CYAN}[*] Performing enhanced reverse DNS...{Style.RESET_ALL}")
            dns_results = await self.perform_enhanced_reverse_dns(ip)
            results["analysis"]["reverse_dns"] = dns_results
            
            if verbose and dns_results.get("hostname"):
                print(f"{Fore.GREEN}[+] Hostname: {dns_results['hostname']}{Style.RESET_ALL}")
            
            # Advanced port scanning
            if verbose:
                print(f"{Fore.CYAN}[*] Performing advanced port scan...{Style.RESET_ALL}")
            port_results = await self.perform_advanced_port_scan(ip, verbose)
            results["analysis"]["port_scan"] = port_results
            
            # VPN/Proxy detection
            if verbose:
                print(f"{Fore.CYAN}[*] Performing VPN/Proxy detection...{Style.RESET_ALL}")
            vpn_results = self.detect_vpn_proxy(ip, geo_results, dns_results)
            results["analysis"]["vpn_detection"] = vpn_results
            
            if verbose:
                risk_level = vpn_results.get("risk_level", "LOW")
                print(f"{Fore.GREEN}[+] VPN/Proxy risk: {risk_level} ({vpn_results.get('indicators_count', 0)} indicators){Style.RESET_ALL}")
            
            # Abuse checking
            if verbose:
                print(f"{Fore.CYAN}[*] Performing abuse checks...{Style.RESET_ALL}")
            abuse_results = await self.check_abuse_enhanced(ip)
            results["analysis"]["abuse_check"] = abuse_results
            
            if verbose:
                confidence = abuse_results.get("abuse_confidence", 0)
                reports = abuse_results.get("total_reports", 0)
                print(f"{Fore.GREEN}[+] Abuse confidence: {confidence}% ({reports} reports){Style.RESET_ALL}")
            
            
        except Exception as e:
            results["error"] = str(e)
            print(f"{Fore.RED}[-] Error during IP analysis: {str(e)}{Style.RESET_ALL}")
        
        return results
    
    async def enhanced_geolocation(self, ip_address):
        """Enhanced geolocation with multiple APIs and data correlation"""
        results = {}
        consensus_data = {}
        
        # Query all APIs concurrently
        tasks = []
        for api in self.geo_apis:
            task = self.query_geolocation_api(ip_address, api)
            tasks.append(task)
        
        api_responses = await asyncio.gather(*tasks, return_exceptions=True)
        
        # Process responses
        for i, response in enumerate(api_responses):
            api = self.geo_apis[i]
            if isinstance(response, dict) and "error" not in response:
                results[api["name"]] = response
                
                # Build consensus data
                for key, value in response.items():
                    if key not in consensus_data:
                        consensus_data[key] = {}
                    if value not in consensus_data[key]:
                        consensus_data[key][value] = 0
                    consensus_data[key][value] += 1
        
        # Calculate consensus
        consensus = {}
        for key, values in consensus_data.items():
            if values:
                consensus[key] = max(values.items(), key=lambda x: x[1])[0]
                consensus[f"{key}_confidence"] = max(values.values()) / len(self.geo_apis)
        
        # Additional analysis
        analysis = {
            "country": consensus.get("country"),
            "country_code": consensus.get("countryCode"),
            "region": consensus.get("regionName") or consensus.get("region"),
            "city": consensus.get("city"),
            "latitude": consensus.get("lat") or consensus.get("latitude"),
            "longitude": consensus.get("lon") or consensus.get("longitude"),
            "timezone": consensus.get("timezone"),
            "isp": consensus.get("isp"),
            "organization": consensus.get("org"),
            "as_number": consensus.get("as"),
            "data_sources": len(results),
            "consensus_confidence": sum(
                consensus.get(f"{k}_confidence", 0) 
                for k in ["country", "city", "isp", "org"]
            ) / 4
        }
        
        return {
            "raw_results": results,
            "consensus": analysis,
            "reliable_sources": sum(1 for r in results.values() if r)
        }
    
    async def query_geolocation_api(self, ip_address, api_config):
        """Query individual geolocation API"""
        try:
            url = api_config["url"].format(ip_address)
            timeout = aiohttp.ClientTimeout(total=8)
            
            async with aiohttp.ClientSession(timeout=timeout) as session:
                headers = {"User-Agent": self.ua.random}
                async with session.get(url, headers=headers) as response:
                    if response.status == 200:
                        data = await response.json()
                        
                        # Standardize response format
                        if api_config["name"] == "ip-api":
                            if data.get("status") == "success":
                                return data
                            else:
                                return {"error": data.get("message", "API error")}
                        else:
                            return data
                    else:
                        return {"error": f"HTTP {response.status}"}
        except Exception as e:
            return {"error": str(e)}
    
    async def enhanced_reverse_dns(self, ip_address):
        """Enhanced reverse DNS with multiple techniques"""
        results = {}
        
        # Standard reverse DNS
        try:
            hostname, aliaslist, ipaddrlist = socket.gethostbyaddr(ip_address)
            results["standard"] = {
                "hostname": hostname,
                "aliases": aliaslist,
                "ip_addresses": ipaddrlist,
                "method": "standard_reverse_dns"
            }
        except socket.herror:
            results["standard"] = {"error": "No reverse DNS record found"}
        except Exception as e:
            results["standard"] = {"error": str(e)}
        
        # Try to get additional DNS records
        try:
            # Try to get TXT records for the IP
            import dns.resolver
            reversed_ip = '.'.join(reversed(ip_address.split('.'))) + '.in-addr.arpa'
            txt_answers = dns.resolver.resolve(reversed_ip, 'TXT')
            results["txt_records"] = [str(rdata) for rdata in txt_answers]
        except:
            results["txt_records"] = []
        
        # Analyze hostname patterns
        if "standard" in results and "hostname" in results["standard"]:
            hostname = results["standard"]["hostname"]
            results["hostname_analysis"] = self.analyze_hostname(hostname)
        
        return results
    
    def analyze_hostname(self, hostname):
        """Analyze hostname for patterns and indicators"""
        if not hostname:
            return {"error": "No hostname to analyze"}
        
        analysis = {
            "hostname": hostname,
            "length": len(hostname),
            "subdomains": len(hostname.split('.')) - 2,
            "tld": hostname.split('.')[-1] if '.' in hostname else "",
            "patterns": []
        }
        
        # Check for patterns
        hostname_lower = hostname.lower()
        
        # VPN/Proxy indicators
        for indicator in self.vpn_indicators:
            if indicator in hostname_lower:
                analysis["patterns"].append(f"vpn_proxy_indicator: {indicator}")
        
        # Hosting patterns
        hosting_patterns = ['host', 'server', 'dedicated', 'vps', 'cloud', 'compute']
        for pattern in hosting_patterns:
            if pattern in hostname_lower:
                analysis["patterns"].append(f"hosting_pattern: {pattern}")
        
        # Geographic indicators
        geo_patterns = ['us', 'eu', 'asia', 'uk', 'de', 'fr', 'jp', 'cn', 'ru', 'br']
        for pattern in geo_patterns:
            if pattern in hostname_lower:
                analysis["patterns"].append(f"geographic_indicator: {pattern}")
        
        # Number patterns
        if re.search(r'\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}', hostname):
            analysis["patterns"].append("contains_ip_pattern")
        
        return analysis
    
    async def advanced_port_scan(self, ip_address, scan_type="quick"):
        """Advanced port scanning with multiple techniques"""
        
        if scan_type == "quick":
            ports_to_scan = self.quick_scan_ports
        elif scan_type == "full":
            # Combine all port categories
            ports_to_scan = []
            for category_ports in self.port_categories.values():
                ports_to_scan.extend(category_ports)
            ports_to_scan = list(set(ports_to_scan))  # Remove duplicates
        else:
            ports_to_scan = self.quick_scan_ports
        
        open_ports = []
        filtered_ports = []
        closed_ports = []
        
        # Use semaphore to limit concurrent connections
        semaphore = asyncio.Semaphore(50)
        
        async def scan_port(port):
            try:
                async with semaphore:
                    # Try TCP connection
                    future = asyncio.open_connection(ip_address, port)
                    reader, writer = await asyncio.wait_for(future, timeout=2)
                    
                    # Port is open
                    writer.close()
                    await writer.wait_closed()
                    
                    # Try to get service info
                    service_info = await self.get_service_info(ip_address, port)
                    
                    return {
                        "port": port,
                        "status": "open",
                        "service": service_info.get("service", "unknown"),
                        "banner": service_info.get("banner", ""),
                        "response_time": service_info.get("response_time", 0)
                    }
            except (asyncio.TimeoutError, ConnectionRefusedError, OSError):
                # Port is closed or filtered
                return {"port": port, "status": "closed"}
            except Exception as e:
                return {"port": port, "status": "error", "error": str(e)}
        
        # Scan ports concurrently
        tasks = [scan_port(port) for port in ports_to_scan]
        results = await asyncio.gather(*tasks, return_exceptions=True)
        
        # Process results
        for result in results:
            if isinstance(result, dict):
                if result["status"] == "open":
                    open_ports.append(result)
                elif result["status"] == "closed":
                    closed_ports.append(result["port"])
                else:
                    filtered_ports.append(result["port"])
        
        # Analyze port patterns
        port_analysis = self.analyze_port_patterns(open_ports, ports_to_scan)
        
        return {
            "scan_type": scan_type,
            "total_ports_scanned": len(ports_to_scan),
            "open_ports": open_ports,
            "closed_ports": closed_ports,
            "filtered_ports": filtered_ports,
            "analysis": port_analysis,
            "scan_time": time.time()
        }
    
    async def get_service_info(self, ip_address, port):
        """Get service information for open port"""
        service_info = {"service": "unknown", "banner": "", "response_time": 0}
        
        try:
            start_time = time.time()
            
            # Try to connect and read banner
            future = asyncio.open_connection(ip_address, port)
            reader, writer = await asyncio.wait_for(future, timeout=1)
            
            # Try to read banner (for services that send one)
            try:
                writer.write(b"\r\n")
                await writer.drain()
                
                banner = await asyncio.wait_for(reader.read(1024), timeout=1)
                if banner:
                    service_info["banner"] = banner.decode('utf-8', errors='ignore').strip()
            except:
                pass
            
            writer.close()
            await writer.wait_closed()
            
            service_info["response_time"] = round((time.time() - start_time) * 1000, 2)
            
            # Identify service based on port and banner
            service_info["service"] = self.identify_service(port, service_info["banner"])
            
        except:
            pass
        
        return service_info
    
    def identify_service(self, port, banner=""):
        """Identify service based on port and banner"""
        service_map = {
            21: "FTP",
            22: "SSH",
            23: "Telnet",
            25: "SMTP",
            53: "DNS",
            80: "HTTP",
            110: "POP3",
            143: "IMAP",
            443: "HTTPS",
            993: "IMAPS",
            995: "POP3S",
            3306: "MySQL",
            3389: "RDP",
            5432: "PostgreSQL",
            5900: "VNC",
            6379: "Redis",
            8080: "HTTP-Alt",
            8443: "HTTPS-Alt",
            27017: "MongoDB"
        }
        
        # Check banner for service identification
        banner_lower = banner.lower()
        if "ssh" in banner_lower:
            return "SSH"
        elif "ftp" in banner_lower:
            return "FTP"
        elif "http" in banner_lower or "html" in banner_lower:
            return "HTTP"
        elif "mysql" in banner_lower:
            return "MySQL"
        elif "postgresql" in banner_lower:
            return "PostgreSQL"
        elif "redis" in banner_lower:
            return "Redis"
        
        return service_map.get(port, "unknown")
    
    def analyze_port_patterns(self, open_ports, scanned_ports):
        """Analyze port patterns for security insights"""
        analysis = {
            "total_open": len(open_ports),
            "open_port_list": [p["port"] for p in open_ports],
            "services": list(set(p["service"] for p in open_ports if p["service"] != "unknown")),
            "risk_level": "LOW",
            "indicators": []
        }
        
        # Calculate risk level
        if len(open_ports) > 10:
            analysis["risk_level"] = "HIGH"
            analysis["indicators"].append("many_open_ports")
        elif len(open_ports) > 5:
            analysis["risk_level"] = "MEDIUM"
            analysis["indicators"].append("moderate_open_ports")
        
        # Check for suspicious combinations
        open_port_numbers = [p["port"] for p in open_ports]
        for combination in self.suspicious_combinations:
            if all(port in open_port_numbers for port in combination):
                analysis["risk_level"] = "HIGH"
                analysis["indicators"].append(f"suspicious_combination: {combination}")
        
        # Check for remote access services
        remote_ports = [22, 3389, 5900]
        if any(port in open_port_numbers for port in remote_ports):
            analysis["indicators"].append("remote_access_services")
            if analysis["risk_level"] == "LOW":
                analysis["risk_level"] = "MEDIUM"
        
        # Check for database services
        db_ports = [3306, 5432, 6379, 27017]
        if any(port in open_port_numbers for port in db_ports):
            analysis["indicators"].append("database_services")
        
        # Check for web services
        web_ports = [80, 443, 8080, 8443]
        if any(port in open_port_numbers for port in web_ports):
            analysis["indicators"].append("web_services")
        
        return analysis
    
    async def enhanced_vpn_proxy_detection(self, ip_address):
        """Enhanced VPN/Proxy detection with multiple indicators"""
        detection_methods = {
            "geolocation_analysis": {},
            "hostname_analysis": {},
            "asn_analysis": {},
            "reputation_check": {}
        }
        
        # Method 1: Geolocation analysis
        geo_data = await self.enhanced_geolocation(ip_address)
        if "consensus" in geo_data:
            consensus = geo_data["consensus"]
            isp = consensus.get("isp", "").lower()
            org = consensus.get("organization", "").lower()
            
            geo_indicators = []
            for indicator in self.vpn_indicators:
                if indicator in isp or indicator in org:
                    geo_indicators.append(indicator)
            
            detection_methods["geolocation_analysis"] = {
                "indicators_found": geo_indicators,
                "isp": consensus.get("isp"),
                "organization": consensus.get("organization"),
                "is_suspicious": len(geo_indicators) > 0
            }
        
        # Method 2: Hostname analysis
        reverse_dns = await self.enhanced_reverse_dns(ip_address)
        if "hostname_analysis" in reverse_dns:
            hostname_analysis = reverse_dns["hostname_analysis"]
            patterns = hostname_analysis.get("patterns", [])
            
            vpn_patterns = [p for p in patterns if "vpn_proxy" in p or "hosting" in p]
            
            detection_methods["hostname_analysis"] = {
                "patterns": patterns,
                "vpn_patterns": vpn_patterns,
                "is_suspicious": len(vpn_patterns) > 0
            }
        
        # Method 3: ASN analysis
        if "consensus" in geo_data:
            as_number = geo_data["consensus"].get("as_number", "")
            if as_number:
                # Check for known hosting/VPN ASNs
                suspicious_asn_patterns = [
                    "AS13335",  # Cloudflare
                    "AS16509",  # Amazon
                    "AS8075",   # Microsoft
                    "AS15169",  # Google
                    "AS16276",  # OVH
                    "AS197695", # DigitalOcean
                ]
                
                detection_methods["asn_analysis"] = {
                    "as_number": as_number,
                    "is_known_hosting": any(asn in as_number for asn in suspicious_asn_patterns),
                    "is_suspicious": any(asn in as_number for asn in suspicious_asn_patterns)
                }
        
        # Overall assessment
        total_suspicious = sum(
            method.get("is_suspicious", False) 
            for method in detection_methods.values()
        )
        
        overall_risk = "LOW"
        if total_suspicious >= 2:
            overall_risk = "HIGH"
        elif total_suspicious >= 1:
            overall_risk = "MEDIUM"
        
        return {
            "detection_methods": detection_methods,
            "overall_assessment": {
                "risk_level": overall_risk,
                "suspicious_indicators": total_suspicious,
                "total_methods": len(detection_methods)
            }
        }
    
    async def enhanced_abuse_check(self, ip_address):
        """Enhanced abuse checking with multiple sources"""
        abuse_sources = {}
        
        # Method 1: AbuseIPDB (if API key available)
        try:
            with open('config.json', 'r') as f:
                config = json.load(f)
                abuseipdb_key = config.get('api_keys', {}).get('abuseipdb', '')
                
                if abuseipdb_key:
                    url = f"https://api.abuseipdb.com/api/v2/check?ipAddress={ip_address}&maxAgeInDays=90&verbose"
                    headers = {"Key": abuseipdb_key, "Accept": "application/json"}
                    
                    timeout = aiohttp.ClientTimeout(total=10)
                    async with aiohttp.ClientSession(timeout=timeout) as session:
                        async with session.get(url, headers=headers) as response:
                            if response.status == 200:
                                data = await response.json()
                                abuse_sources["abuseipdb"] = {
                                    "confidence_score": data.get("data", {}).get("abuseConfidenceScore", 0),
                                    "country_code": data.get("data", {}).get("countryCode"),
                                    "usage_type": data.get("data", {}).get("usageType"),
                                    "isp": data.get("data", {}).get("isp"),
                                    "domain": data.get("data", {}).get("domain"),
                                    "total_reports": data.get("data", {}).get("totalReports", 0),
                                    "last_reported": data.get("data", {}).get("lastReportedAt")
                                }
                            else:
                                abuse_sources["abuseipdb"] = {"error": f"HTTP {response.status}"}
        except:
            abuse_sources["abuseipdb"] = {"error": "API key not configured or request failed"}
        
        # Method 2: Generic reputation check (placeholder)
        abuse_sources["reputation_analysis"] = {
            "note": "Advanced reputation checking requires API integration",
            "sources": ["Spamhaus", "Project Honey Pot", "PhishTank"]
        }
        
        return abuse_sources
    
    async def analyze_enhanced(self, ip_address, verbose=False):
        """Enhanced IP analysis with all features"""
        
        # Validate IP
        validation_result = self.validate_ip(ip_address)
        if not validation_result["valid"]:
            raise ValueError(validation_result.get("error", "Invalid IP address"))
        
        results = {
            "ip_address": ip_address,
            "timestamp": time.time(),
            "analysis": {},
            "enhanced": True
        }
        
        try:
            # Add validation info
            results["validation"] = validation_result
            
            # Geolocation analysis
            if verbose:
                print(f"{Fore.CYAN}[*] Performing enhanced geolocation...{Style.RESET_ALL}")
            
            geo_info = await self.enhanced_geolocation(ip_address)
            results["analysis"]["geolocation"] = geo_info
            
            if verbose and "consensus" in geo_info:
                consensus = geo_info["consensus"]
                country = consensus.get("country", "Unknown")
                city = consensus.get("city", "Unknown")
                isp = consensus.get("isp", "Unknown")
                confidence = consensus.get("consensus_confidence", 0)
                print(f"{Fore.GREEN}[+] Location: {city}, {country} - ISP: {isp} (confidence: {confidence:.2f}){Style.RESET_ALL}")
            
            # Reverse DNS analysis
            if verbose:
                print(f"{Fore.CYAN}[*] Performing enhanced reverse DNS...{Style.RESET_ALL}")
            
            dns_info = await self.enhanced_reverse_dns(ip_address)
            results["analysis"]["reverse_dns"] = dns_info
            
            if verbose and "standard" in dns_info and "hostname" in dns_info["standard"]:
                hostname = dns_info["standard"]["hostname"]
                print(f"{Fore.GREEN}[+] Hostname: {hostname}{Style.RESET_ALL}")
            
            # Port scanning
            if verbose:
                print(f"{Fore.CYAN}[*] Performing advanced port scan...{Style.RESET_ALL}")
            
            port_info = await self.advanced_port_scan(ip_address, "quick")
            results["analysis"]["port_scan"] = port_info
            
            if verbose:
                open_count = len(port_info["open_ports"])
                risk_level = port_info["analysis"]["risk_level"]
                print(f"{Fore.GREEN}[+] {open_count} open ports (risk: {risk_level}){Style.RESET_ALL}")
                
                if port_info["open_ports"]:
                    print(f"{Fore.YELLOW}    Open ports: {', '.join(str(p['port']) for p in port_info['open_ports'][:10])}{Style.RESET_ALL}")
            
            # VPN/Proxy detection
            if verbose:
                print(f"{Fore.CYAN}[*] Performing VPN/Proxy detection...{Style.RESET_ALL}")
            
            vpn_info = await self.enhanced_vpn_proxy_detection(ip_address)
            results["analysis"]["vpn_proxy"] = vpn_info
            
            if verbose:
                risk_level = vpn_info["overall_assessment"]["risk_level"]
                indicators = vpn_info["overall_assessment"]["suspicious_indicators"]
                print(f"{Fore.GREEN}[+] VPN/Proxy risk: {risk_level} ({indicators} indicators){Style.RESET_ALL}")
            
            # Abuse checking
            if verbose:
                print(f"{Fore.CYAN}[*] Performing abuse checks...{Style.RESET_ALL}")
            
            abuse_info = await self.enhanced_abuse_check(ip_address)
            results["analysis"]["abuse"] = abuse_info
            
            if verbose and "abuseipdb" in abuse_info:
                abuse_data = abuse_info["abuseipdb"]
                if "confidence_score" in abuse_data:
                    score = abuse_data["confidence_score"]
                    reports = abuse_data.get("total_reports", 0)
                    print(f"{Fore.GREEN}[+] Abuse confidence: {score}% ({reports} reports){Style.RESET_ALL}")
            
            # Generate comprehensive summary
            results["summary"] = {
                "ip_address": ip_address,
                "ip_type": validation_result.get("type", "Unknown"),
                "is_private": validation_result.get("is_private", False),
                "country": geo_info.get("consensus", {}).get("country"),
                "city": geo_info.get("consensus", {}).get("city"),
                "isp": geo_info.get("consensus", {}).get("isp"),
                "hostname": dns_info.get("standard", {}).get("hostname"),
                "open_ports_count": len(port_info.get("open_ports", [])),
                "services": port_info.get("analysis", {}).get("services", []),
                "port_scan_risk": port_info.get("analysis", {}).get("risk_level"),
                "vpn_proxy_risk": vpn_info.get("overall_assessment", {}).get("risk_level"),
                "abuse_confidence": abuse_info.get("abuseipdb", {}).get("confidence_score", 0),
                "overall_risk": self.calculate_overall_risk(
                    port_info.get("analysis", {}).get("risk_level"),
                    vpn_info.get("overall_assessment", {}).get("risk_level"),
                    abuse_info.get("abuseipdb", {}).get("confidence_score", 0)
                ),
                "analysis_complete": True
            }
            
            
        except Exception as e:
            results["error"] = str(e)
            print(f"{Fore.RED}[-] Error during analysis: {str(e)}{Style.RESET_ALL}")
        
        return results
    
    def calculate_overall_risk(self, port_risk, vpn_risk, abuse_confidence):
        """Calculate overall risk level"""
        risk_scores = {"LOW": 1, "MEDIUM": 2, "HIGH": 3}
        
        port_score = risk_scores.get(port_risk, 1)
        vpn_score = risk_scores.get(vpn_risk, 1)
        
        # Calculate average score
        avg_score = (port_score + vpn_score + (abuse_confidence / 33.33)) / 3
        
        if avg_score >= 2.5:
            return "HIGH"
        elif avg_score >= 1.5:
            return "MEDIUM"
        else:
            return "LOW"
    
    async def analyze(self, ip_address, verbose=False):
        """Main analysis method (backward compatibility)"""
        return await self.analyze_enhanced(ip_address, verbose)
