はぐれメタルBOTをRuby on Railsに移植しました
はぐれメタルのBOTとそのサイトをRuby on Railsに移植しました。2〜3年前に最初のはぐれメタルができてからほとんど手を加えずに動かしてきたのですが、TwitterのAPIがそろそろ使えなくなりそうなのと、当時の自分のコードなんてメンテナンスする気になれないので、1から作り直しています。
今回の移植で勉強になったことをつらつらと書き連ねます。
Haml
http://haml.info/
もともとのはぐれメタルのサイトはベタ書きの静的なhtmlで構成されていました。それをマルッとHamlに書き直しています。これと言って特別なことはしていません。HamlかわいいよHamlペロペロ。
rails runner
はぐれメタルBOTは定期的に動かすスクリプトなのでRailsには乗せられないかと思ってたんですが、そんなことはなかった。これを使えばRailsに乗ったRubyのコードを簡単に実行できます。
# lib/batches/battle/main.rb module Batches module Battle class Main def self.start # はぐれメタルの処理 end end end end
$ rails runner Batches::Battle::Main.start
本番環境では
$ rails runner -e production Batches::Battle::Main.start
ファイルをどこに置くか迷ったのですが、lib/batches/battle/main.rbに置きました。
便利なGemたち
便利な世の中になったもので、何かしたいと思ったらたいてい誰かが便利なgemを作ってくれています。今回使ったgemの中で特に便利だと思ったものをいくつか挙げます。
tweetstream
https://github.com/intridea/tweetstream
twitterのストリーミングAPIに対応したgem。このgemのおかげではぐれメタルがリアルタイムに応答するようになりました。以下のように使用しています。
EM.run do stream = TweetStream::Client.new EM::Timer.new(180) do stream.stop # 180秒後にストップ end stream.userstream do |status| # はぐれメタルへの攻撃に対する処理 end end
settingslogic
https://github.com/binarylogic/settingslogic
YAMLで定数を管理することができるgem。develop環境とproduction環境で値を変えるなんてこともできます。
こんな感じでtwitterの接続情報をYAMLに書いてます。
# config/twitter.yml development: consumer_key: hogehoge consumer_secret: fugafuga oauth_token: foofoo oauth_token_secret: barbar production: consumer_key: hogehoge consumer_secret: fugafuga oauth_token: foofoo oauth_token_secret: barbar
# lib/settings/twitter.rb module Settings class Twitter < Settingslogic source "#{Rails.root}/config/twitter.yml" namespace Rails.env end end
capistrano
https://github.com/capistrano/capistrano
定番のデプロイツールです。今回使ってみてその簡単さに惚れ惚れしました。
最終的に以下のコマンドでデプロイできるようになりました。プログラムの更新、DBのmigration、assetsのprecompile、unicornの再起動、cronの設定などもろもろが1コマンドで完了です。
$ cap production deploy
whenever
https://github.com/javan/whenever
cronの設定をRubyで書ける優れものです。cronの設定って結構間違えやすいのですが、これなら間違えない設定を書き出してくれます。
# config/schedule.rb set :output, {:error => 'log/error.log', :standard => 'log/cron.log'} every 6.hours do runner 'Batches::Battle::Main.start' end
# crontab -l 0 0,6,12,18 * * * /bin/bash -l -c 'cd /path/to/application && script/rails runner -e development '\''Batches::Battle::Main.start'\'' >> log/cron.log 2>> log/error.log'
asset_sync
https://github.com/rumblelabs/asset_sync
precompileしたassetsをクラウドに配置できるgemです。僕はこれを使ってCSSとJavascriptと画像をAmazonS3に配置しています。静的なファイルを置くならAmazonS3が一番優秀だと思います。
以下の設定ファイルを用意すればassetsのprecompile時に自動的に配置してくれるようになります。
# config/asset_sync.yml production: fog_provider: 'AWS' fog_directory: 'Bucket名' fog_region: 'ap-northeast-1' aws_access_key_id: 'AWSアクセスキー' aws_secret_access_key: 'AWSシークレットアクセスキー' existing_remote_files: delete manifest: true gzip_compression: true
# config/environment/production.rb Hoge::Application.configure do ... config.action_controller.asset_host = '//s3-ap-northeast-1.amazonaws.com/バケット名' end