[deploy]RailsアプリをGCPにデプロイ！④~Rails を起動させるまで~

[前回](https://qiita.com/Yukina_28/items/8390e53bc9a7b95ff020)の続きです。
今回Railsアプリが起動できるところまでを書こうと思うのですが、たくさんのエラーを出してしまったため長くなるかと思います。

# 流れ
`1.ローカルでRailsアプリをproductionモードで起動する`
`2.GCP内でmysqlをインストールする`
`3.pumaとnginxを繋げる`



## 1.ローカルでRailsアプリをproductionモードで起動する

まずはローカルでproductionモードで起動できるようにしておこうと思い、いろいろと設定していきました。現在自分の作ったRailsアプリはデータベースのデフォルトが`sqlite３`なのですが、`mysql`に変更したかったためmysqlの設定をしていきました。

はじめにconfig/environments/production.rbの設定を変えておきます
自分はローカルのRailsアプリから新たにデプロイ用のブランチを作り、そこで作業していきました。

```
config.public_file_server.enabled = ENV["RAILS_SERVE_STATIC_FILES"].present?
```
となっているところを

```
config.public_file_server.enabled = true
```
と変更しました。

順番が違うかもしれないのですがRailsアプリに先にmysqlを入れました。

Gemfileに

```
gem “mysql2”
```
bundle installしようとするとエラーが出ました。
`"ld: library not found for -lssl"`

これを調べて、どうやらpathが通ってないようでした。

```
export LIBRARY_PATH=$LIBRARY_PATH:/usr/local/opt/openssl/lib/
```

その後無事にgem install mysql2 -v '0.5.2’できました。

残りは[ローカルで Rails アプリを production モードで起動する](https://qiita.com/mokuo/items/b766ca36521530fd3084)を大変参考にさせていただき、この通りに進めると

```
bundle exec rails s -e production
```

エラーなくアプリの画面を表示することができました。

## 2.GCP内でmysqlをインストールする

次にGCP内にgit cloneしたアプリの方の設定に移ります。
gcloudにログインし、アプリのある場所に移動します。

ここで`bundle install`しようとするのですが、エラーが出ました。
`make: g++: Command not found`

[CentOS7上のRailsでtherubyracerが入らない問題](https://qiita.com/yodaka/items/89149677998f8861200d)の記事が大変参考になりました。この記事の通りに

```
sudo yum -y install gcc-c++
```
しました。

もう一度`bundle install`しようとするのですが、再びエラーが出ました。
確かこのようなエラーでした。
` The "libxml2" package isn't available. (RuntimeError)`

https://github.com/trystant/knowledgebase/issues/43
この記事を参考に

```
sudo yum install libxml2-devel
sudo yum install curl-devel
```
これでbundle installできました。

一度起動してみようと思い

```
sudo env PATH=$PATH bin/rails s -p 3000
```
すると`Could not find a JavaScript runtime`のエラーが出たので

```
sudo yum -y install nodejs
```
しました。

まだエラーが出ているのですが、ここで、mysqlの設定をし忘れていたことに気づいたので、ローカルで作った環境を`git pull`します。

```
git pull origin deploy(ブランチ名)
```
再度`bundle install`しようとするとmysqlでのエラーが出たので

```
sudo yum install mysql-devel
```
すると、無事に`bundle install`できました。

このあとmysqlをインストールしていくのですが、ここで詰まってしまいました。
(`Can't connect to local MySQL server through socket '/tmp/mysql.sock'`のエラーが延々と出てしまいました。)
なので、一旦mysqlをアンインストールし再度インストールしていった過程を書いていこうと思います。

```
yum list installed mysql*
```
このコマンドを使い、mysql周りのものをアンインストールしていきました。


```
sudo yum remove mysql
sudo yum remove mysql-common
sudo rm -rf /var/lib/mysql
sudo yum remove mysql80-community-release.noarch
```
フォルダも削除し、mysql周りのものが削除できたので再インストールしていきます。


```
sudo yum localinstall  https://dev.mysql.com/get/mysql80-community-release-el8-1.noarch.rpm
```
自分はCentOS8なのでこれに合わせたものをインストールします。

また、

```
sudo yum install mysql-devel
```
(↑これをしておかないとbundle install時にエラーが出てしまいました。)

```
sudo yum install -y @mysql:8.0
```
このコマンドを使うことでmysql周りのものを一気にインストールすることができました。
ここで

```
sudo systemctl start mysqld
```
すると、mysqlを起動することができ

```
sudo systemctl status mysqld
```
状態がちゃんとactiveになっていることを確認できました。

次にmysqlにrootユーザーでログインし、新たにユーザーを作っていきます。

```
mysql -u root -p
```
https://www7390uo.sakura.ne.jp/wordpress/archives/456
この記事を参考にユーザーを生成しました。


```
mysql> create user 'user_name'@'localhost' identified by 'password';
Query OK, 0 rows affected (0.14 sec)

mysql> grant all on *.* to 'user_name'@'localhost' with grant option;
Query OK, 0 rows affected (0.19 sec)

mysql> flush privileges;
Query OK, 0 rows affected (0.22 sec)
```
`user_name` ,`password`のところは自分で適したものを入力します。



次に`db:migrate`などしていきたいので、railsアプリのconfig/database.ymlを編集していきます。

```
default: &default
  adapter: mysql2
  encoding: utf8
  pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>
  database: insta_database
  username: user_name
  password: user_password
  socket: /var/lib/mysql/mysql.sock

test:
  <<: *default

production:
  <<: *default

```
(developmentの設定が違うかもしれないのでここでは割愛しました。)

また、必要そうだったので/etc/my.cnfに以下のコードを追加しておきました。

```
character_set_server=utf8
skip-character-set-client-handshake
```

再起動しておきます。

```
sudo systemctl restart mysqld
```
ここまで設定できれば、`rails db:create`できるかと思います。

```
rails db:create RAILS_ENV=production
rails db:migrate RAILS_ENV=production
```
(自分はmigrateファイルの日付の順序がおかしく読み込めないというエラーが出たため、migrationファイルの日付を変更して再度`db:create`しました。)

## 3.pumaとnginxを繋げる

/etc/nginx/nginx.confの設定は以下のようにしました。

```
user　[gcloudでのユーザ名];
worker_processes auto;
error_log /var/log/nginx/error.log;
pid /run/nginx.pid;

# append :rbenv_map_bins, 'puma', 'pumactl'

# Load dynamic modules. See /usr/share/doc/nginx/README.dynamic.
include /usr/share/nginx/modules/*.conf;

events {
    worker_connections 1024;
}

http {
    log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                      '$status $body_bytes_sent "$http_referer" '
                      '"$http_user_agent" "$http_x_forwarded_for"';

    access_log  /var/log/nginx/access.log  main;

    sendfile            on;
    tcp_nopush          on;
    tcp_nodelay         on;
    keepalive_timeout   65;
    types_hash_max_size 2048;

    include             /etc/nginx/mime.types;
    default_type        application/octet-stream;

    include /etc/nginx/conf.d/*.conf;
    include /etc/nginx/sites-available/*;

```

また、アプリ内の`puma.rb`は以下のコードを書いております。

```

threads_count = ENV.fetch("RAILS_MAX_THREADS") { 5 }
threads threads_count, threads_count

bind "unix://#{Rails.root}/tmp/sockets/puma.sock"

port        ENV.fetch("PORT") { 3000 }

environment ENV.fetch("RAILS_ENV") { "development" }

```

このまま

```
rails server --environment production
```

しようとしてもエラーがいくつか出てしまうため、まずgetenforceの設定を変えました。


```
sudo vi /etc/selinux/config
```
config内で

```
SELINUX=disabled
```
と書き換え、再起動します。

```
sudo reboot
```
再起動したら`getenforce`を入力し、`Disabled`になっているか確認します。

最後にプリコンパイルします。

```
bundle exec rake assets:precompile RAILS_ENV=production
```

これで、

```
rails server --environment production
```
すると、http://[外部IPアドレス]でアプリの画面が表示されました！！