最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

基于Python編寫(xiě)一個(gè)簡(jiǎn)單的端口掃描器

 更新時(shí)間:2025年11月04日 09:10:16   作者:閑人編程  
在當(dāng)今數(shù)字化時(shí)代,網(wǎng)絡(luò)安全已成為個(gè)人和企業(yè)不可忽視的重要議題,端口掃描作為網(wǎng)絡(luò)偵察的基礎(chǔ)技術(shù),是網(wǎng)絡(luò)安全領(lǐng)域中的一個(gè)核心概念,下面我們就來(lái)看看如何基于Python編寫(xiě)一個(gè)簡(jiǎn)單的端口掃描器

1. 引言

在當(dāng)今數(shù)字化時(shí)代,網(wǎng)絡(luò)安全已成為個(gè)人和企業(yè)不可忽視的重要議題。隨著網(wǎng)絡(luò)攻擊手段的不斷升級(jí),了解基本的網(wǎng)絡(luò)安全原理和工具變得尤為重要。端口掃描作為網(wǎng)絡(luò)偵察的基礎(chǔ)技術(shù),是網(wǎng)絡(luò)安全領(lǐng)域中的一個(gè)核心概念。

1.1 端口掃描的重要性

端口掃描器是一種用于探測(cè)目標(biāo)主機(jī)開(kāi)放端口的工具,它可以幫助網(wǎng)絡(luò)管理員:

  • 檢測(cè)網(wǎng)絡(luò)中存在的安全漏洞
  • 驗(yàn)證防火墻規(guī)則的有效性
  • 識(shí)別未經(jīng)授權(quán)的服務(wù)
  • 評(píng)估網(wǎng)絡(luò)安全性

1.2 Python在網(wǎng)絡(luò)安全中的優(yōu)勢(shì)

Python因其簡(jiǎn)潔的語(yǔ)法、豐富的庫(kù)生態(tài)系統(tǒng)和強(qiáng)大的社區(qū)支持,已成為網(wǎng)絡(luò)安全領(lǐng)域的首選編程語(yǔ)言之一。在端口掃描器開(kāi)發(fā)方面,Python提供了socket、threading等標(biāo)準(zhǔn)庫(kù),使得網(wǎng)絡(luò)編程變得簡(jiǎn)單高效。

本文將詳細(xì)介紹如何使用Python編寫(xiě)一個(gè)功能完整的端口掃描器,涵蓋從基礎(chǔ)原理到高級(jí)優(yōu)化的各個(gè)方面。

2. 端口掃描基礎(chǔ)

2.1 網(wǎng)絡(luò)端口概念

在網(wǎng)絡(luò)通信中,端口是計(jì)算機(jī)與外部世界通信的虛擬端點(diǎn)。每個(gè)端口都有一個(gè)唯一的數(shù)字標(biāo)識(shí),范圍從0到65535。根據(jù)IANA(互聯(lián)網(wǎng)號(hào)碼分配機(jī)構(gòu))的規(guī)定,端口可分為三類(lèi):

  • 知名端口(0-1023):分配給系統(tǒng)服務(wù),如HTTP(80)、HTTPS(443)、SSH(22)
  • 注冊(cè)端口(1024-49151):分配給用戶(hù)應(yīng)用程序
  • 動(dòng)態(tài)/私有端口(49152-65535):臨時(shí)分配給客戶(hù)端應(yīng)用程序

2.2 TCP/IP握手過(guò)程

TCP(傳輸控制協(xié)議)是一種面向連接的協(xié)議,它通過(guò)三次握手建立可靠連接:

  • SYN:客戶(hù)端發(fā)送SYN包到服務(wù)器,請(qǐng)求建立連接
  • SYN-ACK:服務(wù)器響應(yīng)SYN-ACK包,確認(rèn)連接請(qǐng)求
  • ACK:客戶(hù)端發(fā)送ACK包,完成連接建立

端口掃描技術(shù)正是基于對(duì)這一過(guò)程的巧妙利用。

2.3 常見(jiàn)的端口掃描技術(shù)

