223 lines
4.8 KiB
Python
223 lines
4.8 KiB
Python
# -*- coding: UTF-8 -*-
|
|
'''
|
|
@Project :domainScanDemo
|
|
@File :domain_utils.py
|
|
@IDE :PyCharm
|
|
@Author :梦伴
|
|
@Date :2026/4/9 0:05
|
|
@explain : 域名工具类
|
|
'''
|
|
|
|
import re
|
|
import tldextract
|
|
from loguru import logger
|
|
|
|
|
|
def normalize_domain(domain):
|
|
"""
|
|
标准化域名
|
|
|
|
:param domain: 域名
|
|
:return: str - 标准化后的域名
|
|
"""
|
|
try:
|
|
# 转换为小写
|
|
domain = domain.lower()
|
|
|
|
# 去除空格
|
|
domain = domain.strip()
|
|
|
|
# 去除协议
|
|
domain = re.sub(r'^https?://', '', domain)
|
|
|
|
# 去除路径和查询参数
|
|
domain = domain.split('/')[0]
|
|
domain = domain.split('?')[0]
|
|
|
|
# 去除端口
|
|
domain = domain.split(':')[0]
|
|
|
|
# 只保留主域
|
|
ext = tldextract.extract(domain)
|
|
if ext.domain and ext.suffix:
|
|
domain = f"{ext.domain}.{ext.suffix}"
|
|
|
|
# 验证域名格式
|
|
if not is_valid_domain(domain):
|
|
return None
|
|
|
|
return domain
|
|
except Exception as e:
|
|
logger.error(f"标准化域名出错: {e}")
|
|
return None
|
|
|
|
|
|
def is_valid_domain(domain):
|
|
"""
|
|
验证域名格式
|
|
|
|
:param domain: 域名
|
|
:return: bool - 是否有效
|
|
"""
|
|
try:
|
|
# 域名格式正则
|
|
pattern = r'^[a-zA-Z0-9][a-zA-Z0-9-]{0,61}[a-zA-Z0-9]\.[a-zA-Z]{2,}$'
|
|
return bool(re.match(pattern, domain))
|
|
except Exception as e:
|
|
logger.error(f"验证域名格式出错: {e}")
|
|
return False
|
|
|
|
|
|
def extract_tld(domain):
|
|
"""
|
|
提取顶级域名
|
|
|
|
:param domain: 域名
|
|
:return: str - 顶级域名
|
|
"""
|
|
try:
|
|
ext = tldextract.extract(domain)
|
|
return ext.suffix
|
|
except Exception as e:
|
|
logger.error(f"提取顶级域名出错: {e}")
|
|
return ''
|
|
|
|
|
|
def extract_domain(domain):
|
|
"""
|
|
提取主域名
|
|
|
|
:param domain: 域名
|
|
:return: str - 主域名
|
|
"""
|
|
try:
|
|
ext = tldextract.extract(domain)
|
|
if ext.domain and ext.suffix:
|
|
return f"{ext.domain}.{ext.suffix}"
|
|
return domain
|
|
except Exception as e:
|
|
logger.error(f"提取主域名出错: {e}")
|
|
return domain
|
|
|
|
|
|
def is_com_or_net(domain):
|
|
"""
|
|
检查是否为 .com 或 .net 域名
|
|
|
|
:param domain: 域名
|
|
:return: bool - 是否为 .com 或 .net 域名
|
|
"""
|
|
try:
|
|
tld = extract_tld(domain)
|
|
return tld in ['com', 'net']
|
|
except Exception as e:
|
|
logger.error(f"检查域名后缀出错: {e}")
|
|
return False
|
|
|
|
|
|
def generate_domain_variants(domain):
|
|
"""
|
|
生成域名变体
|
|
|
|
:param domain: 域名
|
|
:return: list - 域名变体列表
|
|
"""
|
|
try:
|
|
variants = []
|
|
|
|
# 原始域名
|
|
variants.append(domain)
|
|
|
|
# 添加 www
|
|
if not domain.startswith('www.'):
|
|
variants.append(f"www.{domain}")
|
|
|
|
# 移除 www
|
|
if domain.startswith('www.'):
|
|
variants.append(domain[4:])
|
|
|
|
return variants
|
|
except Exception as e:
|
|
logger.error(f"生成域名变体出错: {e}")
|
|
return [domain]
|
|
|
|
|
|
def parse_domain_status(status_code):
|
|
"""
|
|
解析域名状态码
|
|
|
|
:param status_code: 状态码
|
|
:return: str - 状态描述
|
|
"""
|
|
status_map = {
|
|
0: '待检测',
|
|
1: '可注册',
|
|
2: '已注册',
|
|
3: '宽限期',
|
|
4: '赎回期',
|
|
5: '删除期',
|
|
6: 'clientHold',
|
|
7: 'serverHold',
|
|
8: '状态未知',
|
|
9: '检测失败'
|
|
}
|
|
|
|
return status_map.get(status_code, '未知')
|
|
|
|
|
|
def parse_use_status(status_code):
|
|
"""
|
|
解析使用状态码
|
|
|
|
:param status_code: 状态码
|
|
:return: str - 状态描述
|
|
"""
|
|
status_map = {
|
|
0: '未使用',
|
|
1: '已经使用',
|
|
2: '已经卖出',
|
|
3: '已经预定'
|
|
}
|
|
|
|
return status_map.get(status_code, '未知')
|
|
|
|
|
|
def parse_detect_status(status_code):
|
|
"""
|
|
解析检测状态码
|
|
|
|
:param status_code: 状态码
|
|
:return: str - 状态描述
|
|
"""
|
|
status_map = {
|
|
0: '待检测',
|
|
1: '检测中',
|
|
2: '正常',
|
|
3: '黑名单',
|
|
4: '检测失败',
|
|
5: '暂停检测'
|
|
}
|
|
|
|
return status_map.get(status_code, '未知')
|
|
|
|
|
|
def parse_source_type(source_type):
|
|
"""
|
|
解析来源类型
|
|
|
|
:param source_type: 来源类型
|
|
:return: str - 来源描述
|
|
"""
|
|
source_map = {
|
|
1: '聚名一口价',
|
|
2: '聚名过期删除',
|
|
3: 'zone file',
|
|
4: '搜索引擎采集',
|
|
5: '企业目录采集',
|
|
6: '手工录入',
|
|
7: 'TXT 导入',
|
|
8: '第三方接口',
|
|
9: '其它'
|
|
}
|
|
|
|
return source_map.get(source_type, '未知') |