web技術勉強会 第38回
DESCRIPTION
Web技術勉強会 第38回TRANSCRIPT
Web技術勉強会 第38回
2chから世相を占う
1
「rankforce」
rev.2
Ryuichi TANAKA.
Twitter:@mapserver2007
前回からの続き前回からの続き
http://www.slideshare.net/mapserver2007/web-37
2
・速報がほしい
・速報=2ch(Twitterも?)
・会社にいても速報がほしい・会社にいても速報がほしい
・「有名人が逮捕」→キタ━━━━━━(゚∀゚)━━━━━━ !!!!!
・せめて末席で参加したい
3
前回まででiPhoneに
通知ができた。
4
しかし…しかし…
5
・kayacのAPIの動作がおかしい
->認証エラー多発(設定に問題なし、エラー発生のパターンが
よくわからない)
・なんだかんだでWebで見れたほうが楽ということ
が判明
->会社でいちいちiPhone開くこと自体面倒(笑)
6
方針変更方針変更
7
Twitterに流す
Web上で表示
8
いつものパターンかよ
実行している処理について実行している処理について
9
1.勢いを収集1.勢いを収集
10
・スレタイ・URL・勢いを取得
・2chの勢いまとめサイトから取得(怒られない範囲で…)
・Hpricotで楽々取得
・データをcronで定期的に取得
11
12
2.Twitterに流す2.Twitterに流す
13
アカウント取得
@rankforce
勢いをひたすら垂れ流すbot
14
botを作るbotを作る
15
t = Twitter::Client.new(:login => @login, :password => @password)status = t.status(:post, message)
Twitter4Rを使うと簡単
16
messageにPOSTするメッセージ。statusには
ユーザ情報、投稿内容などが成功すれば返る
bot自体は数十行でできる。
3.取得したデータをDBに格納3.取得したデータをDBに格納
17
方針:
DB使用は任意にする
->DBを使用するのは「オプション」にするため。つまりDBがなく
ても動作するようにする。ても動作するようにする。
テーブルは正規化しない
->つまりActiveRecord級の複雑さは要求しない。Sequelで
できる範囲のDB処理しかしない。
18
その前に…
開発ではDBのマイグレーションを多用するので以下のようなツ
ールを準備すると便利
(SequelにはARのように自動migrateができないので作る)
19
down:テーブルの消去
up:テーブルの生成
Sequelを直接たたくのではなく、間にクラスを作る
(Facadeパターン)
20
DB:CRUDを実行。Sequelをシンプルにラップすることで簡単に
扱えるようにする。使用できる機能は制限されている。
(Something class):DBクラスを継承して使用。複雑な条件を指定するとき
ここにカスタマイズする必要がある(具象化)。実装は使用するクラス
にまかせる。
def custom_select(where, grep)beginds = select.grep(:thread_date,
"#{grep}%").order(:thread_date)ds = ds.filter({:board_id => where}) unless where.nil?return ds
例:
(Something class)#custom_select
return dsrescue => eerror(e)
endend
21
DB#select
(Something class)#custom_selectを呼び出すだけでselect処理が完了
するので、呼び出し元(Controller)で複雑なコードを書かずにすむ。
同様にcustom_xxxを実装すればある程度複雑な処理も簡単に呼び出せる。
4.グラフを作る4.グラフを作る
22
Web上で表示するとき、「グラフ」にすると
格好がいい。
どう実装する?どう実装する?
・Google Chart API
・jQuery系
・その他フリー系
・独自実装
23
Web上で表示するとき、「グラフ」にすると
格好がいい。
どう実装する?どう実装する?
・Google Chart API
・jQuery系
・その他フリー系 -> 「amCharts」
・独自実装
24
“amCharts”
http://www.amcharts.com/
Flashベースのグラフ。見た目がかなり綺麗。
25
XMLかCSV形式のデータを作成し、JavaScript経由で読み込ま
せる。また、FlashのAPIとしてJavaScript関数が使える。
<?xml version="1.0" encoding="UTF-8"?><chart><series><value xid="0">12:58</value><value xid="1">13:01</value><value xid="2">14:15</value></series><graphs><graph gid="1" title="ニュース速報+">
26
<graph gid="1" title="ニュース速報+"><value xid="0" bullet="round_outlined"
url="http://tsushima.2ch.net/test/read.cgi/newsplus/1265169486/" description="【小沢問題】特捜部、民主・小沢氏を「不起訴処分」する方針で検討…現状では「立証困難」★10">3054</value>
<value xid="1" bullet="round_outlined" url="http://tsushima.2ch.net/test/read.cgi/newsplus/1265169665/" description="【トヨタ】新型プリウス、ブレーキ苦情が米で102件 日本でも 「横断歩道で止まれない」★3">3073</value>
<value xid="2" bullet="round_outlined" url="http://tsushima.2ch.net/test/read.cgi/newsplus/1265174114/" description="【裁判】女子高生レイプで服役→19歳女性レイプで服役→鬼畜レイプ魔、今度は犬の散歩中の女性レイプ、首切り殺害→無期懲役求刑★2">3650</value></graph></graphs></chart>
JavaScriptでグラフをコール
var so = new SWFObject("/graph/amline.swf", "amline", "900", "400", "8", "#FFFFFF");so.addVariable("path", "/graph/");so.addVariable("settings_file",
27
so.addVariable("settings_file", encodeURIComponent("/graph/amline_settings.xml"));so.addVariable("data_file", encodeURIComponent("/xml/rankforce_xml_#{@board}_#{@date}.xml"), 0);so.write("graph"); //div#id
28
rankforceの仕様
(収集機能)
29
# スレが登録されていない場合はInsertする# スレが登録されている場合は、勢いがを確認し、勢いが高い場合にUpdateするdef custom_insert(data = nil)unless insert(data)ds = select.filter({:title => data[:title]})ds.each do |e|if data[:ikioi].to_i > e[:ikioi].to_iupdate({:ikioi => data[:ikioi]}, {:id => e[:id]})
endendendfalse
elsetrue
endend
こうすることで、最大の勢いをカウントすることができる。
30
-r [--register-threshold integer]-i [--im-threshold integer]-t [--tweet tweet-threshold integer]-b [--board String[,String,…]]-d [--database]-g [--graph]
取得するスレの勢いの閾値
Im.kayac.comのIMを送信する閾値
取得したスレ情報をTwitterにPOSTする閾値
取得する板名(カンマ区切りで複数可能)
取得したスレ情報をDBに格納するかどうか
取得したスレ情報をグラフ化するかどうか
設定例
31
ruby rankforce.rb –r 3000 –t 6000 –b newsplus –d -g設定例
運用時はこれをcronで実行。
10分に1回収集が妥当
(TwitterAPIの70post/hに引っかからないようにする)
rankforceの仕様
(表示機能)
32
def describe@board ||= ‘newsplus’ # default board@date ||= Time.now.strftime(“%Y%m%d”)calendar = RankForce::Calendar.new(@board, @date)@calendar = calendar.generatehistory = RankForce::History.new@history = history.exechaml :index
end# main methodget ‘/’ do describe end
Webの実装は「Sinatra」。
画面が1つしかないのでRailsを使う必要はないため。
シンプルに作るにはSinatraがやはり向いている。
33
・APサーバは「thin」
thin start –C config/server.yml -d・個人的にRailsでもSinatraでもthinを利用中。
34
thin start –C config/server.yml -d
使ってみた使ってみた
35
rankforce@Twitter
・即時性は低いがTLで追える
・ちょっとした休憩に見て確認
・使い心地はまずまず?
36
rankforce@Web
・常時座席で確認できる
(確認は3秒程度でできる
ので仕事上影響なし)
・グラフなので一発で重要
ニュースがわかるニュースがわかる
(例:朝青龍引退
勢いが通常の10倍
程度あったので
一発でわかった)
・使い勝手は最高
37
結論と今後結論と今後
38
結論
・グラフ表示することでニュースの重要度が一目瞭然
有名人逮捕
↓
グラフで確認
↓
今後
・gem化したい
・自動ビルドするためにrakefileを作る
39
↓
(時間差で)キタ━━━━━━(゚∀゚)━━━━━━ !!!!!
↓
祭り参加inトイレ
注:まだやったことはない
おまけおまけ
40
rankforceをフォローしているおもな人たち。
(2010/2/6現在)
41
広瀬香美 (@kohmi)
なぜフォローしたし。フォロー数/被フォロー数
が凄まじすぎる。
菊池雄星 (@kikuchi_yusei)
NHKニュース (@nhk_rss)
bot。書いていないが個人っぽい?
アルファモザイク (@alfamosaic)
42
高木美帆 (@takagi_miho)
本人じゃ当然ありません。bot。
趣味botかと思いきや、どうやら会社が
運用しているbotらしい。
浅田真央 (@mao_asada)
痛いニュース (@itai_news)
いつも見てます。
というか、どんどん増えてる。
フォロー thx!!!!
ソースはgithubに置きました。ソースはgithubに置きました。
43
http://github.com/mapserver2007/rankforce
44