Site cover image

Site icon imagemy-site-blog

Description is here. The icon, the title, the description can be modified in Notion.

An error occurred while installing mysql2 (0.5.3), M1 Mac

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

rails7でbundle installしようとしたらハマって、
なかなか記事が見つけられなかったので作成することにしました。

以下のコマンドで解決した人しなかった人向けの記事です

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

一番下のまとめがあるので、端折りたい人は下までスクロールしてください

開発環境

MacBook Pro(14インチ、2021)
Apple M1 Pro
ローカル
Ruby 3.0.1
Rails 7.0.1

mysql 0.5.3がinstallできなかった

上記でも書いたようにrails7でbundle installしたら、mysql2(0.5.3)がインストールできませんでした。

$ bundle install
..
..
linking shared-object mysql2/mysql2.bundle
ld: library not found for -lssl
ld: library not found for -lzstd
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 /var/folders/mj/93db0vd975799gg9w3nnr3_r0000gn/T/bundler20190503-14531-xlyd6cmysql2-0.5.3/gems/mysql2-0.5.3 for inspection.
Results logged to /var/folders/mj/93db0vd975799gg9w3nnr3_r0000gn/T/bundler20190503-14531-xlyd6cmysql2-0.5.3/extensions/universal-darwin-18/2.3.0/mysql2-0.5.2/gem_make.out


An error occurred while installing mysql2 (0.5.3), and Bundler cannot continue.
Make sure that `gem install mysql2 -v '0.5.3'` succeeds before bundling.

In Gemfile:
  mysql2

とりあえず、エラーに書かれていたので
gem install mysql2 -v '0.5.3'
を実行

$ gem install mysql2 -v '0.5.3'
Building native extensions. This could take a while...
ERROR:  Error installing mysql2:
	ERROR: Failed to build gem native extension.

    current directory: /Users/kosuke/.rbenv/versions/3.0.1/lib/ruby/gems/3.0.0/gems/mysql2-0.5.3/ext/mysql2
/Users/kosuke/.rbenv/versions/3.0.1/bin/ruby -I /Users/kosuke/.rbenv/versions/3.0.1/lib/ruby/3.0.0 -r ./siteconf20220203-35588-2amaid.rb extconf.rb
checking for rb_absint_size()... yes
checking for rb_absint_singlebit_p()... yes
checking for rb_wait_for_single_fd()... yes
*** extconf.rb failed ***
Could not create Makefile due to some reason, probably lack of necessary
libraries and/or headers.  Check the mkmf.log file for more details.  You may
need configuration options.

Provided configuration options:
	--with-opt-dir
...
..
.

調べてみると、どうやらAppleの独自暗号化ライブラリが優先して使用されるからgemをinstallしてビルドする際に、互換性のあるopensslを使用しなければいけないらしい...?

homebrew の mysql ライブラリは homebrew の openssl を使ってビルドされていて、それを gem i mysql2 でも使いたいけど、homebrew の openssl は /usr/local (or /opt/homebrew )に symlink が貼られておらず gem install では見つけることができないので ldflag を指定する

とりあえず、確認

$ openssl version
LibreSSL 2.8.3

opensslじゃないものが入ってる
→High SierraからデフォルトがOpenSSLからLibreSSLに変更されたらしい

LibreSSLからOpenSSLに変更

まずはLibreSSLが悪さをしているので、OpenSSLに変更する

$ brew link --force openssl@1.1
Linking /opt/homebrew/Cellar/openssl@1.1/1.1.1m... 3989 symlinks created.

If you need to have this software first in your PATH instead consider running:
  echo 'export PATH="/opt/homebrew/opt/openssl@1.1/bin:$PATH"' >> ~/.zshrc


# ~/.zshrcに以下のパスを追加
$ echo 'export PATH="/opt/homebrew/opt/openssl@1.1/bin:$PATH"' >> ~/.zshrc
$ source ~/.zshrc
$ openssl version
OpenSSL 1.1.1m

これでOpenSSLに変わった

bundle configのパス変更

その後にbundle configにmysqlをbuildするためのパスを追加

$ brew info openssl@1.1
openssl@1.1: stable 1.1.1m (bottled) [keg-only]
Cryptography and SSL/TLS Toolkit
<https://openssl.org/>
/opt/homebrew/Cellar/openssl@1.1/1.1.1m (8,081 files, 18MB) *
  Poured from bottle on 2022-01-18 at 19:26:24
From: <https://github.com/Homebrew/homebrew-core/blob/HEAD/Formula/openssl@1.1.rb>
License: OpenSSL
==> Dependencies
Required: ca-certificates ✔
==> Caveats
A CA file has been bootstrapped using certificates from the system
keychain. To add additional certificates, place .pem files in
  /opt/homebrew/etc/openssl@1.1/certs

and run
  /opt/homebrew/opt/openssl@1.1/bin/c_rehash

openssl@1.1 is keg-only, which means it was not symlinked into /opt/homebrew,
because macOS provides LibreSSL.

If you need to have openssl@1.1 first in your PATH, run:
  echo 'export PATH="/opt/homebrew/opt/openssl@1.1/bin:$PATH"' >> ~/.zshrc

