- 本书赞誉
- 前言
- 目标读者
- 不适合阅读本书的读者
- 本书结构
- 什么是数据处理
- 遇到困难怎么办
- 排版约定
- 使用代码示例
- 致谢
- 第 1 章 Python 简介
- 第 2 章 Python 基础
- 第 3 章 供机器读取的数据
- 第 4 章 处理 Excel 文件
- 第 5 章 处理 PDF 文件 以及用 Python 解决问题
- 第 6 章 数据获取与存储
- 第 7 章 数据清洗:研究、匹配与格式化
- 第 8 章 数据清洗:标准化和脚本化
- 第 9 章 数据探索和分析
- 第 10 章 展示数据
- 第 11 章 网页抓取:获取并存储网络数据
- 第 12 章 高级网页抓取:屏幕抓取器与爬虫
- 第 13 章 应用编程接口
- 第 14 章 自动化和规模化
- 第 15 章 结论
- 附录 A 编程语言对比
- 附录 B 初学者的 Python 学习资源
- 附录 C 学习命令行
- 附录 D 高级 Python 设置
- 附录 E Python 陷阱
- 附录 F IPython 指南
- 附录 G 使用亚马逊网络服务
- 关于作者
- 关于封面
13.3 使用 Twitter REST API 进行高级数据收集
从 Twitter 拉取单个数据文件并不是非常有用,因为这只返回大约 15 条推文。我们希望执行一连串的查询,这样可以收集尽可能多的关于这一话题的推文。我们会使用另外一个库来做这项工作——Tweepy。Tweepy 可以管理一系列的请求,包括 Twitter 的 OAuth。首先安装 tweepy:
pip install tweepy
在脚本的最开始,导入 tweepy,并且再一次设置你的 key:
import tweepy API_KEY = '5Hqg6JTZ0cC89hUThySd5yZcL' API_SECRET = 'Ncp1oi5tUPbZF19Vdp8Jp8pNHBBfPdXGFtXqoKd6Cqn87xRj0c' TOKEN_KEY = '3272304896-ZTGUZZ6QsYKtZqXAVMLaJzR8qjrPW22iiu9ko4w' TOKEN_SECRET = 'nsNY13aPGWdm2QcgOl0qwqs5bwLBZ1iUVS2OE34QsuR4C'
之后将你的 API key 和 API secret 传入 tweepy 的 OAuthHandler 对象,这个对象会管理上一个实际提到的 OAuth 协议。之后设置你的访问 token。
auth = tweepy.OAuthHandler(API_KEY, API_SECRET) ➊ auth.set_access_token(TOKEN_KEY, TOKEN_SECRET) ➋
❶ 创建一个对象,通过 tweepy 来管理 API 认证。
❷ 设置访问 token。
之后,将刚刚创建的认证对象传递给 tweepy.API:
api = tweepy.API(auth)
tweepy.API 对象可以接受不同的参数,这给了你请求数据时控制 tweepy 行为的能力。你可以通过传递参数(像 retry_count=3, retry_delay=5)直接添加重试和延迟。另一个有用的选项是 wait_on_rate_limit,这个选项会直到频率限制解除后再去做下一次请求。 tweepy 文档(http://docs.tweepy.org/en/latest/api.html)中有这些选项的细节和更多信息。
我们想要使用 tweepy.Cursor 创建一个和 Twitter API 的连接。然后将 API 方法(这里是 api.search,http://docs.tweepy.org/en/latest/api.html#API.search)和与其相关的参数传递给指针(cursor)。
query = '#childlabor' ➊ cursor = tweepy.Cursor(api.search, q=query, lang="en") ➋
❶ 创建 query 变量。
❷ 使用 query 创建 cursor,并且限制其只检索英语。
尽管 Cursor 并不是很直观,但是这是一个在数据库连接中很常用的编程名词。虽然 API 不是数据库,但类名称 Cursor 可能受 API 类似数据库使用方式的影响而命名。你可以在维基百科(https://en.wikipedia.org/wiki/Cursor_(databases))上阅读更多关于指针的内容。
根据 tweepy 的文档(http://tweepy.readthedocs.org/en/latest/api.html),cursor 可以返回一个在单个对象级别或单页对象级别上的迭代器。你同样可以定义限制(http://tweepy.readthedocs.io/en/latest/cursor_tutorial.html#limits),来确定 cursor 抓取的页面数或对象数。如果查看 print(dir(cursor)),你会看到这里有 3 个方法:['items', 'iterator', 'pages']。一页返回一串对象,即在你的查询下独立的推文。根据需要,我们会使用页面。
让我们遍历这些页面,并且保存数据。在此之前,需要做以下两件事。
(1) 添加 import json 到脚本的顶端。
(2) 在脚本的相同目录下,创建一个名叫 data 的文件夹。为此,在命令行中运行 mkdir data。
一旦你完成了这两件事情,运行下面的代码来遍历和保存推文:
for page in cursor.pages(): ➊ tweets = [] ➋ for item in page: ➌ tweets.append(item._json) ➍ with open('data/hashchildlabor.json', 'wb') as outfile: ➎
❶ 对于每一个 cursor.pages() 返回的页面……
❷ 创建一个空列表来保存推文。
❸ 对于页面中的每一个对象(或推文)……
❹ 抽取 JSON 推文数据,保存到推文列表中。
❺ 打开一个名为 hashchildlabor.json 的文件,保存这些推文。
你会注意到,没有保存太多的推文到文件。每个页面只有 15 个推文,所以我们需要找出一个方法来得到更多的数据。有以下一些选项。
· 打开一个文件,并且永远不关闭它,或者打开一个文件,在末尾追加信息。这会创建一个非常大的文件。
· 将每一页保存到自己的文件中(你可以使用时间戳来保证每个文件有不同的文件名)。
· 在你的数据库中创建一个新的表来保存数据。
创建一个文件是危险的,因为进程在任何时候都可能失败,破坏数据。除非你只是在进行很小规模的数据拉取(例如,1000 条推文),或进行开发测试,否则你应该使用其他选择。
每次都有很多种方法可以将数据保存到新文件中,最普遍的一种方式是使用日期和时间戳(https://docs.python.org/2/library/datetime.html)创建一个文件,或者只是递增一个数字,将其添加到文件名的末尾。
我们会继续添加推文到简单的数据库。为此,使用下面的函数。
def store_tweet(item): db = dataset.connect('sqlite:///data_wrangling.db') table = db['tweets'] ➊ item_json = item._json.copy() for k, v in item_json.items(): if isinstance(v, dict): ➋ item_json[k] = str(v) table.insert(item_json) ➌
❶ 创建或访问一个新表,名为 tweets。
❷ 检查推文中是否含有字典对象。由于 SQLite 并不支持保存 Python 字典,我们需要将其转换为字符串。
❸ 插入合法的 JSON 对象。
我们还需要添加 dataset 到 import 部分的代码中。在之前保存页面的地方,需要添加这个函数的使用。确保遍历每一条推文。最后的脚本应该看起来像下面一样。
import json import tweepy import dataset API_KEY = '5Hqg6JTZ0cC89hUThySd5yZcL' API_SECRET = 'Ncp1oi5tUPbZF19Vdp8Jp8pNHBBfPdXGFtXqoKd6Cqn87xRj0c' TOKEN_KEY = '3272304896-ZTGUZZ6QsYKtZqXAVMLaJzR8qjrPW22iiu9ko4w' TOKEN_SECRET = 'nsNY13aPGWdm2QcgOl0qwqs5bwLBZ1iUVS2OE34QsuR4C' def store_tweet(item): db = dataset.connect('sqlite:///data_wrangling.db') table = db['tweets'] item_json = item._json.copy() for k, v in item_json.items(): if isinstance(v, dict): item_json[k] = str(v) table.insert(item_json) auth = tweepy.OAuthHandler(API_KEY, API_SECRET) auth.set_access_token(TOKEN_KEY, TOKEN_SECRET) api = tweepy.API(auth) query = '#childlabor' cursor = tweepy.Cursor(api.search, q=query, lang="en") for page in cursor.pages(): for item in page: store_tweet(item)
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论