掃描類(lèi)型原理優(yōu)點(diǎn)缺點(diǎn)
TCP Connect掃描完成完整的TCP三次握手準(zhǔn)確可靠,不需要特殊權(quán)限容易被檢測(cè),速度較慢
SYN掃描(半開(kāi)放掃描)只發(fā)送SYN包,不完成握手速度快,相對(duì)隱蔽需要原始套接字權(quán)限
UDP掃描發(fā)送UDP包并分析響應(yīng)可檢測(cè)UDP服務(wù)不可靠,速度慢
FIN掃描發(fā)送FIN包繞過(guò)防火墻可繞過(guò)某些防火墻結(jié)果可能不準(zhǔn)確

3. 端口掃描器設(shè)計(jì)

3.1 功能需求分析

我們的端口掃描器需要具備以下核心功能:

  • 基本掃描功能:能夠檢測(cè)指定主機(jī)的端口狀態(tài)
  • 多線(xiàn)程支持:提高掃描效率
  • 靈活的端口范圍指定:支持單個(gè)端口、端口列表和端口范圍
  • 超時(shí)控制:避免長(zhǎng)時(shí)間等待無(wú)響應(yīng)端口
  • 結(jié)果輸出:清晰展示掃描結(jié)果
  • 錯(cuò)誤處理:優(yōu)雅處理網(wǎng)絡(luò)異常和用戶(hù)輸入錯(cuò)誤

3.2 系統(tǒng)架構(gòu)設(shè)計(jì)

4. 數(shù)學(xué)原理與性能優(yōu)化

4.1 掃描時(shí)間估算

端口掃描的總時(shí)間可以通過(guò)以下公式估算:

Ttotal?=Nports?×Ttimeout?×(1/Nthreads)+Toverhead?

其中:

  • Ttotal?:總掃描時(shí)間
  • Nports?:掃描的端口數(shù)量
  • Ttimeout?:?jiǎn)蝹€(gè)端口超時(shí)時(shí)間
  • Nthreads?:線(xiàn)程數(shù)量
  • Toverhead?:線(xiàn)程管理和結(jié)果處理的額外開(kāi)銷(xiāo)

4.2 最優(yōu)線(xiàn)程數(shù)計(jì)算

根據(jù)Amdahl定律,并行程序的加速比受限于其串行部分。對(duì)于端口掃描器,最優(yōu)線(xiàn)程數(shù)可以通過(guò)以下方式估算:

Noptimal?=(Tserial??/Tparallel?)×Ncores?

在實(shí)際應(yīng)用中,考慮到網(wǎng)絡(luò)延遲和系統(tǒng)資源限制,我們通常設(shè)置線(xiàn)程數(shù)為CPU核心數(shù)的2-4倍。

5. Python實(shí)現(xiàn)細(xì)節(jié)

5.1 核心模塊介紹

我們的端口掃描器將包含以下核心模塊:

  • 參數(shù)解析模塊:處理命令行參數(shù)
  • 網(wǎng)絡(luò)工具模塊:執(zhí)行實(shí)際的端口掃描
  • 線(xiàn)程管理模塊:管理掃描線(xiàn)程池
  • 結(jié)果處理模塊:收集和展示掃描結(jié)果

5.2 關(guān)鍵技術(shù)實(shí)現(xiàn)

5.2.1 Socket編程基礎(chǔ)

Python的socket模塊提供了底層的網(wǎng)絡(luò)通信功能。創(chuàng)建TCP連接的基本流程如下:

import socket

# 創(chuàng)建socket對(duì)象
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
# 設(shè)置超時(shí)時(shí)間
sock.settimeout(5)
try:
    # 嘗試連接
    result = sock.connect_ex((host, port))
    if result == 0:
        print(f"端口 {port} 開(kāi)放")
    else:
        print(f"端口 {port} 關(guān)閉")
except socket.error as e:
    print(f"掃描端口 {port} 時(shí)出錯(cuò): {e}")
finally:
    sock.close()

5.2.2 多線(xiàn)程實(shí)現(xiàn)

為了提高掃描效率,我們使用concurrent.futures模塊實(shí)現(xiàn)線(xiàn)程池:

from concurrent.futures import ThreadPoolExecutor, as_completed

