2021SC@SDUSC
目录
一、摘要
二、“souhu_new.py”文件核心代码分析
1.部分一
2.部分二
三、总结
一、摘要
本篇博客作为“SohuNewCrawler”项目核心代码分析的第二篇。我将从这篇开始对本项目的核心代码部分进行分析。
二、“souhu_new.py”文件核心代码分析
1.部分一
class SouhuSpider():
def __init__(self):
self.dburl = MongoUrl()
self.dbarticle = MongoArticle()
self.url_set = set()
self.url_queue = queue.Queue()
self.init_set()
def init_set(self):
url_list = self.dburl.select({"type": type_name})
for url in url_list:
self.url_set.add(url.get('url'))
def strf_time(self,timeStamp):
if timeStamp is None:
return datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S")
localTime = time.localtime(int(timeStamp)/1000)
strTime = time.strftime("%Y-%m-%d %H:%M:%S", localTime)
return strTime
class SouhuSpider():
def __init__(self):
self.dburl = MongoUrl()
self.dbarticle = MongoArticle()
self.url_set = set()
self.url_queue = queue.Queue()
self.init_set()
def init_set(self):
url_list = self.dburl.select({"type": type_name})
for url in url_list:
self.url_set.add(url.get('url'))
def strf_time(self,timeStamp):
if timeStamp is None:
return datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S")
localTime = time.localtime(int(timeStamp)/1000)
strTime = time.strftime("%Y-%m-%d %H:%M:%S", localTime)
return strTime
一开始的_init_函数是定义变量的初始值。MongoUrl和MongoArticle是来自“db.py”文件定义的类。
“db.py”文件是关于url链接的存储以及文章的相关操作。定义了部分数据库操作的函数。
插入的数据:{"url":"待爬取的新闻链接","time":'2019-05-03 01:32:00',"flag":是否被爬取标志0,"title":"标题","type":"新闻来源百度新闻"}
# db_mu.insert({"url":"http://www.baidu.com","time":'2019-05-03 01:32:00',"flag":0,"title":"暂无","type":"baidu_new百度新闻"}){"articel":"一段内容","flag":是否被导出,"time":"2019-05-03 01:32:00","title":"暂无","type":"新闻来源百度新闻","url":"新闻链接"}
# db_ma.insert({"articel":"一段过滤后的内容","flag":0,"time":"2019-05-03 01:32:00","title":"暂无","type":"baidu_new百度新闻","url":"http://www.baidu.com"})
dburl是表示待爬取的新闻链接。dbarticle表示文章。
url_set是创建了一个新的set集合,url_queue是创建了一个新的队列。
在爬虫程序中,为了不重复爬取已经爬过的页面,需要把已经爬过的页面的url放进集合中,在每一次要爬取某一个url之前,先看看集合里面是否已经存在,如果已经存在跳过这个url,如果不存在,则把url放进集合中,然后再去爬取这个页面。
python提供了set这种数据结构,set是一种无序的,不包含重复元素的结构,一般用来测试是否已经包含了某元素,或者对众多元素们去重复。它支持的运算有交、并、差、对称差。
def init_set(self):
url_list = self.dburl.select({"type": type_name})
for url in url_list:
self.url_set.add(url.get('url'))
该函数是通过调用dburl的查询方法在数据库中查询出url列表并保存为url_list,然后对这个url列表进行for循环,将该url添加到空的url_set集合中。
def strf_time(self,timeStamp):
if timeStamp is None:
return datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S")
localTime = time.localtime(int(timeStamp)/1000)
strTime = time.strftime("%Y-%m-%d %H:%M:%S", localTime)
return strTime
该函数返回一个时间戳,返回的是当前的时间。
2.部分二
def req_json(self):
while True:
start_url = self.url_queue.get()
try:
req = requests.get(url=start_url, timeout=30)
if req.status_code != 200:
print('网站拒绝访问')
souhu_json = req.json()
news_header_list = souhu_json.get('data')
if news_header_list:
for per_new in news_header_list:
if not per_new.get("url"):
continue # 没有url则继续下一个
if urlparse(per_new.get('url')).scheme == 'https':
continue # 没有http则是广告
url = parse.urljoin('http://m.sohu.com', per_new.get("url"))
title = per_new.get("title")
publicTime = per_new.get("publicTime")
url_time = self.strf_time(publicTime)
while True:
start_url = self.url_queue.get()
try:
req = requests.get(url=start_url, timeout=30)
if req.status_code != 200:
print('网站拒绝访问')
souhu_json = req.json()
news_header_list = souhu_json.get('data')
在url队列中获取一个url作为开始的url(start_url),然后对该url对应的网站进行爬取操作,若网站的HTTP状态码不为200,则表示网站拒绝访问。若网站正常访问,将爬取的网站内容转换成json格式,将json格式中的‘data’获取为新闻头(news_header)列表。
if news_header_list:
for per_new in news_header_list:
if not per_new.get("url"):
continue # 没有url则继续下一个
if urlparse(per_new.get('url')).scheme == 'https':
continue # 没有http则是广告
遍历news_header列表,找出那些符合规则的。若没有url则继续下一个,若没有http则表示为广告。
url = parse.urljoin('http://m.sohu.com', per_new.get("url"))
title = per_new.get("title")
publicTime = per_new.get("publicTime")
url_time = self.strf_time(publicTime)
parse.urljoin将‘http://m.sohu.com’与后面的‘url’结合起来转为完整的url。
python中urlparse.urljoin()的用法:
以response.url为基础,将URL相对路径转换为URL绝对路径。例如:
>>>from urllib.parse import urljoin
>>> urljoin("http://www.chachabei.com/folder/currentpage.html", "anotherpage.html")
'http://www.chachabei.com/folder/anotherpage.html'
遍历的news_header_list的title作为标题“title”,时间设为news_header_list的publicTime。
三、总结
本次通过分析部分核心代码,对该项目的了解更加深入了,也收获了不少爬虫的相关函数及知识,受益匪浅。
我将在下一篇继续分析本项目的核心代码。



