美文网首页
requests爬取网页的通用框架

requests爬取网页的通用框架

作者: sbill | 来源:发表于2017-12-29 09:34 被阅读0次

    概述

    代码编写完成时间:2017.12.28
    写文章时间:2017.12.29


    看完中国大学MOOC上的爬虫教程后,觉得自己之前的学习完全是野蛮生长,决定把之前学的东西再梳理一遍,主要是觉得自己写的程序和老师写的差别太大,有很多学习的地方,决定用老师所教的和自己已有的知识融合,形成新的知识。
    爬虫的第一步当然获取到网页,所以可以专门写一个程序来获取网页,以后对此进行不断改进就行,不必重复制造轮子。


    准备

    此程序用到的库主要是requests库,还有现在的网站一般都有反爬虫措施,最常见的是检查浏览器的头部信息,所以对头部信息进行伪装的操作可以说是很必要的,为此可以引入fake_useragent库,引入:

    from fake_useragent import UserAgent
    import requests
    

    编写

    对爬取网页代码的编写,一般都用requests的get方法对网页进行访问,对于get方法,为了反爬虫和良好的体验,可以增加一些参数来增加约束:
    response = requests.get(url, headers=headers, timeout=10)
    发现对百度首页的爬取增不增加头部信息返回的内容是不一样的,增加了之后可以明显看到返回的内容变多和排版更加人性化。
    然后要返回text属性所包含的内容,还有一个很重要的网页编码问题,如果编码设置的不对,那么返回的text可能是乱码,因为现在国际上一般都使用UTF-8编码,所以我直接令网页的编码为UTF-8:

    response.encoding = 'utf-8'
    

    其实按照老师的写法是这样的:

    response.encoding = response.apparent_encoding
    

    但这样每次都要根据网页的源代码对编码进行判断,无疑是要花费一点时间的,干脆使用UTF-8这个万金油省事,反正requests一般都是用来爬取单个网站的内容,编码不对再改就行了,没什么大不了的。
    现在基本上能完成对静态网页的访问并返回源代码了。


    优化

    没看视频之前,我就是写到上面那一步之后就收工了,因为完成了基本功能嘛,但是通过和老师的学习,我知道这样使不行的,因为这样的代码不够健壮,出错了就直接崩溃,现在代码量少没有关系,但是以后代码量大了,就会有很大的麻烦,所以这是非常不好的习惯,好的程序应该有良好的对异常处理功能,然后我引入可能发生的异常:
    from requests import Timeout, HTTPError
    Timeout是可能请求超时的异常,因为校园网不稳定,这种情况是十分常见的;HTTPError是请求HTTP页面的时候可能发生的异常,比如常见的404错误。
    下面是改进的代码:

    from fake_useragent import UserAgent
    import requests
    from requests import Timeout, HTTPError
    
    ua = UserAgent()    #能够获得浏览器种类信息的实例
    
    def get_page(url):
        try:
            headers = {'User-Agent':ua.random}  #随机获得头部信息
            response = requests.get(url, headers=headers, timeout=10)
            response.raise_for_status()
            response.encoding = 'utf-8'
            return response.text
        except Timeout:
            print('requests timeout')
            get_page(url)
        except HTTPError:
            print('the http error(maybe status is not 200)')
        except:
            print('other error')
    
    url = 'https://www.baidu.com/'
    html = get_page(url)
    print(html)
    

    通过上述代码,除了捕获引入的两个异常外,为了保险起见,把其他的所有异常就统一进行了处理,对于超时异常,就递归调用,重新访问;还有对返回的response增加了一行代码判断:

    response.raise_for_status()
    

    作用是如果返回的状态码不是正常的200,就抛出HTTP错误。
    一些网页不能正常访问也返回200状态码,真是有毒,这个有点无解,目前除了人工判断,还没有其他办法。


    总结

    一个简单的获取网页的框架的代码已经完成了,虽然比较“寒酸”,但基本功能也有了,也有对一些异常的处理,健壮性提升了一点,直觉上觉得还有许多不足,但是我相信,随着不断地进步,此程序就可以变得更加完善的。

    相关文章

      网友评论

          本文标题:requests爬取网页的通用框架

          本文链接:https://www.haomeiwen.com/subject/awnbgxtx.html