Rails 新規プロジェクト作成 bundle installで発生するmysql2エラーの解消法

rails

こんにちは。菜笑[なえ]です。
今回は「Rails 新規プロジェクト作成 bundle installで発生するmysql2エラーの解消法」という内容で書いていきます。

事象

Railsで新規プロジェクト作成時にbundle install でエラー発生してハマりました。
いろいろと試したことを載せているので、とりあえず解決法を知りたい方は最後の「解決方法」をご覧ください。

また、エラー解消して無事にrails s まで辿りつけましたが、内容に間違いがあれば優しくご指摘よろしくお願いします。

ディレクトリ・Gemfileの作成

まずはプロジェクト用のディレクトリと、RailsをインストールするためのGemfileを作成。

$ mkdir project-name

$ cd project-name/

$ bundle init

$ vi Gemfile
# frozen_string_literal: true

source "https://rubygems.org"

git_source(:github) {|repo_name| "https://github.com/#{repo_name}" }

gem "rails" # ここのコメントアウトを解除

bundle install

$ bundle install --path vendor/bundle

$ bundle exec rails new . -d mysql --skip-test

エラー内容

$ bundle install

-----
Don't know how to set rpath on your system, if MySQL libraries are not in path mysql2 may not load
-----
-----
Setting libpath to /usr/local/opt/mysql@5.6/lib
-----
creating Makefile

To see why this extension failed to compile, please check the mkmf.log which can be found here:

  /Users/username/git/project-name/vendor/bundle/ruby/2.3.0/extensions/universal-darwin-18/2.3.0/mysql2-0.5.2/mkmf.log

current directory: /Users/username/git/project-name/vendor/bundle/ruby/2.3.0/gems/mysql2-0.5.2/ext/mysql2
make "DESTDIR=" clean

current directory: /Users/username/git/project-name/vendor/bundle/ruby/2.3.0/gems/mysql2-0.5.2/ext/mysql2
make "DESTDIR="
compiling client.c
compiling infile.c
compiling mysql2_ext.c
compiling result.c
compiling statement.c
linking shared-object mysql2/mysql2.bundle
ld: library not found for -lssl
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make: *** [mysql2.bundle] Error 1

make failed, exit code 2

Gem files will remain installed in /Users/username/git/project-name/vendor/bundle/ruby/2.3.0/gems/mysql2-0.5.2 for inspection.
Results logged to /Users/username/git/project-name/vendor/bundle/ruby/2.3.0/extensions/universal-darwin-18/2.3.0/mysql2-0.5.2/gem_make.out

An error occurred while installing mysql2 (0.5.2), and Bundler cannot continue.
Make sure that `gem install mysql2 -v '0.5.2' --source 'https://rubygems.org/'` succeeds before bundling.

In Gemfile:
  mysql2

やってみたこと その1: エラーを信じて実行

まずは、上記エラーに書いてある通りに実行してみます。

$ gem install mysql2 -v '0.5.2' --source 'https://rubygems.org/' -- --with-cppflags=-I/usr/local/opt/openssl/include --with-ldflags=-L/usr/local/opt/openssl/lib

You don't have write permissions for the /Library/Ruby/Gems/2.3.0 directory.

ダメですね。
別のエラーが発生しました。

やってみたこと その2: rbenvインストール

こちらの記事で気になる文言を発見。

システムのrubyを利用しているため、権限不足でgemのインストールができない可能性が高いです。
ルート権限でシステムのRubyにインストールをしてもいいのですが、開発環境ではrbenvでrubyを管理することをおすすめします。

gem installでpermissionエラーになった時の対応方法

とのことなので、やってみます。

rbenv インストール

$ brew install rbenv ruby-build

rbenv: version `ruby-2.3.7' is not installed (set by /Users/username/git/project-name/.ruby-version)
  system

$ rbenv install 2.6.3

$ rbenv versions

rbenv: version `ruby-2.3.7' is not installed (set by /Users/username/git/project-name/.ruby-version)
  system
  2.6.3

