Ruby
Rails
Windows

Bash on WindowsでRails開発

More than 1 year has passed since last update.


前書き

予め言っておきますが、僕の所属している会社は、サーバサイドエンジニアには最新のMacBookProを配布してますので、タイトルにあるような闇に突っ込む真似をさせたりはしていません。本記事は個人的に趣味でやってみた記録です。


ついにきた


  • Windows10 Anniversary Update


    • Bash on WindowsはまだBetaだけど、Updateに含まれており、設定で有効にできる



  • Docker for Windows/Mac


    • VirtualBox上のCoreOSを用意しなくても、Windows/Mac上で直接Dockerが動く




Railsぐらいは動くんじゃね?動いて欲しいw


  • bashが動くなら、rbenvが動くはず

  • apt-getで適切にライブラリ入れればrubyインストールできるはず

  • DBとか、周辺ミドルウェアはDockerに任せとけ

  • あとはnative extensionを含むgem次第


やってみた

Ruby 2.3.1

Rails 5.0.0

な感じのRailsアプリケーションを動かすのをゴールにして、環境構築からやってみる


  • rbenv


    • 普通にubuntuにインストールする手順で行ける



  • rbenv経由のrubyインストール


    • 問題なし



  • bundler(on rbenv)


    • なぜか僕の環境では、bash起動時に umask 022 を通ってなかった

    • それに気づかずここまで来てしまったため、 ~/.rbenv 下に、permission 777のディレクトリが大量にできてしまった

    • bundlerは777のディレクトリを拒否するので、コケた


    • chmod -R go-w ~/.rbenv 実行と、.bashrcに umask 022 追加した

    • ↑で問題なく動いた



  • Docker


    • 問題なし

    • インストール時に再起動を要求されたので、rubyまわりの環境構築と同時にやってる場合は注意



  • native extension インストール


    • 問題なし

    • Linuxでもたまにハマるnokogiriも一発でインストール成功した



  • rails実行


    • ハマった。後述。




Rails起動でハマった

こんなの出た

rails aborted!

Errno::EINVAL: Invalid argument - Failed to watch "/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/activesupport-5.0.0/lib/active_support/locale": the given event mask contains no legal events; or fd is not an inotify file descriptor.
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/rb-inotify-0.9.7/lib/rb-inotify/watcher.rb:74:in `initialize'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/rb-inotify-0.9.7/lib/rb-inotify/notifier.rb:190:in `new'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/rb-inotify-0.9.7/lib/rb-inotify/notifier.rb:190:in `watch'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/rb-inotify-0.9.7/lib/rb-inotify/notifier.rb:204:in `watch'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/listen-3.1.5/lib/listen/adapter/linux.rb:32:in `_configure'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/listen-3.1.5/lib/listen/adapter/base.rb:45:in `block in configure'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/listen-3.1.5/lib/listen/adapter/base.rb:40:in `each'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/listen-3.1.5/lib/listen/adapter/base.rb:40:in `configure'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/listen-3.1.5/lib/listen/adapter/base.rb:63:in `start'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/listen-3.1.5/lib/listen/listener.rb:68:in `block in <class:Listener>'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/listen-3.1.5/lib/listen/fsm.rb:121:in `instance_eval'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/listen-3.1.5/lib/listen/fsm.rb:121:in `call'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/listen-3.1.5/lib/listen/fsm.rb:91:in `transition_with_callbacks!'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/listen-3.1.5/lib/listen/fsm.rb:57:in `transition'
/home/nishioka/.rbenv/versions/2.3.1/lib/ruby/gems/2.3.0/gems/listen-3.1.5/lib/listen/listener.rb:91:in `start'


何が起きたか

デフォルト設定で、 RAILS_ENV=development でrailsを起動すると、 file_watcher ってのがセットされる。 rails server 時に、ソースコード書き換えたら勝手に反映されるのをトリガーするやつ。デフォルト設定は config/environments/development.rb に書いてある。

config.file_watcher = ActiveSupport::EventedFileUpdateChecker

で、こいつは、

rb-inotify -> ffi 経由で、擬似(?)native extensionになっていて、nativeのinotifyを使う。

https://github.com/nex3/rb-inotify/blob/v0.9.7/lib/rb-inotify/native.rb

しかし、残念ながら、Bash on WindowsはFilesystem watchに対応していない。

https://github.com/Microsoft/BashOnWindows/issues/216


回避

あんまりうれしくないけど、 config/environments/development.rb で、inotifyを使わないように設定してやることができる。

config.file_watcher = ActiveSupport::FileUpdateChecker

これで動いた!


余談

これはBash on Windows関係ない話だけど、一応。

mysql clientはhostを localhost と設定すると、Unix Socketを見に行く。

が、Docker上にmysql serverを立てていると、TCPしか空いてないので、コケる。

127.0.0.1 を設定するとTCPを使うようになる。