def scan_ports(host, ports, max_threads=100):
    open_ports = []
    with ThreadPoolExecutor(max_workers=max_threads) as executor:
        # 提交掃描任務(wù)
        future_to_port = {
            executor.submit(scan_port, host, port, timeout): port 
            for port in ports
        }
        
        # 收集結(jié)果
        for future in as_completed(future_to_port):
            port = future_to_port[future]
            try:
                result = future.result()
                if result:
                    open_ports.append(port)
            except Exception as e:
                print(f"端口 {port} 掃描異常: {e}")
    
    return sorted(open_ports)

6. 完整代碼實(shí)現(xiàn)

6.1 端口掃描器完整代碼

#!/usr/bin/env python3
"""
簡(jiǎn)單的多線(xiàn)程端口掃描器
作者: 網(wǎng)絡(luò)安全愛(ài)好者
版本: 1.0
"""

import socket
import argparse
import threading
from concurrent.futures import ThreadPoolExecutor, as_completed
import time
import sys
from typing import List, Tuple, Union

class PortScanner:
    """
    端口掃描器類(lèi)
    實(shí)現(xiàn)多線(xiàn)程TCP Connect掃描功能
    """
    
    def __init__(self, timeout: float = 1.0, max_threads: int = 100):
        """
        初始化端口掃描器
        
        Args:
            timeout: 連接超時(shí)時(shí)間(秒)
            max_threads: 最大線(xiàn)程數(shù)
        """
        self.timeout = timeout
        self.max_threads = max_threads
        self.lock = threading.Lock()
        self.scan_results = []
        
    def resolve_host(self, host: str) -> str:
        """
        解析主機(jī)名或IP地址
        
        Args:
            host: 主機(jī)名或IP地址
            
        Returns:
            解析后的IP地址
            
        Raises:
            socket.gaierror: 當(dāng)主機(jī)名無(wú)法解析時(shí)
        """
        try:
            # 嘗試解析主機(jī)名
            ip = socket.gethostbyname(host)
            return ip
        except socket.gaierror as e:
            raise socket.gaierror(f"無(wú)法解析主機(jī): {host}, 錯(cuò)誤: {e}")
    
    def scan_port(self, host: str, port: int) -> Tuple[int, bool, str]:
        """
        掃描單個(gè)端口
        
        Args:
            host: 目標(biāo)主機(jī)
            port: 目標(biāo)端口
            
        Returns:
            (端口, 是否開(kāi)放, 服務(wù)名稱(chēng))
        """
        try:
            # 創(chuàng)建socket對(duì)象
            sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
            sock.settimeout(self.timeout)
            
            # 嘗試連接
            result = sock.connect_ex((host, port))
            
            if result == 0:
                # 端口開(kāi)放,嘗試獲取服務(wù)名稱(chēng)
                try:
                    service = socket.getservbyport(port, 'tcp')
                except OSError:
                    service = "unknown"
                return (port, True, service)
            else:
                return (port, False, "")
                
        except socket.timeout:
            return (port, False, "timeout")
        except socket.error as e:
            return (port, False, f"error: {e}")
        finally:
            try:
                sock.close()
            except:
                pass
    
    def parse_port_range(self, port_range: str) -> List[int]:
        """
        解析端口范圍字符串
        
        Args:
            port_range: 端口范圍字符串,如 "80", "1-100", "22,80,443"
            
        Returns:
            端口列表
            
        Raises:
            ValueError: 當(dāng)端口范圍格式錯(cuò)誤時(shí)
        """
        ports = []
        
        # 處理逗號(hào)分隔的端口列表
        if ',' in port_range:
            parts = port_range.split(',')
            for part in parts:
                if '-' in part:
                    # 處理范圍
                    start, end = part.split('-')
                    try:
                        start_port = int(start.strip())
                        end_port = int(end.strip())
                        if 1 <= start_port <= end_port <= 65535:
                            ports.extend(range(start_port, end_port + 1))
                        else:
                            raise ValueError(f"端口范圍 {part} 無(wú)效")
                    except ValueError as e:
                        raise ValueError(f"無(wú)效的端口范圍: {part}, 錯(cuò)誤: {e}")
                else:
                    # 處理單個(gè)端口
                    try:
                        port = int(part.strip())
                        if 1 <= port <= 65535:
                            ports.append(port)
                        else:
                            raise ValueError(f"端口 {port} 超出范圍")
                    except ValueError as e:
                        raise ValueError(f"無(wú)效的端口: {part}, 錯(cuò)誤: {e}")
        
        # 處理端口范圍
        elif '-' in port_range:
            start, end = port_range.split('-')
            try:
                start_port = int(start.strip())
                end_port = int(end.strip())
                if 1 <= start_port <= end_port <= 65535:
                    ports = list(range(start_port, end_port + 1))
                else:
                    raise ValueError(f"端口范圍 {port_range} 無(wú)效")
            except ValueError as e:
                raise ValueError(f"無(wú)效的端口范圍: {port_range}, 錯(cuò)誤: {e}")
        
        # 處理單個(gè)端口
        else:
            try:
                port = int(port_range)
                if 1 <= port <= 65535:
                    ports = [port]
                else:
                    raise ValueError(f"端口 {port} 超出范圍")
            except ValueError as e:
                raise ValueError(f"無(wú)效的端口: {port_range}, 錯(cuò)誤: {e}")
        
        return sorted(set(ports))  # 去重并排序
    
    def scan_ports(self, host: str, ports: Union[str, List[int]], 
                   show_closed: bool = False) -> List[Tuple[int, bool, str]]:
        """
        掃描指定主機(jī)的端口
        
        Args:
            host: 目標(biāo)主機(jī)
            ports: 端口范圍或列表
            show_closed: 是否顯示關(guān)閉的端口
            
        Returns:
            掃描結(jié)果列表,每個(gè)元素為 (端口, 是否開(kāi)放, 服務(wù)名稱(chēng))
        """
        # 解析主機(jī)名
        try:
            ip = self.resolve_host(host)
            print(f"掃描主機(jī): {host} ({ip})")
        except socket.gaierror as e:
            print(f"錯(cuò)誤: {e}")
            return []
        
        # 解析端口
        if isinstance(ports, str):
            try:
                port_list = self.parse_port_range(ports)
            except ValueError as e:
                print(f"錯(cuò)誤: {e}")
                return []
        else:
            port_list = ports
        
        print(f"掃描端口數(shù)量: {len(port_list)}")
        print(f"使用線(xiàn)程數(shù): {self.max_threads}")
        print(f"超時(shí)時(shí)間: {self.timeout}秒")
        print("-" * 50)
        
        start_time = time.time()
        open_count = 0
        
        # 使用線(xiàn)程池執(zhí)行掃描
        with ThreadPoolExecutor(max_workers=self.max_threads) as executor:
            # 提交所有掃描任務(wù)
            future_to_port = {
                executor.submit(self.scan_port, ip, port): port 
                for port in port_list
            }
            
            # 處理完成的任務(wù)
            for future in as_completed(future_to_port):
                port = future_to_port[future]
                try:
                    result = future.result()
                    port_num, is_open, service = result
                    
                    with self.lock:
                        if is_open:
                            print(f"端口 {port_num:5d} 開(kāi)放 - 服務(wù): {service}")
                            open_count += 1
                            self.scan_results.append(result)
                        elif show_closed:
                            print(f"端口 {port_num:5d} 關(guān)閉")
                            self.scan_results.append(result)
                            
                except Exception as e:
                    print(f"掃描端口 {port} 時(shí)發(fā)生異常: {e}")
        
        # 輸出統(tǒng)計(jì)信息
        elapsed_time = time.time() - start_time
        print("-" * 50)
        print(f"掃描完成!")
        print(f"開(kāi)放端口數(shù)量: {open_count}/{len(port_list)}")
        print(f"掃描耗時(shí): {elapsed_time:.2f} 秒")
        
        return self.scan_results

