Python批量识别资产类型异常:文件资产均被判定为FQDN
问题描述
现有Python代码可正常识别单个IP或FQDN,但读取文件中的资产列表时,所有资产均被错误判定为FQDN。测试资产列表如下:
apple 123.4.5.1 bob.com 20.10.4.6 300.100.200.50
需要修改代码,使得通过-T filename -A 文件名参数执行时,能正确逐行评估每个资产的类型(包括最后一个无效IP)。原代码如下:
#!/usr/bin/env python import argparse import ipaddress import re def parse_args(): # Assess arguments parser = argparse.ArgumentParser(description='do some sh*t') parser.add_argument('-T', required=True, choices=['single','filename'], help='Type of input i.e. single asset name or file of assets') parser.add_argument('-A', required=True, help='Asset name or file name') args = parser.parse_args() args = vars(args) asset_type = (args['T']) if asset_type == 'single': single_asset(args) elif asset_type == 'filename': filename_asset(args) else: raise Exception('Unexpected asset type') def single_asset(args): # Function for single asset type print ('single_asset function') asset = (args['A']) identify_asset_type(asset) def filename_asset(args): # Function for file of assets print ('filename_asset function') filename = (args['A']) with open(filename, 'r') as filename_input: for asset in filename_input: identify_asset_type(asset) def identify_asset_type(asset): # Identify if IP address, FQDN or other try: if ipaddress.ip_address(asset): print(f'IP address - {asset}') except ValueError: if re.match(r'^(?!.{255}|.{253}[^.])([a-z0-9](?:[-a-z-0-9]{0,61}[a-z0-9])?\.)*[a-z0-9](?:[-a-z0-9]{0,61}[a-z0-9])?[.]?$', asset, re.IGNORECASE): print (f'FQDN - valid {asset}') else: print ('Not an IP or FQDN')
修改后的代码
#!/usr/bin/env python import argparse import ipaddress import re def parse_args(): parser = argparse.ArgumentParser(description='识别资产类型(IP/FQDN)') parser.add_argument('-T', required=True, choices=['single','filename'], help='输入类型:single(单个资产)或filename(资产文件)') parser.add_argument('-A', required=True, help='资产内容或文件名') args = parser.parse_args() asset_type = args['T'] if asset_type == 'single': single_asset(args) elif asset_type == 'filename': filename_asset(args) else: raise Exception('无效的输入类型') def single_asset(args): print('处理单个资产') asset = args['A'].strip() identify_asset_type(asset) def filename_asset(args): print('处理资产文件') filename = args['A'] with open(filename, 'r') as filename_input: for asset in filename_input: # 去除每行的换行符和首尾空白,跳过空行 cleaned_asset = asset.strip() if not cleaned_asset: continue identify_asset_type(cleaned_asset) def identify_asset_type(asset): # 识别IP地址、FQDN或其他类型 try: ipaddress.ip_address(asset) print(f'IP地址 - {asset}') except ValueError: # 正则排除纯IP格式,适配无后缀名称,同时符合FQDN规则 fqdn_pattern = r'^(?!\d+\.\d+\.\d+\.\d+$)(?:[a-z0-9](?:[-a-z0-9]{0,61}[a-z0-9])?\.)*[a-z0-9](?:[-a-z0-9]{0,61}[a-z0-9])?$' if re.match(fqdn_pattern, asset, re.IGNORECASE): print(f'FQDN - 有效 {asset}') else: print(f'非IP或有效FQDN - {asset}')
修改说明
- 清理换行符:读取文件时每行末尾默认带
\n,直接传入IP识别函数会触发异常,通过strip()清理首尾空白和换行符,同时跳过空行避免无效处理。 - 修正正则规则:原正则会把带换行的IP误判为FQDN,新增
(?!\d+\.\d+\.\d+\.\d+$)前瞻断言,排除纯IP格式的字符串;去掉末尾可选.,避免无意义的匹配。 - 优化输出信息:将模糊提示改为带资产内容的明确信息,方便定位问题资产。
- 简化代码逻辑:移除冗余的
vars()转换和不必要的括号,提升代码可读性。
内容的提问来源于stack exchange,提问作者yeleek
相关产品推荐
相关产品推荐