$ rbenv global 2.6.3

$ rbenv versions

rbenv: version `ruby-2.3.7' is not installed (set by /Users/username/git/project-name/.ruby-version)
  system
  2.6.3

ずっとrbenv versions で確認しても設定されないと思ったら、.ruby-version を削除することで設定できました。

$ rm .ruby-version_bk

$ rbenv versions
  system
* 2.6.3 (set by /Users/username/.rbenv/version)

rbenvでバージョンは設定できましたが、rubyコマンドを打つとバージョンも、rubyの参照位置も変わらずです。

$ ruby -v
ruby 2.3.7p456 (2018-03-28 revision 63024) [universal.x86_64-darwin18]

$ which ruby
/usr/bin/ruby

パスの設定

これはパスが通ってないせいだったので、~/.bashrcに以下を記述してパスを通してあげます。

$ vi ~/.bashrc
# rbenv
export PATH="$HOME/.rbenv/bin:$PATH"
if which rbenv > /dev/null; then eval "$(rbenv init -)"; fi
$ source ~/.bashrc

$ echo $PATH
/Users/username/.rbenv/shims:/Users/username/.rbenv/bin:/usr/local/opt/mysql@5.6/bin:/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin

パスの設定が完了したら、Rubyのバージョンも、rubyの参照位置も無事に変りました!

$ ruby -v
ruby 2.6.3p62 (2019-04-16 revision 67580) [x86_64-darwin18]

$ which ruby
/Users/username/.rbenv/shims/ruby

$ which gem
/Users/username/.rbenv/shims/gem

これでbundle install できるはず!と思い実行。

$ bundle install

Traceback (most recent call last):
    2: from /Users/username/.rbenv/versions/2.6.3/bin/bundle:23:in `<main>'
    1: from /Users/username/.rbenv/versions/2.6.3/lib/ruby/2.6.0/rubygems.rb:302:in `activate_bin_path'
/Users/username/.rbenv/versions/2.6.3/lib/ruby/2.6.0/rubygems.rb:283:in `find_spec_for_exe': Could not find 'bundler' (2.0.1) required by your /Users/username/git/project-name/Gemfile.lock. (Gem::GemNotFoundException)
To update to the latest version installed on your system, run `bundle update --bundler`.
To install the missing version, run `gem install bundler:2.0.1`

rubyのバージョン変えたからか、bundler 2.0.1バージョンが必要になったみたいです。

bundler:2.0.1 インストール

$ gem install bundler:2.0.1

そして再度bundle install を実行。

$ bundle install

-----
Don't know how to set rpath on your system, if MySQL libraries are not in path mysql2
may not load
-----
-----
Setting libpath to /usr/local/opt/mysql@5.6/lib
-----
creating Makefile

current directory:
/Users/username/git/project-name/vendor/bundle/ruby/2.6.0/gems/mysql2-0.5.2/ext/mysql2
make "DESTDIR=" clean

current directory:
/Users/username/git/project-name/vendor/bundle/ruby/2.6.0/gems/mysql2-0.5.2/ext/mysql2
make "DESTDIR="
compiling client.c
compiling infile.c
compiling mysql2_ext.c
compiling result.c
compiling statement.c
linking shared-object mysql2/mysql2.bundle
ld: library not found for -lssl
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make: *** [mysql2.bundle] Error 1

make failed, exit code 2

Gem files will remain installed in
/Users/username/git/project-name/vendor/bundle/ruby/2.6.0/gems/mysql2-0.5.2 for
inspection.
Results logged to
/Users/username/git/project-name/vendor/bundle/ruby/2.6.0/extensions/x86_64-darwin-18/2.6.0-static/mysql2-0.5.2/gem_make.out

An error occurred while installing mysql2 (0.5.2), and Bundler cannot continue.
Make sure that `gem install mysql2 -v '0.5.2' --source 'https://rubygems.org/'` succeeds
before bundling.