def main():
    """主函數(shù)"""
    parser = argparse.ArgumentParser(
        description="簡(jiǎn)單的多線(xiàn)程端口掃描器",
        formatter_class=argparse.RawDescriptionHelpFormatter,
        epilog="""
使用示例:
  %(prog)s 192.168.1.1 80
  %(prog)s example.com 1-100
  %(prog)s localhost 22,80,443,8000-9000
  %(prog)s 10.0.0.1 1-1000 -t 5 -T 2.0 -v
        """
    )
    
    parser.add_argument("host", help="要掃描的目標(biāo)主機(jī)名或IP地址")
    parser.add_argument("ports", help="要掃描的端口范圍,如: 80, 1-100, 22,80,443")
    parser.add_argument("-t", "--threads", type=int, default=100,
                       help="最大線(xiàn)程數(shù) (默認(rèn): 100)")
    parser.add_argument("-T", "--timeout", type=float, default=1.0,
                       help="連接超時(shí)時(shí)間,單位秒 (默認(rèn): 1.0)")
    parser.add_argument("-v", "--verbose", action="store_true",
                       help="顯示所有端口(包括關(guān)閉的端口)")
    
    args = parser.parse_args()
    
    # 創(chuàng)建掃描器實(shí)例
    scanner = PortScanner(timeout=args.timeout, max_threads=args.threads)
    
    try:
        # 執(zhí)行掃描
        results = scanner.scan_ports(args.host, args.ports, args.verbose)
        
        # 輸出開(kāi)放端口摘要
        if results:
            open_ports = [(port, service) for port, is_open, service in results if is_open]
            if open_ports:
                print("\n開(kāi)放端口摘要:")
                for port, service in sorted(open_ports):
                    print(f"  {port}/tcp - {service}")
            else:
                print("\n未發(fā)現(xiàn)開(kāi)放端口")
                
    except KeyboardInterrupt:
        print("\n掃描被用戶(hù)中斷")
        sys.exit(1)
    except Exception as e:
        print(f"掃描過(guò)程中發(fā)生錯(cuò)誤: {e}")
        sys.exit(1)