For compilers to find openssl@1.1 you may need to set:
  export LDFLAGS="-L/opt/homebrew/opt/openssl@1.1/lib"
  export CPPFLAGS="-I/opt/homebrew/opt/openssl@1.1/include"

For pkg-config to find openssl@1.1 you may need to set:
  export PKG_CONFIG_PATH="/opt/homebrew/opt/openssl@1.1/lib/pkgconfig"

==> Analytics
install: 855,084 (30 days), 2,889,680 (90 days), 10,383,915 (365 days)
install-on-request: 25,446 (30 days), 83,602 (90 days), 642,883 (365 days)
build-error: 719 (30 days)


$ bundle config --local build.mysql2 "--with-ldflags=-L/opt/homebrew/opt/openssl@1.1/lib


$ bundle install
Gem::Ext::BuildError: ERROR: Failed to build gem native extension.
..
..
..
2 warnings generated.
compiling infile.c
compiling mysql2_ext.c
compiling result.c
compiling statement.c
linking shared-object mysql2/mysql2.bundle
ld: warning: directory not found for option '-L/usr/local/opt/openssl/lib/'
ld: library not found for -lzstd
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make: *** [mysql2.bundle] Error 1

make failed, exit code 2

..
..

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

In Gemfile:
  mysql2

まだいけない

他の解決策を探している中でLIBRARY_PATHを設定しているものがあった
https://github.com/brianmario/mysql2/issues/795#issuecomment-861871957

※ 以下は最終的に要らないので打ち込まないでください

$ export LIBRARY_PATH=$LIBRARY_PATH:/opt/homebrew/Cellar/openssl@3/lib

$ bundle install
...
..
2 warnings generated.
compiling infile.c
compiling mysql2_ext.c
compiling result.c
compiling statement.c
linking shared-object mysql2/mysql2.bundle
ld: warning: directory not found for option '-L/usr/local/opt/openssl/lib/'
ld: warning: directory not found for option '-L/opt/homebrew/Cellar/openssl@3/lib'
ld: library not found for -lzstd
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make: *** [mysql2.bundle] Error 1

make failed, exit code 2

..
..

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

In Gemfile:
  mysql2

ld: library not found for -lzstdのエラーが消えない

無駄な環境変数の削除

上記のログに他の手順で無駄な環境変数を追加してしまっていて、
warningが出ていたので一先ず、消すことにした

ld: warning: directory not found for option '-L/usr/local/opt/openssl/lib/'
ld: warning: directory not found for option '-L/opt/homebrew/Cellar/openssl@1.1/1.1.1k/lib'
ld: library not found for -lzstd
# 環境変数一覧コマンド
$ export -p
..
...
export LIBRARY_PATH=:/usr/local/opt/openssl/lib/:/opt/homebrew/Cellar/openssl@1.1/1.1.1k/lib:/opt/homebrew/Cellar/openssl@3/3.0.1/lib/
...
..

以下のコマンドで消す

$ unset LIBRARY_PATH
正しいLIBRARY_PATHの設定
$ export LIBRARY_PATH=$LIBRARY_PATH:/opt/homebrew/Cellar/zstd/1.5.2/lib:/opt/homebrew/Cellar/openssl@1.1/1.1.1m/lib/

zstdのパスとopensslのパスの両方が必要だった
もう一度エラーを見返そう
ld: library not found for -lzstd
-lzstd
答えはエラーの中に書いてあった...orz

  • zstdとは?
    • 圧縮形式Zstandard
    • Facebookがオープンソース化した圧縮アルゴリズムライブラリ
  • Cellarとは?
    • インストール先。brew install でインストールしたパッケージがある場所。

https://qiita.com/01en/items/6cfc542c52f1853019d6

まとめ

一番最初に出ていたエラーに書かれていた

ld: library not found for -lssl
ld: library not found for -lzstd

1つ目がOpenSSLが原因で、2つ目はzstdが原因だったようです。
最初からエラーに答えは書いてあったという...

$ brew install openssl
$ echo 'export PATH="/opt/homebrew/opt/openssl@1.1/bin:$PATH"' >> ~/.zshrc
$ source ~/.zshrc
$ bundle config --local build.mysql2 "--with-ldflags=-L/opt/homebrew/opt/openssl@1.1/lib"
$ export LIBRARY_PATH=$LIBRARY_PATH:/opt/homebrew/Cellar/zstd/1.5.2/lib:/opt/homebrew/Cellar/openssl@1.1/1.1.1m/lib/

ruby3.1の場合は、

$ brew install openssl
$ echo 'export PATH="/opt/homebrew/opt/openssl@3/bin:$PATH"' >> ~/.zshrc
$ source ~/.zshrc
$ bundle config --local build.mysql2 "--with-ldflags=-L/opt/homebrew/opt/openssl@3/lib"
$ export LIBRARY_PATH=$LIBRARY_PATH:/opt/homebrew/Cellar/zstd/1.5.2/lib:/opt/homebrew/Cellar/openssl@3/3.0.1/lib/

参考

https://qiita.com/tatama/items/5e6c7c0ba1a2ba7ff9d3

https://qiita.com/halo57/items/e7511f3befbcb9fedd6a

https://www.blog.umentu.work/rails-openssl-zstd-error/

https://qiita.com/P-man_Brown/items/bb525958f361af39a472