自分用メモ

  • 週2日制について
    • 1日目(月曜日)に新しいことを学ぶ
    • 2日目(毎週決める)に練習問題やったり補足説明したり
  • 来週の月曜(海の日)について

はじめに

前回は、Webページをスクレイピングして、必要な情報を取得するためのテクニックを学びました。

今回は、実践的なプログラミングの第二弾として、Web APIを利用したプログラミングをやってみましょう。

APIとは

まずAPIとは何なのかという話からいきましょう。アプリケーションプログラミングインタフェース - Wikipediaによると、API(Application Programming Interface)とは、「アプリケーションから利用できる、オペレーティングシステムやプログラミング言語で用意されたライブラリなどの機能の入り口となるものである。」との事です。また、かんたんに言えば、「アプリケーションをプログラムするにあたって、プログラムの手間を省くため、もっと簡潔にプログラムできるように設定されたインターフェースの事である。」とも書いています。

アプリケーションは、WordやExcel、ブラウザの他、みなさんが作るプログラムのことと考えて良いでしょう。インターフェースとは、何かと何かをつなぐもの、接点という意味です。APIは、皆さんのアプリと、その他の既存のプログラムをつなぐためのインターフェースです。

インターフェースとAPI

例えば、Windowsのアプリをゼロから作ろうとすると大変ですが、Windows APIを利用することによって、Windowsっぽい画面(なんかガラスっぽくて、右上に×とか□とかあるアレ)を生成することや、マウスがクリックされた事を検知する処理などは気にすること無く、自分の書きたい部分だけを書くことができます。

Web APIとは

では、これからみなさんが利用してみるWeb APIについて考えてみましょう。Web APIは、Webを通じて用いるAPIの事です。

Web API

例えば、TwitterはWeb APIを公開しているので、Twitter社が作った公式のアプリ以外にも、TweetbotやJanetterなど使いやすいサードパーティ製のアプリを利用することができます。また、whotwiなどは、TwitterのWeb APIを通じてそのアカウントの情報を取得・分析しています。

Twitter API

また、Instagramへ投稿した写真をTwitterで自動的にツイートしている人がいますが、あれはInstagramが、Twitter Web APIを利用しているために、実現できていることです。

インスタTwitter

Twitter APIで遊んでみる

下準備

では実際に、Twitter APIを利用してみましょう。まず、Twitterにアプリケーションを登録する必要があります。

WebブラウザでTwitterにログインした後、apps.twitter.comへアクセスして下さい。アクセスすると、「Create New App」というボタンが出ると思うので、NameやDescription、Websiteを適当に埋めて、Developer Agreementの下のチェックボックスにチェックして、Create your Twitter applicationボタンを押して下さい。もし、電話番号を登録する旨のエラーが出た場合は、従って下さい。

アプリケーションの登録が完了すると、アプリの画面へと遷移します。アプリ名の下のKeys and Access Tokensを推して、Your Access Token欄のCreate my access tokenを推して下さい。

Consumer Key、Consumer Secret、Access Token、Access Token Secretの4つの値をコピーして、どこかに保存しておいて下さい。なお、この4つの値は絶対に他人に知られてはいけません。

clientオブジェクトの作成

では早速Twitter APIを叩いて遊んでみましょう。

twitter gemの基本的な使い方は、GitHubのtwitter gemのページを参照して下さい。

sferik/twitter - GitHub.com

また、詳しい使い方は、rubydocのページを参照します。

Documentation for twitter (6.1.0)

とはいえ、いきなりドキュメントだけ渡されてサクサクとコードを書けるようならこの講習に出る意味はありません。一緒にやっていきましょう。

まず、Twitter APIを叩くためのgemをインストールしましょう。Tera Termを開いて実習用サーバにログインし、以下のコマンドを実行して下さい。

$ gem install twitter

twitter gemのインストールに成功したら、irbまたはpryを起動して、以下のコードを実行して下さい。

1
2
3
4
5
6
7
8
9
10
require 'twitter'