if __name__ == "__main__":
    main()

6.2 代碼說(shuō)明與使用示例

6.2.1 代碼結(jié)構(gòu)說(shuō)明

  • PortScanner類(lèi):核心掃描器類(lèi),封裝所有掃描功能
  • resolve_host方法:解析主機(jī)名到IP地址
  • scan_port方法:掃描單個(gè)端口
  • parse_port_range方法:解析端口范圍字符串
  • scan_ports方法:多線(xiàn)程掃描主方法

6.2.2 使用示例

# 掃描單個(gè)端口
python port_scanner.py example.com 80

# 掃描端口范圍
python port_scanner.py 192.168.1.1 1-100

# 掃描多個(gè)指定端口
python port_scanner.py localhost 22,80,443,8000

# 使用更多線(xiàn)程和更長(zhǎng)超時(shí)時(shí)間
python port_scanner.py target.com 1-1000 -t 200 -T 2.0

# 顯示所有端口(包括關(guān)閉的)
python port_scanner.py 10.0.0.1 20-30 -v

7. 高級(jí)功能與優(yōu)化

7.1 性能優(yōu)化策略

7.1.1 動(dòng)態(tài)超時(shí)調(diào)整

根據(jù)網(wǎng)絡(luò)狀況動(dòng)態(tài)調(diào)整超時(shí)時(shí)間可以顯著提高掃描效率:

def adaptive_timeout(self, host: str, sample_ports: List[int] = [80, 443, 22]) -> float:
    """
    根據(jù)樣本端口響應(yīng)時(shí)間計(jì)算合適的超時(shí)時(shí)間
    
    Args:
        host: 目標(biāo)主機(jī)
        sample_ports: 用于測(cè)試的樣本端口
        
    Returns:
        計(jì)算得到的超時(shí)時(shí)間
    """
    response_times = []
    
    for port in sample_ports:
        try:
            start = time.time()
            sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
            sock.settimeout(2.0)
            result = sock.connect_ex((host, port))
            elapsed = time.time() - start
            
            if result == 0:  # 端口開(kāi)放
                response_times.append(elapsed)
            sock.close()
        except:
            pass
    
    if response_times:
        avg_time = sum(response_times) / len(response_times)
        return min(max(avg_time * 3, 0.5), 5.0)  # 限制在0.5-5秒之間
    else:
        return 2.0  # 默認(rèn)超時(shí)時(shí)間

7.1.2 連接池優(yōu)化

對(duì)于大量端口的掃描,可以復(fù)用socket連接以減少資源開(kāi)銷(xiāo):

