Rails初級者が一ヶ月研修を受けて得た学びをまとめた~Docker・ほか~

この記事は「[Rails初級者が一ヶ月研修を受けて得た学びをまとめた - Qiita](https://qiita.com/Nifu-Uchi/items/f676d9f082e8c02bd88d)」の環境構築とDockerとその他の項目を切り出した分割記事です。
概要などについては親記事を参照してください。


# 環境構築・その他

### CPUアーキテクチャにあったplatformの設定をする(M1対応)
- [Ruby BundlerでCPUアーキテクチャにあったgemをインストールする](https://zenn.dev/fuuukeee3/articles/df15e32cf3706407a0a6)
- 最終的にこれらのplatform対応を実施
```Gemfile.lock
PLATFORMS
	aarch64-linux ##Docker環境
	arm64-darwin-21 ##M1 Mac
	x86_64-linux ##intel mac
```

## Docker
### DockerfileのCOPYは中間ファイルが増えるので出来るだけまとめる
```Dockerfile
# bad
COPY Gemfile 
COPY Gemfile.lock
COPY $APP_ROOT/

# good
COPY Gemfile Gemfile.lock $APP_ROOT/
```
- ref: [Dockerfile 記述のベストプラクティス | Docker ドキュメント](https://matsuand.github.io/docs.docker.jp.onthefly/develop/develop-images/dockerfile_best-practices/#minimize-the-number-of-layers)

### Dockerfile
```Dockerfile
FROM ruby:3.1.1

RUN apt-get update -qq && \
apt-get install -y build-essential

ENV APP_ROOT /task-manager
WORKDIR $APP_ROOT

COPY Gemfile Gemfile.lock $APP_ROOT/

RUN bundle install
COPY . $APP_ROOT

```


### 不要なディレクトリはマウントしない
- vendorやtmpなどのlocalマシンと同期させる必要がないディレクトリはマウントから除外しておいた方がパフォーマンスが上がる
- ref:【Docker】volume をマウントする時に特定の一部ディレクトリを除外する – こぴぺたん ログ [https://c-a-p-engineer.github.io/tech/2022/04/06/docker-volume-mount-exclude/](https://c-a-p-engineer.github.io/tech/2022/04/06/docker-volume-mount-exclude/)
### `rm -f tmp/pids/server.pid`はやっとくといい
- railsサーバーコンテナをたちあげた際、`server.pid`が残っておりエラーになることが多い
- 起動時のコマンドで消しておく
### dbのvolumeマウントを忘れずに
- 忘れるとコンテナ終了時にDBデータが消えてしまうため、マウントして永続化しておく
```yml
services:
db:
volumes:
- db-data:/var/lib/mysql

volumes:
db-data:  
```

### 最終的なdocker-compose.yml
```yml
version: '3'
services:
db:
image: mysql:5.7
environment:
MYSQL_DATABASE: root
MYSQL_ROOT_PASSWORD: password
volumes:
- db-data:/var/lib/mysql
platform: linux/amd64
ports:
- "${DB_PORT:-3312}:3306"

task-manager:
build: .
command: /bin/sh -c "rm -f tmp/pids/server.pid && bundle exec rails s -p 3000 -b '0.0.0.0'"
volumes:
- .:/task-manager
- vendor:/task-manager/vendor
- tmp:/task-manager/tmp
ports:
- "${APP_PORT:-3003}:3000"
links:
- db

volumes:
vendor:
tmp:
db-data:
```


## Github・その他

### .gitignoreの読み込み直し
- PJ作成後に新規に.gitignoreに加筆した場合、リモートで当該ファイルを削除して、pullして…とやって適応させていたがコマンドで簡単にできることがわかった
- `git rm -r --cached .` でキャッシュを消せ、gitignore対象ファイルをbranchから削除できる
- 実施後にcommitすれば良い
### 思想
- これに倣ってととのえる
  https://twitter.com/t_wada/status/904916106153828352?s=20&t=-DZv-yp9ZO60fqzitCRNCw

### プルリク
- スコープはとにかく切り分ける。まあこれくらいいいかと思ってやらない
  - 切り分けの意識は開発者が一人だと薄れがちなので研修開始当初は結構雑だった 
- やらなくていいことはやらない。根拠ない変更はしない


## その他
### READMEなどの見出しのCapitalizeは整形ツールを使うと便利
- [Title Capitalization Tool - Capitalize My Title - Title Case Tool](https://capitalizemytitle.com/)
- [Title Case Converter – A Smart Title Capitalization Tool](https://titlecaseconverter.com/)
### READMEのRequirementsの親切な書き方とポイント
- アプリケーションを動かすのに飛鳥な製品＆環境という点で書くならば
  - Railsはアプリケーション自体なので書かなくていい（仕様と混同していた）
  - `Docker`単体では動かないので`Docker Desktop`のように製品名を書いてあると良い
	```md
	## Requirements

	- MySQL 5.7 (required if you develop building on local)
	- [Docker Desktop](https://docs.docker.com/desktop/) (required if you develop on Docker)
	```

### テキストファイルの最後に空行挿入する理由
- POSIX標準規格に従うためらしい
- ref https://stackoverflow.com/questions/729692/why-should-text-files-end-with-a-newline  
### そもそもPOSIX規格とは？調べてみました！
- POSIXとは
    > オペレーティングシステム (OS) の標準的なインタフェースおよび環境を定義するIEEE規格である
    [POSIX - Wikipedia](https://ja.wikipedia.org/wiki/POSIX)
- よくわかりませんでした！もう少し詳しく知りたい。
- [POSIX準拠 とは本当はどういうことなのか？「POSIXで規定されたものだけを使う」ではありません - Qiita](https://qiita.com/ko1nksm/items/08228276ce9335592989)
  > OS 実装者向けの要件とアプリケーションの開発者向けの要件があり、高い移植性の実現には双方が POSIX に準拠する必要があります。
  > 「各 OS の動作の違いに対応すること」が POSIX が定めている POSIX 準拠の要件です。
- OSインターフェースの標準規格で、準拠すれば移植性の高いアプリケーションが開発できる。
- ただし、「POSIX準拠＝すべてのPOSIX準拠環境で動く」ではないらしい
- 今の自分の理解ではうまく言葉にまとめられない。少し間を置いて読み返したい
- ref: [The Open Group Base Specifications Issue 7, 2018 edition](https://pubs.opengroup.org/onlinepubs/9699919799.2018edition/)