# YOUR_CONSUMER_KEY, YOUR_CONSUMER_SECRET,
# YOUR_TOKEN, YOUR_ACCESS_SECRET はそれぞれ自分のものに書き換え
client = Twitter::REST::Client.new do |config|
  config.consumer_key        = 'YOUR_CONSUMER_KEY'
  config.consumer_secret     = 'YOUR_CONSUMER_SECRET'
  config.access_token        = 'YOUR_ACCESS_TOKEN'
  config.access_token_secret = 'YOUR_ACCESS_SECRET'
end

これで、TwitterサーバとAPIを通じて通信するためのオブジェクト(クライアント)ができました。今後、このclientオブジェクトを通じてTwitter APIをいじっていきます。

今後、間違えてirb(pry)を終了してしまった場合は、その都度上のコードを実行してclientオブジェクトを生成するようにしてください。

タイムラインを取得してみる

まず、自分のホームTLを表示してみましょう。client#home_timelineで、自分のTLのツイートが20件返ってきます。

ClassName#method_nameや、object_name#method_nameのように記述してあるときは、それぞれクラスやオブジェクトのインスタンスメソッドを意味します。)

1
2
3
home_tl = client.home_timeline
home_tl.class
#=> Array

home_tlオブジェクトは、単なる配列です。では、その要素はTweetクラスのオブジェクトです。(性格には、Twitter moduleのTweetクラスですが、まあ今はいいでしょう。)

1
2
3
tweet = home_tl[0]
tweet.class
#=> Twitter::Tweet

そろそろ、gemのドキュメントを見ながらプログラミングをする練習をしてみましょう。Twitter::Tweetクラスのドキュメントは、コチラにあります。

Class: Twitter::Tweet — Documentation for twitter (6.1.0)

とりあえず今は、最新20件のツイートを、以下のように表示したいとしましょう。なお、スクリーンネームは、@以下を指します。

#{ユーザの氏名}(#{ユーザのスクリーンネーム})
#{ツイートの本文}