class ConnectionPool:
    """連接池管理類(lèi)"""
    
    def __init__(self, max_size=10):
        self.max_size = max_size
        self.pool = []
        self.lock = threading.Lock()
    
    def get_connection(self, host, port, timeout):
        """從池中獲取或創(chuàng)建連接"""
        with self.lock:
            if self.pool:
                sock = self.pool.pop()
                try:
                    # 測(cè)試連接是否仍然有效
                    sock.getsockopt(socket.SOL_SOCKET, socket.SO_ERROR)
                    return sock
                except socket.error:
                    sock.close()
            
        # 創(chuàng)建新連接
        sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        sock.settimeout(timeout)
        return sock
    
    def return_connection(self, sock):
        """將連接返回池中"""
        with self.lock:
            if len(self.pool) < self.max_size:
                self.pool.append(sock)
            else:
                sock.close()

7.2 安全與隱蔽性考慮

7.2.1 隨機(jī)化掃描順序

按順序掃描端口容易被入侵檢測(cè)系統(tǒng)識(shí)別,隨機(jī)化掃描順序可以提高隱蔽性:

import random

def randomize_scan_order(self, ports: List[int]) -> List[int]:
    """
    隨機(jī)化端口掃描順序
    
    Args:
        ports: 原始端口列表
        
    Returns:
        隨機(jī)排序后的端口列表
    """
    randomized_ports = ports.copy()
    random.shuffle(randomized_ports)
    return randomized_ports

7.2.2 速率限制

為了避免被目標(biāo)主機(jī)的防火墻封鎖,可以實(shí)施速率限制:

import time

class RateLimiter:
    """速率限制器"""
    
    def __init__(self, max_requests_per_second):
        self.max_requests = max_requests_per_second
        self.interval = 1.0 / max_requests_per_second
        self.last_request_time = 0
        self.lock = threading.Lock()
    
    def acquire(self):
        """獲取執(zhí)行許可"""
        with self.lock:
            current_time = time.time()
            elapsed = current_time - self.last_request_time
            
            if elapsed < self.interval:
                time.sleep(self.interval - elapsed)
            
            self.last_request_time = time.time()

8. 代碼測(cè)試與驗(yàn)證

8.1 單元測(cè)試

為了確保代碼質(zhì)量,我們需要編寫(xiě)單元測(cè)試:

import unittest
from unittest.mock import patch, MagicMock

class TestPortScanner(unittest.TestCase):
    """端口掃描器測(cè)試類(lèi)"""
    
    def setUp(self):
        self.scanner = PortScanner(timeout=0.1, max_threads=10)
    
    def test_resolve_host_valid(self):
        """測(cè)試有效主機(jī)名解析"""
        ip = self.scanner.resolve_host("localhost")
        self.assertEqual(ip, "127.0.0.1")
    
    def test_resolve_host_invalid(self):
        """測(cè)試無(wú)效主機(jī)名解析"""
        with self.assertRaises(socket.gaierror):
            self.scanner.resolve_host("invalid-hostname-that-should-not-exist")
    
    def test_parse_port_range_single(self):
        """測(cè)試單個(gè)端口解析"""
        ports = self.scanner.parse_port_range("80")
        self.assertEqual(ports, [80])
    
    def test_parse_port_range_range(self):
        """測(cè)試端口范圍解析"""
        ports = self.scanner.parse_port_range("1-3")
        self.assertEqual(ports, [1, 2, 3])
    
    def test_parse_port_range_mixed(self):
        """測(cè)試混合端口解析"""
        ports = self.scanner.parse_port_range("80,443,1-3")
        self.assertEqual(ports, [1, 2, 3, 80, 443])
    
    @patch('socket.socket')
    def test_scan_port_open(self, mock_socket):
        """測(cè)試開(kāi)放端口掃描"""
        mock_sock = MagicMock()
        mock_socket.return_value = mock_sock
        mock_sock.connect_ex.return_value = 0
        
        port, is_open, service = self.scanner.scan_port("localhost", 80)
        
        self.assertEqual(port, 80)
        self.assertTrue(is_open)
        mock_sock.connect_ex.assert_called_with(("localhost", 80))

if __name__ == '__main__':
    unittest.main()

8.2 集成測(cè)試

