import threading
import nmap3
from functools import partial
import json

def test_concurrent_scans():

    def scan_target(addr, label):
        nm = nmap3.Nmap()
        # progress_callback now only passes a string
        res = nm.scan_top_ports(addr, progress_callback=print_progress)
        print(f"-----{label} Result-----")
        print(json.dumps(res, indent=4, sort_keys=True))

    # Targets and labels
    targets = [
        ("192.168.1.185", "Scan1"),
        ("192.168.1.186", "Scan2")
    ]

    threads = []

    for addr, label in targets:
        t = threading.Thread(target=scan_target, args=(addr, label))
        t.start()
        threads.append(t)

    for t in threads:
        t.join()

    print("All scans complete.")

def print_progress(progress):
    print(progress)

# Call the test function
if __name__ == "__main__":
    nm = nmap3.Nmap()
    nst = nmap3.NmapScanTechniques()
    nhd = nmap3.NmapHostDiscovery()
    
    # Test concurrent scans
    print("testing: concurrent scans")
    test_concurrent_scans()

    # Nmap instance tests
    print("testing: scan_top_ports")
    res = nm.scan_top_ports("192.168.1.185", progress_callback=print_progress, timeout=1)
    print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_dns_brute_script")
    res = nm.nmap_dns_brute_script("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_os_detection")
    res = nm.nmap_os_detection("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_stealth_scan")
    res = nm.nmap_stealth_scan("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_detect_firewall")
    res = nm.nmap_detect_firewall("192.168.1.185", progress_callback=None)
    print(res)
    #print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_subnet_scan")
    res = nm.nmap_subnet_scan("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_list_scan")
    res = nm.nmap_list_scan("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))

    # NmapScanTechniques tests
    print("testing: nmap_fin_scan")
    res = nst.nmap_fin_scan("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_syn_scan")
    res = nst.nmap_syn_scan("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_tcp_scan")
    res = nst.nmap_tcp_scan("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_udp_scan")
    res = nst.nmap_udp_scan("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_ping_scan")
    res = nst.nmap_ping_scan("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_idle_scan")
    res = nst.nmap_idle_scan("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))

    print("testing: nmap_ip_scan")
    res = nst.nmap_ip_scan("192.168.1.185", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))
    
    # NmapHostDiscovery tests
    print("testing: nmap_portscan_only")
    res = nhd.nmap_portscan_only("192.168.1.185/24", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))
    
    print("testing: nmap_no_portscan")
    res = nhd.nmap_no_portscan("192.168.1.185/24", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))
    
    print("testing: nmap_arp_discovery")
    res = nhd.nmap_arp_discovery("192.168.1.185/24", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))
    
    print("testing: nmap_disable_dns")
    res = nhd.nmap_disable_dns("192.168.1.185/24", progress_callback=print_progress)
    print(json.dumps(res, indent=4, sort_keys=True))