以下は例です。(元ツイート: https://twitter.com/mktakuya/status/884079688057880576

mktakuya(@mktakuya)
専攻科最高!一番好きな進学先です!

Twitter::Tweetクラスのドキュメントによると、Tweetクラスは#textというインスタンスメソッドを持っているようなので、ツイートの本文の表示にはそれを使えばよさそうです。

また、tweetオブジェクトは、userというインスタンス変数を持っています。userというインスタンス変数は、以下のコードから、Twitter::Userクラスのオブジェクトだということがわかります。

1
2
tweet.user.class
#=> Twitter::User

では、Twitter::Userクラスのドキュメントを見てみましょう。それはこちらにあります。

Class: Twitter::User — Documentation for twitter (6.1.0)

Twitter::Userクラスのドキュメントを見ると、#screen_name#nameというメソッドがあります。ユーザの氏名とユーザのスクリーンネームは、これらを使えば良さそうです。

では、自分のホームタイムラインを取得して、上に示したような書式で表示してみましょう。以下のコードを書いて下さい。なお、puts '-' * 50は、-を50個表示するという意味で、単なる区切りです。

1
2
3
4
5
6
7
home_tl = client.home_timeline
home_tl.each do |tweet|
  puts '-' * 50
  puts "#{tweet.user.name}(@#{tweet.user.screen_name})"
  puts "#{tweet.text}"
  puts '-' * 50
end

ツイートしてみる

では、いよいよRubyからツイートしてみましょう。

1
client.update('Rubyからツイート!')

特にエラーが出なければ、ツイート成功です。自分のTwitterアカウントを開いてみてください。ツイートするだけなら実は結構カンタンだったりします。

ちなみに、#updateはclientオブジェクトから直接呼び出しています。clientオブジェクトはTwitter::REST::Clientクラスのオブジェクトなので、詳しいドキュメントは以下のページにあります。

Class: Twitter::REST::Client — Documentation for twitter (6.1.0)

練習問題

今回は順番じゃなくてやりたい順にやると良いです。

0. 参考情報

Twitter Gemを使ってプログラミングをする際の参考ページを以下にまとめておきます。

また、個人のブログ等でまとめられているものを見てみるのも良いでしょう。

その他、「ruby twitter やりたいこと」でGoogle検索すれば、出てきたりもします。

1. もっといろいろな情報を出力する

先程作成したタイムラインのツイートを表示するプログラムを拡張して、以下のようなフォーマットでツイートを表示するようにしましょう。ファイル名は、disp_home_tl.rbとします。

mktakuya(@mktakuya)
専攻科最高!一番好きな進学先です!
00:59 - 2017年7月10日
いいね: 5件 RT: 0件
URL: https://twitter.com/mktakuya/status/884079688057880576

ツイートの時刻は、以下のように取得できます。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
tweet.created_at
#=> 2017-07-09 15:59:57 +0000
tweet.created_at.class
#=> Time
# tweet.created_at は、Timeクラスのオブジェクトである。

# 年を取得
tweet.created_at.year
#=> 2017
# 月を取得
tweet.created_at.month
#=> 7
# 日付を取得
tweet.created_at.day

# 時を取得
tweet.created_at.hour
#=> 15
# 分を取得
tweet.created_at.min
#=> 59

ドキュメントを見てもわからない(というかそもそもドキュメントの見方がわからない)ときは、ググったほうが早かったりもします。適宜、使い分けましょう。(ググり力もプログラミング能力のひとつだと思います。)

2. 好きな絵師のイラスト自動ダウンロードマッシーン

あるユーザのツイート最新200件を取得し、画像をダウンロードするコードを書きましょう。ファイル名は、dl_images.rbとします。以下に示す3つのサンプルコードを組み合わせれば、実現できます。
なお、画像のダウンロード先はホームディレクトリのimagesディレクトリ内とし、ファイル名は適当な連番(01.jpg, 02.jpg, 03.jpg …… )とします。

あるユーザのツイート200件は、以下のように取得できます。

1
2
3
client.user_timeline('bkub_comic', { count: 200 }).each do |tweet|
  # tweet変数にツイートが格納されているので、それに対して処理を行う
end

また、ある一件のツイートの画像のURLは以下のように処理できます。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
# ツイートのIDを指定して特定のツイートを取得する
# 例として、 https://twitter.com/mktakuya/status/870958051565502465 を用いる。
tweet = client.status(870958051565502465) 

media_urls = [] # 画像のURLを格納する配列

# tweet.media? は、ツイートに画像や動画が含まれていればtrueを、そうでなければfalseを返す。
if tweet.media?
  # ひとつのツイートに複数の画像が含まれる場合もあるので、tweet.mediaは配列である事に注意!
  tweet.media.each do |media|
    # mediaオブジェクトは Twitter::Media::Photoクラスのオブジェクトである。
    # Twitter::Media::Photoクラスは、media_urlメソッドを持つ。
    media_urls.push media.media_url
  end
end

最後に、あるURLの画像をダウンロードするコードを示します。先に、imagesディレクトリを作っておいて下さい。

1
2
3
4
5
6
7
8
9
10
11
12
# 例として、https://twitter.com/mktakuya/status/870958051565502465の画像である、
# http://pbs.twimg.com/media/DBZDtmjUQAE544Q.jpg を、
# imagesディレクトリにダウンロードする。

url = 'http://pbs.twimg.com/media/DBZDtmjUQAE544Q.jpg'

# ENV['HOME']は、自分のホームディレクトリのパスを返す
open("#{ENV['HOME']}/images/filename.jpg", 'wb') do |file|
  open(url) do |data|
    file.write(data.read)
  end
end

3. 今日の運勢をツイートする

今日の運勢をツイートするbotを作りましょう。ファイル名は、omikuji.rbとします。

ツイートする運勢はなんでもいいですが、特に希望がなければ、以下のとおりとします。

  • 大吉
  • 中吉
  • 笑吉
  • 末吉
  • 大凶

これらの運勢をランダムにツイートするようにしてください。定期的に実行する(朝8時にツイートするようにするなど)は、別の設定でできるので、とりあえずひとつだけ運勢をツイートするようなコードを書きましょう。

いきなりツイートしようとせずに、とりあえずputsで出力してテストすることをおすすめします。