在實(shí)際環(huán)境中測(cè)試掃描器的功能:

def integration_test():
    """集成測(cè)試函數(shù)"""
    scanner = PortScanner(timeout=1.0, max_threads=50)
    
    # 測(cè)試本地主機(jī)
    print("測(cè)試本地主機(jī)掃描...")
    results = scanner.scan_ports("localhost", "80,443,22,8080")
    
    # 驗(yàn)證結(jié)果
    open_ports = [port for port, is_open, service in results if is_open]
    print(f"發(fā)現(xiàn)的開(kāi)放端口: {open_ports}")
    
    # 預(yù)期至少本地回環(huán)地址應(yīng)該有某些端口開(kāi)放
    assert len(open_ports) >= 0, "應(yīng)該能夠掃描本地主機(jī)"

if __name__ == "__main__":
    integration_test()

9. 法律與道德考量

9.1 合法使用原則

端口掃描器是一把雙刃劍,既可以用于安全評(píng)估,也可能被惡意使用。在使用本工具時(shí),請(qǐng)務(wù)必遵守以下原則:

  • 獲得授權(quán):只掃描你擁有或已獲得明確授權(quán)的主機(jī)
  • 遵守法律:了解并遵守當(dāng)?shù)鼐W(wǎng)絡(luò)安全法律法規(guī)
  • 最小影響:避免對(duì)目標(biāo)系統(tǒng)造成不必要的負(fù)擔(dān)
  • 尊重隱私:不掃描或探測(cè)未經(jīng)授權(quán)的網(wǎng)絡(luò)資源

9.2 負(fù)責(zé)任披露

如果發(fā)現(xiàn)安全漏洞,應(yīng)遵循負(fù)責(zé)任披露原則:

  • 私下向相關(guān)組織報(bào)告漏洞
  • 給予合理的時(shí)間修復(fù)問(wèn)題
  • 在公開(kāi)披露前協(xié)調(diào)時(shí)間表

10. 總結(jié)與擴(kuò)展

10.1 項(xiàng)目總結(jié)

通過(guò)本文,我們實(shí)現(xiàn)了一個(gè)功能完整的Python端口掃描器,具備以下特點(diǎn):

  • 多線(xiàn)程支持:大幅提高掃描效率
  • 靈活的端口指定:支持各種端口范圍格式
  • 健壯的錯(cuò)誤處理:優(yōu)雅處理各種異常情況
  • 清晰的輸出:提供詳細(xì)的掃描結(jié)果和統(tǒng)計(jì)信息

10.2 進(jìn)一步擴(kuò)展

這個(gè)基礎(chǔ)掃描器還可以進(jìn)一步擴(kuò)展:

  • 更多掃描技術(shù):實(shí)現(xiàn)SYN掃描、UDP掃描等高級(jí)技術(shù)
  • 服務(wù)指紋識(shí)別:識(shí)別端口上運(yùn)行的具體服務(wù)和版本
  • 操作系統(tǒng)檢測(cè):通過(guò)TCP/IP棧指紋識(shí)別目標(biāo)操作系統(tǒng)
  • 圖形界面:開(kāi)發(fā)易于使用的GUI界面
  • 分布式掃描:支持多臺(tái)機(jī)器協(xié)同掃描

免責(zé)聲明:本文介紹的端口掃描技術(shù)僅用于教育目的和授權(quán)的安全測(cè)試。未經(jīng)授權(quán)掃描他人網(wǎng)絡(luò)可能違反法律,請(qǐng)務(wù)必在合法合規(guī)的前提下使用這些技術(shù)。

代碼自查說(shuō)明:本文提供的代碼已經(jīng)過(guò)基本測(cè)試,但在生產(chǎn)環(huán)境中使用前仍需進(jìn)行充分的安全測(cè)試和代碼審查。特別注意線(xiàn)程安全、資源管理和異常處理等方面。