In Gemfile:
  mysql2

最初のエラーその1と同じエラーです…。
ですが、今回はこちらエラーの言葉を信じて実行すると成功しました!

$ gem install mysql2 -v '0.5.2' --source 'https://rubygems.org/' -- --with-cppflags=-I/usr/local/opt/openssl/include --with-ldflags=-L/usr/local/opt/openssl/lib

これでgem mysql2 はインストールできました!

ですが、プロジェクト配下ではなく、システムにインストールされてる。
かつ、bundle install を再度しても同じエラーが出たので解決とはなりませんでした。

やってみたこと その3: macOS_SDK_headers_for_macOS のインストール

こんなのも試してみましたが、ダメでした。

$ xcode-select --install
xcode-select: error: command line tools are already installed, use "Software Update" to install updates

$ sudo open /Library/Developer/CommandLineTools/Packages/macOS_SDK_headers_for_macOS_10.14.pkg

やってみたこと その4: bundle config

次に発見したこちら。

$ bundle config --local build.mysql2 "--with-ldflags=-L/usr/local/opt/openssl/lib --with-cppflags=-I/usr/local/opt/openssl/include"

実行しましたが、変わらずです。
bundle install すると最初と同じエラーが出ます。

解決方法

$ bundle config

Settings are listed in order of priority. The top value will be used.
path
Set for your local app (/Users/username/git/project-name/.bundle/config): "vendor/bundle"

build.mysql2
Set for your local app (/Users/username/git/project-name/.bundle/config): "--with-ldflags=-L/usr/local/opt/openssl/lib --with-cppflags=-I/usr/local/opt/openssl/include"

$ bundle config --delete build.mysql2

$ bundle config

Settings are listed in order of priority. The top value will be used.
path
Set for your local app (/Users/username/git/project-name/.bundle/config): "vendor/bundle"

$ bundle config --local build.mysql2 "--with-cppflags=-I/usr/local/opt/openssl/include"

You are replacing the current local value of build.mysql2, which is currently nil

$ bundle config

Settings are listed in order of priority. The top value will be used.
path
Set for your local app (/Users/username/git/project-name/.bundle/config): "vendor/bundle"

build.mysql2
Set for your local app (/Users/username/git/project-name/.bundle/config): "--with-cppflags=-I/usr/local/opt/openssl/include"

$ bundle install --path vendor/bundle

ついにbundle install 成功しました!!!!!!!!!!

以下のようにオプションを2つ付けたものを実行するとダメなようです。

$ bundle config --local build.mysql2 "--with-ldflags=-L/usr/local/opt/openssl/lib --with-cppflags=-I/usr/local/opt/openssl/include"

オプション1つのこちらで無事解決です!

$ bundle config --local build.mysql2 "--with-cppflags=-I/usr/local/opt/openssl/include"

自分のようにすでにオプション2つで実行した方は、設定を削除したあとオプション1つで実行すると解決できます。

設定を削除
$ bundle config --delete build.mysql2

オプション1つで実行
$ bundle config --local build.mysql2 "--with-cppflags=-I/usr/local/opt/openssl/include"

設定の確認
$ bundle config

その後は問題なくDB作成して、サーバー起動できました。

$ bundle exec bin/rails db:create
$ bundle exec rails s

これでhttp://localhost:3000/ へアクセス完了です。

おわりに

今回は長かったです。
かなりハマりました。

このエラー文で調べたら、わりとたくさんの記事が出てきます。
が、なかなか解決できなかったので、「もうそれ実行したけどダメだったんだよ…」と何度も心が折れそうになりました。

なので同じような人の助けになれば幸いです。

根本的な原因はわかっていないので、そのあたりわかる方がいらっしゃれば、ぜひ教えてください!

参考文献

ありがとうございます!

SNS

Twitter:@nae310_
Instagram:310nae