基于机器学习的违法网站识别

admin 2022年10月19日18:38:58基于机器学习的违法网站识别已关闭评论63 views字数 8052阅读26分50秒阅读模式

1 背景描述

工作中需要对违法网站进行监管处置,在拿到ip清单和网站域名清单后产生了写一个ai模型来自动探测此类违法网站的想法,进而能够实现自动化检测、智能化发现的目的。从翻看论文到理论实现,再到编程调参,前前后后也断断续续了搞了几个月,目前也初步能够满足先前的想法需求。

2 违法网站定义

我理解的违法网站其实分为两类,一类是暗链,一类是明链
暗链是指在网站title、meta中插入违法关键词,从而实现seo的提升和特定访问渠道的跳转,一般来说从页面上看没有任何异样,但是在访问源代码,或者通过百度形式浏览的时候则很容易发现。
基于机器学习的违法网站识别
明链则是在直接在网站中插入跳转语句,实现违法网站的跳转和访问,或者直接将违法页面通过js形式嵌入在原网站中,这种一般比较简单粗暴,也易于发现。

3 检测算法

在前期翻看论文时,发现已有此类对于违法网站识别的比赛,也吸取了部分前人的经验,实验的是主要是两种算法,一种是tfidf,一种是doc2vec。但是做数据抽取都是一样的,下面先介绍数据抽取的方法。
作为数据抽取,那自然是要选择能够跟最终判定直接影响的数据,结合前面的暗链和明链的定义,违法内容和网站域名高发的几个点有title,meta,a,link等标签,因此直接xpath抽取相应标签内容即可。

<span class="n">rule</span> <span class="o">=</span> <span class="n">s</span><span class="o">.</span><span class="n">xpath</span><span class="p">(</span><span class="s1">'//title/text()'</span><span class="p">)</span><span class="o">.</span><span class="n">extract</span><span class="p">()</span>

    <span class="n">rule</span> <span class="o">=</span> <span class="n">s</span><span class="o">.</span><span class="n">xpath</span><span class="p">(</span><span class="s1">'//meta/@content'</span><span class="p">)</span><span class="o">.</span>extract()

    rule += s.xpath('//a/text()').extract()  

    rule += s.xpath('//a/@title').extract()

    rule += s.xpath('//link/@title').extract()

那么抽取之后,我们就能够得到一串跟违法网站和违法域名相关的关键词组,进而对关键词组进行精细化筛选,去除特殊符号。

new_rule = ''.join(re.findall(u'[a-zA-Z0-9\u4E00-\u9FA5]',''.join(rule)))

这里对所有关键词进行了连接,下面就要进行语句分词,把一个整句按照中文格式,拆分为动名词。同时需要注意的是停顿词的处理,会有大量的“虽然”、“但是”、“并且”等无关违法内容识别的单词,在停顿词处理时都要一并考虑,同时结合工作性质,集合了一个针对不同违法类型的关键词库,如涉黄、涉枪、涉爆等。
那么这里需要先对关键词库进行jieba分词,如“威尼斯娱乐”拆分下来就是“威尼斯”、“娱乐”等,其他同理,这里有很多先前的比赛参赛者没有这样的数据,都是在后续检测时通过tfidf值排序,来构建的违法关键词库,人工核验量较大,但是也不失为一种比较好的方法。
在得到违法关键词库和停顿词库后,开始对获取的网页内容进行分词。

##将违法关键词加入到jieba库中,能够精准按照关键词库进行分词

fp = open('blackword.txt','r')

blackword = [x.strip().encode('unicode_escape') for x in fp.readlines()]

#print blackword

for x in blackword:

    jieba.suggest_freq(x.decode('unicode_escape'),True)

fp.close()

在具体实践过程中,发现某些域名或者html字符在对特殊字符去除后,可能会形成超长字符串,如一个正常的域名和访问请求,在去除“.”符号之后,就会变成wwwbaiducomaaaaqwe等这种无意义的字符串,或者变成一串无意义的超长数字或者字母,针对这种情况,通过机器长度判定只抽取长度适中,有统计代表性的分词。

word = jieba.cut(new_rule)

new_word = []

for x in word:

    if x not in stpwrdlst and len(x) > 1 and len(x) < 10 and not re.search(r'^[0-9]*$',x):

        new_word.append(x)

那么至此,我们就能够形成一个网站的唯一文字标识,下面从某一个违法的页面来模拟这个流程。
一是获取特定标签内容,来作为数据抽取的来源。

[u'text/html; charset=gb2312', u'http://45.116.161.82:886/logo.jpg', u'\u5f69\u7968\u5927\u8d62\u5bb6', u'\u5f69\u7968\u5927\u8d62\u5bb6\u5b98\u7f51\u2705\u3010www.401078.com\u3011\u2705\u25b2\u514d\u8d39\u8bd5\u73a9\u25b2\u514d\u8d39\u9886\u7ea2\u5305\u25b2\u514d\u8d39\u804a\u5929\u5ba4  \u770b\u8ba1\u5212,\u5168\u529b\u6253\u9020\u5f69\u754c\u6700\u5feb\u3001\u6700\u7a33\u7684\u6295\u6ce8\u5e73\u53f0,\u5e73\u53f0\u8d85\u5b89\u5168,\u5145\u63d0\u66f4\u4fbf\u6377,\u63d0\u6b3e\u79d2\u5230\u8d26\u3002', u'\u8fdb\u5165\u7f51\u7ad9', u'\u5173\u4e8e\u6211\u4eec', u'\u4f01\u4e1a\u8363\u8a89', u'\u4ea7\u54c1\u5c55\u793a', u'\u65b0\u95fb\u52a8\u6001', u'\u5728\u7ebf\u54a8\u8be2', u'\u8054\u7cfb\u6211\u4eec']