到此這篇關(guān)于基于Python編寫(xiě)一個(gè)簡(jiǎn)單的端口掃描器的文章就介紹到這了,更多相關(guān)Python端口掃描器內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • PyQt5 pyqt多線(xiàn)程操作入門(mén)

    PyQt5 pyqt多線(xiàn)程操作入門(mén)

    本篇文章主要介紹了PyQt5 pyqt多線(xiàn)程操作入門(mén),小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧
    2018-05-05
  • 關(guān)于pycharm找不到MySQLdb模塊的解決方法

    關(guān)于pycharm找不到MySQLdb模塊的解決方法

    MySQLdb是用于Python鏈接Mysql數(shù)據(jù)庫(kù)的接口,它實(shí)現(xiàn)了Python數(shù)據(jù)庫(kù)API規(guī)范V2.0,基于MySql C API上建立的,本文給大家介紹pycharm找不到MySQLdb模塊解決方法,需要的朋友參考下吧
    2021-06-06
  • Python中異常的捕獲與處理詳解

    Python中異常的捕獲與處理詳解

    這篇文章主要介紹了Python中異常的捕獲與處理詳解,調(diào)試Python程序時(shí),經(jīng)常會(huì)報(bào)出一些異常,異常的原因一方面可能是寫(xiě)程序時(shí)由于疏忽或者考慮不全造成了錯(cuò)誤,這時(shí)就需要根據(jù)異常Traceback到出錯(cuò)點(diǎn),進(jìn)行分析改正,需要的朋友可以參考下
    2023-08-08
  • 將 Ubuntu 16 和 18 上的 python 升級(jí)到最新 python3.8 的方法教程

    將 Ubuntu 16 和 18 上的 python 升級(jí)到最新 python3.8 的方法教程

    這篇文章主要介紹了如何將 Ubuntu 16 和 18 上的 python 升級(jí)到最新 3.8 版,本文通過(guò)實(shí)例代碼相結(jié)合給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2020-03-03
  • Python 元組操作總結(jié)

    Python 元組操作總結(jié)

    這篇文章主要介紹了Python 元組操作總結(jié),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2019-09-09
  • 對(duì)python3中pathlib庫(kù)的Path類(lèi)的使用詳解

    對(duì)python3中pathlib庫(kù)的Path類(lèi)的使用詳解

    今天小編就為大家分享一篇對(duì)python3中pathlib庫(kù)的Path類(lèi)的使用詳解,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧
    2018-10-10
  • Django跨域請(qǐng)求原理及實(shí)現(xiàn)代碼

    Django跨域請(qǐng)求原理及實(shí)現(xiàn)代碼

    這篇文章主要介紹了Django跨域請(qǐng)求原理及實(shí)現(xiàn)代碼,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2020-11-11
  • Python文檔處理之實(shí)現(xiàn)自動(dòng)刪除Word中帶指定底紋顏色的內(nèi)容

    Python文檔處理之實(shí)現(xiàn)自動(dòng)刪除Word中帶指定底紋顏色的內(nèi)容

    這篇文章主要為大家介紹了一個(gè)Python腳本,可以用于自動(dòng)刪除 Word 文檔中帶有指定底紋顏色的解析內(nèi)容,文中的示例代碼講解詳細(xì),有需要的小伙伴可以了解下
    2026-02-02
  • Python Excel處理庫(kù)openpyxl使用詳解

    Python Excel處理庫(kù)openpyxl使用詳解

    openpyxl是一個(gè)第三方庫(kù),可以處理xlsx格式的Excel文件。這篇文章主要介紹了Python Excel處理庫(kù)openpyxl使用詳解,小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧
    2019-05-05
  • Python argv用法詳解

    Python argv用法詳解

    這篇文章主要介紹了Python argv用法詳解的相關(guān)資料,涉及到python argv相關(guān)知識(shí),需要的朋友可以參考下
    2016-01-01

最新評(píng)論

夏邑县| 汝城县| 渭南市| 石屏县| 鄂伦春自治旗| 洛扎县| 工布江达县| 子洲县| 梁河县| 阳山县| 寿阳县| 波密县| 新邵县| 和龙市| 子长县| 门头沟区| 日土县| 南乐县| 青海省| 天峨县| 侯马市| 隆安县| 淮北市| 五寨县| 哈尔滨市| 嵩明县| 龙泉市| 讷河市| 民和| 泸州市| 信丰县| 宁陵县| 什邡市| 赤壁市| 巢湖市| 方正县| 黎川县| 沧州市| 仙居县| 西丰县| 城固县|