针对现代网络钓鱼攻击的高频与隐蔽特性,本文提出了一种基于高斯朴素贝叶斯(Gaussian Naive Bayes)的自动化识别模型,并引入特征标准化流水线(Standardization Pipeline)解决了多量纲数值特征导致的预测偏差问题。实验采用包含 23.5 万样本的 PhiUSIIL 数据集,通过对 54 项 URL 维度特征的深度挖掘与预处理优化,模型在测试集上表现卓越。结果显示,优化后的流水线模型召回率(Recall)保持在 99.96%,误报数(False Positives)从原始数据的 687 例锐减至 17 例,ROC-AUC 达到 0.9998。该研究证明了轻量级生成式模型在经过严格特征工程处理后,能够在大规模实时检测场景中兼顾高精度与低延迟。
算法理论基础
高斯朴素贝叶斯原理
朴素贝叶斯分类器基于条件独立性假设,即给定类别 $y$,各特征 $x_i$ 相互独立。其分类决策依据后验概率最大化原则:
$$\hat{y} = \arg\max{y} P(y) \prod{i=1}^n P(x_i|y)$$
对于连续型特征,本研究采用高斯概率密度函数:
$$P(x_i | y) = \frac{1}{\sqrt{2\pi\sigma_y^2}} \exp\left( -\frac{(x_i – \mu_y)^2}{2\sigma_y^2} \right)$$
其中 $\mu_y$ 和 $\sigma_y$ 分别是类别 $y$ 对应特征的均值和标准差。该模型的参数量级与特征维度呈线性关系,具有极高的计算效率。
特征工程与实验设计
数据集与特征
实验使用 PhiUSIIL Phishing URL (Website) 数据集,该数据集提取了 56 项关键特征,主要分为以下四个维度:
URL 静态结构特征
- 基础维度:包括
URLLength、DomainLength、TLDLength等,用于识别异常长的混淆域名。 - 混淆度分析:
IsDomainIP(检测是否直接使用IP作为域名)、CharContinuationRate(字符连续率)、NoOfObfuscatedChar(混淆字符数)以及ObfuscationRatio(混淆比例)。这些特征直接反映了攻击者逃避视觉审查的手段。
统计概率特征
- 信誉建模:
TLDLegitimateProb(顶级域名合法概率)和URLCharProb(字符概率分布)。通过统计学方法量化 URL 与已知安全域名的偏离度。 - 复杂度特征:
NoOfLettersInURL、NoOfDegitsInURL及其对应的比例(Ratio),用于捕捉非典型字符分布。
页面内容与行为特征
- 前端代码统计:
LineOfCode(代码行数)、LargestLineLength(最长行长度),反映页面复杂程度。 - 语义一致性:
DomainTitleMatchScore和URLTitleMatchScore,衡量域名与页面标题的相关性。恶意网站往往通过不匹配的标题来蹭热度或误导。 - 交互逻辑:
NoOfURLRedirect(跳转次数)、NoOfPopup(弹窗数)、NoOfiFrame(框架嵌套数)以及HasExternalFormSubmit(是否存在跨域表单提交)。这些特征是判断钓鱼页面行为的核心指标。
行业敏感度特征
- 关键词倾向:
Bank、Pay、Crypto等布尔特征,标记页面是否涉及金融或加密货币,显著提升了对高风险钓鱼页面的识别权重。
预处理流水线设计
在 56 个特征中,FILENAME、URL、Domain、TLD 和 Title 属于文本元数据(Metadata),不直接参与数学运算。本研究设计的流水线流程如下:
特征剥离:将上述文本字段提取为辅助审计信息,仅保留 50 个数值特征输入模型。
标准化:
由于 LineOfCode(数值可达数千)与 IsHTTPS(0或1)量纲差异巨大,流水线通过下式将所有特征拉回同一尺度:
$$z = \frac{x – \mu}{\sigma}$$
分层抽样:确保模型在 label(标签项)分布上保持训练与测试的一致性。
代码实现
完整代码参见:Malicious-Website-Detection
为了确保实验的可重复性及生产环境的兼容性,项目通过 config.py 实现了路径与参数的解耦。特别地,通过 METADATA_COLS 显式定义了非计算类字段,确保模型输入层的高度纯净。核心代码如下所示:
# 基础路径配置
BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
DATA_PATH = os.path.join(BASE_DIR, 'data', 'PhiUSIIL_Phishing_URL_Dataset.csv')
MODEL_SAVE_PATH = os.path.join(BASE_DIR, 'saved_models')
# 实验参数配置
RANDOM_STATE = 42 # 随机种子,固定此数值可保证每次运行的数据拆分结果一致
TEST_SIZE = 0.2 # 测试集占比 20%
# 数据列配置
# 标签列:1代表合法,0代表钓鱼
LABEL_COL = 'label'
# 元数据列:不参与数学计算的文本信息
METADATA_COLS = ['FILENAME', 'URL', 'Domain', 'TLD', 'Title']
在复杂的机器学习流水线中,最佳实践是将数据读取与数据转换分离。编写了 get_raw_splits() 函数,其核心目标是保持数据的“原始性”,将所有数值变换(如标准化)留给后续的 Pipeline 统一处理,从而避免训练集信息泄露给测试集。核心代码如下所示:
def get_raw_splits():
"""
仅负责基础的数据加载和分层拆分,保持数据的原始性。
预处理步骤将由后续的 Pipeline 统一管理。
"""
# 读取原始数据
df = pd.read_csv(DATA_PATH)
# 特征选择:剔除非数值文本列和标签列
# drop函数用于删除指定的列
X = df.drop(columns=METADATA_COLS + [LABEL_COL])
y = df[LABEL_COL]
# 数据拆分
# stratify=y 确保训练集和测试集中0和1的比例与原始数据一致
X_train, X_test, y_train, y_test = train_test_split(
X, y,
test_size=TEST_SIZE,
random_state=RANDOM_STATE,
stratify=y
)
return X_train, X_test, y_train, y_test, df
main() 函数定义了从数据输入到模型落地(Production-ready)的完整生命周期。通过 Pipeline 架构,我们确保了模型在训练和预测时使用完全一致的逻辑。
def main():
# 1. 获取原始拆分数据
# 调用前期定义的模块,确保数据分层抽样
X_train, X_test, y_train, y_test, raw_df = get_raw_splits()
# 2. 构建流水线 (Pipeline)
# Pipeline 将多个评估器组合成一个。这在处理流程时非常有用。
pipeline = Pipeline([
('scaler', StandardScaler()), # 特征标准化
('nb_classifier', GaussianNB()) # 核心算法:高斯朴素贝叶斯
])
# 3. 训练流水线
# 这一步会按顺序执行流水线中的所有步骤(先转换数据,再训练模型)
print("正在通过流水线训练模型...")
pipeline.fit(X_train, y_train)
# 4. 执行预测
y_pred = pipeline.predict(X_test)
y_prob = pipeline.predict_proba(X_test)[:, 1]
# 5. 指标评估
# 调用 evaluate_model 打印 Precision, Recall, F1 等核心指标
evaluate_model(y_test, y_pred, y_prob, model_name="Gaussian Naive Bayes V1.0")
# 6. 错误追溯分析 (Error Analysis)
# 通过将预测结果对齐原始 DataFrame,筛选出漏报(FN)和误报(FP)样本
fn_df, fp_df = get_error_analysis(X_test, y_test, y_pred, raw_df)
print(f"\n[分析] 漏报样本数 (FN): {len(fn_df)} | 误报样本数 (FP): {len(fp_df)}")
# 7. 整体持久化
if not os.path.exists(MODEL_SAVE_PATH):
os.makedirs(MODEL_SAVE_PATH)
# 注意:保存的是整个 pipeline,而不仅仅是模型权重
save_path = os.path.join(MODEL_SAVE_PATH, "phish_nb_v1.pkl")
joblib.dump(pipeline, save_path)
print(f"\n实验结束,包含预处理逻辑的完整流水线已保存至: {save_path}")
实验结果与误差分析
评价指标体系定义
在恶意网站识别的二分类任务中,单纯的准确率(Accuracy)往往无法真实反映模型在处理样本极度不平衡(如合法网站远多于钓鱼网站)时的防御能力。因此,本文引入以下多维度评估指标:
混淆矩阵
混淆矩阵 (Confusion Matrix) 是评估分类模型性能的最基础工具,其四个核心维度定义如下:
- 真正例 (True Positive, TP):模型正确判定为“钓鱼网站”的样本数。
- 真负例 (True Negative, TN):模型正确判定为“合法网站”的样本数。
- 假正例 (False Positive, FP):模型将“合法网站”误报为“钓鱼网站”的数量(即误报)。
- 假负例 (False Negative, FN):模型将“钓鱼网站”误判为“合法网站”的数量(即漏报)。
精确率
精确率 (Precision) 衡量模型预测为“恶意”的样本中,有多少是真实的恶意网站:
$$Precision = \frac{TP}{TP + FP}$$
安全意义:高精确率意味着安全告警的真实性高,减少了对正常访问的干扰(低误报)。
召回率
召回率 (Recall / Sensitivity) 衡量在所有真实的恶意网站中,模型成功捕捉到的比例:
$$Recall = \frac{TP}{TP + FN}$$
安全意义:Recall 是识别系统的核心指标,Recall 为 1.00 意味着模型几乎没有“漏网之鱼”。
F1-Score
F1 分数是精确率和召回率的调和平均数:
$$F1 = 2 \times \frac{Precision \times Recall}{Precision + Recall}$$
它综合平衡了误报与漏报,是衡量模型整体稳健性的核心指标。
支持数
支持数 (Support) 指的是在测试集中每个类别对应的真实样本数量。在本文实验中,Phishing (0) 的 Support 为 20,189,Legitimate (1) 的 Support 为 26,970。通过 Support 可以观察数据集是否存在类别倾斜。
ROC 曲线与 AUC 得分
- ROC 曲线:以假正率(FPR)为横轴,真正率(TPR,即 Recall)为纵轴绘制的曲线。
- AUC (Area Under Curve):指 ROC 曲线下的面积。
- $AUC = 1$:理想模型,完美区分。
- $AUC = 0.5$:等同于随机猜测。
实验结果
预处理对模型性能的增益分析
为了量化特征标准化(Standardization)对高斯朴素贝叶斯算法的具体贡献,本研究记录了数据在标准化前后的详细评估指标。实验结果表明,预处理流水线对消除特征量纲偏差、优化决策边界具有极其显著的作用。
标准化前后的实验数据对比
通过对比 Baseline(未处理)与 Pipeline(标准化)实验,结果如下:
下表展示了模型在 56 个原始特征下(未标准化)与经过标准化流水线处理后的性能表现:
| 实验组别 | 类别 | Precision | Recall | F1-Score | Support | Accuracy | AUC |
|---|---|---|---|---|---|---|---|
| 未标准化 (Baseline) | Phishing (0) | 0.97 | 1.00 | 0.98 | 20189 | 0.99 | 0.9998 |
| Legitimate (1) | 1.00 | 0.97 | 0.99 | 26970 | |||
| 标准化后 (Proposed) | Phishing (0) | 1.00 | 1.00 | 1.00 | 20189 | 1.00 | 0.9998 |
| Legitimate (1) | 1.00 | 1.00 | 1.00 | 26970 |
在未进行标准化的 Baseline 实验中,Phishing 类的 Precision 仅为 0.97,这意味着在识别出的恶意网站中存在约 3% 的误报(主要由 Legitimate 类的 0.97 Recall 引起)。经过标准化预处理后,所有指标均收敛至 1.00。这一转变证明,通过 Z-Score 标准化,模型成功修正了因部分高数值特征(如 LineOfCode 或 LargestLineLength)产生的概率偏移,使模型在保持极高检测灵敏度的同时,几乎消除了“冤假错案”。
值得注意的是,在两组实验中,Phishing (0) 类的 Recall 始终保持在 1.00。这表明高斯朴素贝叶斯算法配合 56 个多维度特征(特别是 URLSimilarityIndex 和 HasPasswordField 等强特征),对钓鱼网站的特征捕获具有天然的鲁棒性。无论数据如何平移缩放,模型都能稳健地识别出潜在的恶意威胁。
标准化后的 F1-Score 达到 1.00,标志着模型在精确率与召回率之间达到了完美的平衡点。ROC-AUC 得分稳定在 0.9998,反映出模型在不同判定阈值下均具有极强的类分离度。
结论
在基于高斯朴素贝叶斯的恶意网站识别体系中,特征标准化流水线是必要项。通过简单的线性变换,我们不仅将模型的准确率提升至极致,更重要的是证明了轻量级算法在数据质量得到保证的前提下,完全有能力应对复杂的网络安全分类任务。