| @技術/プログラミング

以前、 AWS ECS で試験運用したことがあったので Docker 化自体は済んでいた。 ECS などマネージドコンテナサービスを使わずに Docker 運用ができないか試してみた。

動機

関連記事の更新処理、諸々障害があって自動化できておらず、 DB を clone してきて手元で実行してサーバーにエクスポートするという運用が続いていた。これを自動化したかった。

二つ問題があって、以下の通りだった。

  1. 関連記事の更新処理時に日本語の分かち書きをする必要があるが、 VPS インスタンスのメモリ上限があり MeCab の拡張辞書をサーバー上でインストールできない
  2. VPS 上で SQLite の算術計算を行うためには追加拡張が必要で、そのためには SQLite をソースコードからコンパイルする必要がある

1 は Docker イメージにして手元でイメージをビルドすれば解決できた。 2 の問題も Docker のなかでコンパイルを行うことで解決できた。

どうやるか

  • nginx.conf の修正
  • コンテナの create
    キャッシュのためにファイルシステムを利用しているのでホストとコンテナで public ディレクトリを共有する必要があった。
docker create \
  -e DATABASE_URL=db_url \
  -e RACK_ENV=production \
  -v /home/morygonzalez/sites/portalshit/public:/app/public \
  -p 3001:3001 --name portalshit -it morygonzalez/portalshit bundle exec puma -p 3001
  • コンテナの起動
docker start portalshit

結果どうだったか

サイトを Docker で公開することはできたが、 docker create して docker start するまでの間、ダウンタイムが発生する。

ダウンタイムなしで deploy するためには deploy のタイミングで Nginx conf を書き換えて service nginx reload する必要が出てくる。個人のブログレベルでそこまでやりたくない。

コンテナを管理するサービス( AWS ECS や Kubernetes )があるんだったら Nginx conf の書き換えなどしなくてもいい感じに deploy できると思うが、こちらも個人のブログレベルで使うものではないと思った。

結論

  • サイトの deploy はこれまで通り cap で行い、 puma はホスト OS で普通に動かす(コンテナ化しない)
  • 関連記事表示のバッチ処理のみコンテナ化することにした

| @技術/プログラミング

公開している Lokka の DB (MySQL) のデータを、手もとの Lokka の DB (SQLite) に取り込むときに毎回やり方を忘れるので書いておきます。

今回は MySQL to Sqlite converter という gist のコメント欄に書いてある以下の方法を試した。

sudo gem install sequel
sudo gem install sqlite3
sudo gem install mysql
rbenv rehash
sequel mysql://user:password@host/database -C sqlite://db.sqlite

これでデータを MySQL から SQLite に変換できた。Lokka をローカルで起動してアクセスしてみるが記事が表示されない。DB の中にはちゃんとデータが入ってるし、管理画面から記事一覧を表示するとちゃんと記事が表示される。どうも Post.published[] を返すみたい。

手でクエリを投げてみると

sqlite> select * from entries order by created_at desc limit 1;
             id = 960
        user_id = 1
    category_id = 5
           slug = eye-pro-is-shit
          title = Eye-Fi Pro を買ったけどクソだった
           body = [hitode909さんの日記](http://hitode909.hatenablog.com/entry/2013/05/24/093749 "hitode909の日記")...
           type = Post
          draft = 0
     created_at = 2013-10-06 07:28:00.000000
     updated_at = 2013-10-06 13:11:23.000000
frozen_tag_list =
         markup = redcarpet

draft = 0 なので表示されそうなもんなんだけど、よくよく調べてみると SQLite には Boolean 型がなくて、DataMapper は SQLite に Boolean 型のデータを保存するときは t/f の文字列で保存するみたい。これは盲点だった。

結局 draft = 0draft = 'f' に変えてあげればすべての記事を表示できるようになった。