二是对抽取数据进行连接,将其作为判定标识

texthtmlcharsetgb2312http4511616182886logojpg彩票大赢家彩票大赢家官网www401078com免费试玩免费领红包免费聊天室看计划全力打造彩界最快最稳的投注平台平台超安全充提更便捷提款秒到账进入网站关于我们企业荣誉产品展示新闻动态在线咨询联系我们

三是通过jieba分词和停顿词处理来获得规范化数据

彩票 大赢家 彩票 大赢家 官网 免费 试玩 免费 红包 免费 聊天室 计划 打造 彩界 最快 最稳 投注 平台 平台 安全 充提 便捷 提款 进入 网站 企业 荣誉 产品 展示 新闻动态 在线 咨询 联系

到这里已经初见端倪,其中不断重复出现着“彩票”、“大赢家”、“投注”等平台字样。

3.1 TFIDF

我理解的tfidf通俗来将就是根据单词的出现频率来判定一个网页是否违法,如不断出现“彩票”、“投注”等字样可能就会判定为违法网站,不断出现“学习”、“健康”等正面字样就会判定为非违法网站。
这里ngram_range首选是(1,1),主要考虑有两点,一是的确识别效率快,二是不想掺和太多因素在识别上面,就以单个文字说话。

CV = CountVectorizer(ngram_range=(1,1), decode_error="ignore", min_df=0.05, max_df=0.7)

x = CV.fit_transform(x_all).toarray()

transformer = TfidfTransformer(smooth_idf=False)

x_tfidf = transformer.fit_transform(x)

x = x_tfidf.toarray()

3.2 doc2vec

doc2vec是后来看到别人用的算法,在认真看过文档之后也觉得此类算法可能在效率和识别准确率上更好,但是在实践过程优势不是特别明显。
我理解doc2vec比tfidf好的就是他的CBOW模型,大概意思就是当单词跟单词之间有了上下文关系,且多组单词可以代表同一个含义,如“彩票 大赢家 彩票 大赢家 官网”指向的就是涉赌,其他也是类似。

max_features = 1000

x_train = labelizeReviews(x_train, 'TRAIN')

x_test = labelizeReviews(x_test, 'TEST')

x = x_train + x_test

cores = multiprocessing.cpu_count()

model = Doc2Vec(dm=0, vector_size=max_features, window=40, negative=20, min_count=5, sample=1e-5, hs=0, workers=cores, epochs=40)

model.build_vocab(x)

model.train(x, total_examples=model.corpus_count, epochs=model.epochs)

model.save(doc2ver_bin)

4 识别效率

选取的黑白样本,黑样本是网上公开获取,白样本是dmoz网站爬取,后来机器不断发现新的违法网站,有时候没事就会人工判定,往黑白样本库里面添加,导致现在的识别率没先前那么高了,最终黑样本是1575个,白样本是5256个。

rf...

metrics.accuracy_score:

0.9626783754116356

metrics.confusion_matrix:

[[2031   71]

[  31  600]]

metrics.precision_score:

0.8941877794336811

metrics.recall_score:

0.9508716323296355

metrics.f1_score:

0.9216589861751152

可以看到使用tfidf存疑的矩阵还是蛮多的,这是因为有些模型判定为非正常网站,经人工核对后会将其扔进白网站库里,导致准确率下降,不过因为是偏实战应用,不是为了论文,所以具体指标不纠结。

xgboost and doc2vec

metrics.accuracy_score:

0.9604885057471264

metrics.confusion_matrix:

[[2107   47]

[  63  567]]

metrics.precision_score:

0.9234527687296417

metrics.recall_score:

0.9

metrics.f1_score:

0.9115755627009646

5 存在不足

最终经过抉择和实战,选择的是tfidf算法,原因是在数据抽取过程中,抽取的并不是单一的违法网页,而是网页的所有内容,这就会导致网页内容其实十分掺杂,有非法的和大量合法的,如果是选用doc2vec算法,那么针对暗链,在后续的关键词相似率识别判定上,大量合法关键词的聚集拉高了整体相似率,从而在判定暗链上出现较大偏差。
而选用tfidf其实也会存在问题,如存在暗链的网站一般都是以机械类为主,导致大量机械类术语被拉入黑名单,从而导致误报,而涉黄类视频和app也会导致影视网站进入误报,虽然有些影视网站的确在打擦边球,但是需要人为判定,无法做到精准识别。总的来说,暗链与明链的识别上的确需要区别对待,那样可能检测效果会更好。

上述如有不当之处,敬请指正。

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2022年10月19日18:38:58
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   基于机器学习的违法网站识别https://cn-sec.com/archives/1358422.html