导出我的豆瓣电影列表

这个看上去好像是个奇怪的需求,但我个人还是挺需要的。有时候我想找的其实只是自己看过的列表,而豆瓣的搜索就算我给了关键词我标记过的电影排序并不会在前面。一开始也没有在意,在小众看到有人提供了网页服务,除了速度有点慢的离谱,其他基本能满足需求了。

最近刚好有兴趣,想着自己折腾下直接网页爬的话也更快些,而且自己可以定制自己要的,顺便熟悉下一些包的使用。

# -*- coding: utf-8 -*-
import requests
from pyquery import PyQuery as pq
import xlwings as xw

userid = '38278418'
url = 'https://movie.douban.com/people/{}/collect'.format(userid)

page = requests.get(url)
d = pq(page.text)
pagenum = int(d('.paginator>a:last').text())
res = []
for num in range(pagenum):
    newurl = url + '?start={}&sort=time&rating=all&filter=all&mode=grid'.format(num*15)
    page = requests.get(newurl)
    d = pq(page.text)
    for each in d('.grid-view .item').items():
        detail = [each('.title a').text(), each('.title a').attr('href'), each('.intro+li span:eq(0)').attr('class')[6], each('.tags').text()[4:], each('.comment').text()]
        res.append(detail)
    # if num == 1:
    #     break
# print(res)

wb = xw.Book()
xw.Range('A1').value = ['片名', '评分', '标签', '短评']
length = len(res)
for i in range(length):
    xw.Range('A{}'.format(i+2)).add_hyperlink(res[i][1], text_to_display = res[i][0])
xw.Range('B2:D{}'.format(length+1)).value = [i[2:] for i in res]

wb.save('movie.xlsx')

requests 库不用说,pyquery 提取页面还是挺有意思的,数据导出成 excel 用的 xlwings 有些头大,用的挺难看的。

一直想试试 pyspider ,这次正好搞定它。终于明白以前坑在哪里了,0.3.8 说是修复了windows的一个问题其实还是不行,老版本的0.3.7居然可以?蛋碎,其实锅还是 windows 的,既然搞定了就不弄虚拟机了。pyspider 爬虫就很简单了,直观明了方便,感谢 binux 。顺便提下,在线的 demo 我失败的页面挺多的,所以还是本地运行为好。有些依赖包如 lxml、pycurl ,pip 安装不了,记得去 http://www.lfd.uci.edu/~gohlke/pythonlibs/ 下载。

from pyspider.libs.base_handler import *

class Handler(BaseHandler):
    crawl_config = {
    }

    @every(minutes=24 * 60)
    def on_start(self):
        self.crawl('https://movie.douban.com/people/38278418/collect', callback=self.index_page)

    @config(age=10 * 24 * 60 * 60)
    def index_page(self, response):
        for each in response.doc('.next a').items():
            self.crawl(each.attr.href, callback=self.index_page)
        res = []
        for each in response.doc('.grid-view .item').items():
            detail = [each('.title a').text(), each('.title a').attr('href'), each('.intro+li span:eq(0)').attr('class')[6], each('.tags').text()[4:], each('.comment').text()]
            res.append(detail)
        return res

数据可以 json 导出的,我也没在程序里折腾数据了,毕竟这个量级的爬虫用 pyspider 有点大材小用了。