この記事で書くこと
docker-composeを使用したrailsの開発を始めようとしたら
postgresのエラーによって、躓いてしまったこと。
そしてその躓きをどう解決したかの備忘録。
ことの発端
上記の記述に従いdocker-composeを使用したrailsの開発環境の記述に従って開発環境を整えようとしたら、
postgresのエラーに躓き、長い間原因究明に彷徨った。
状況説明
config/database.yml
default: &default
adapter: postgresql
encoding: unicode
host: db
username: postgres
password:
pool: 5
development:
<<: *default
database: myapp_development
test:
<<: *default
database: myapp_test
.ruby-version
2.7.0
躓いた箇所
$ docker-compose run web rake db:create
これがエラー
fe_sendauth: no password supplied
Couldn't create 'myapp_development' database. Please check your configuration.
rails aborted!
PG::ConnectionBad: fe_sendauth: no password supplied
確かに。
おっしゃる通りパスワードは渡してないです。
じゃあ、渡してあげたらいいのかもしれない。
postgresのデフォルトパスワードってなんだっけ?
調べる。
いろいろな情報を付き合わせてどうやら
初期パスワードはないらしい。
ということがわかる。(何か前にも同じようなことで躓いたような気がする。。。という既視感を得て自己嫌悪する。
てことは設定しないといけない。
ということで、適当なパスワードを config/database.yml
に書いてみる。
注意: 今回はあくまでローカルで動作確認をすることが目的でこのような記述方法になっていますが、
機密情報をハードコードするのはよろしくないので、本番での運用などを見越したプロジェクトの場合はcredentialに書いた変数を呼び出しの方がいいです。老婆心までに。
default: &default
adapter: postgresql
encoding: unicode
host: db
username: postgres
password: password
pool: 5
development:
<<: *default
database: myapp_development
test:
<<: *default
database: myapp_test
適当な文字列を入れただけだし、認証情報がdbに作られてない以上、成功はしないだろうと思いつつ、
一つずつ進みたい派なので、実行。
$ docker-compose stop
$ docker-compose up -d
$ docker-compose run web rake db:create
エラーが出ることを確認する。
Starting xxxx_db_1 ... done
中略
FATAL: password authentication failed for user "postgres"
Couldn't create 'myapp_development' database. Please check your configuration.
rake aborted!
PG::ConnectionBad: FATAL: password authentication failed for user "postgres"
/usr/local/bundle/gems/pg-1.2.3/lib/pg.rb:58:in `initialize'
/usr/local/bundle/gems/pg-1.2.3/lib/pg.rb:58:in `new'
/usr/local/bundle/gems/pg-1.2.3/lib/pg.rb:58:in `connect'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_adapters/postgresql_adapter.rb:692:in `connect'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_adapters/postgresql_adapter.rb:223:in `initialize'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_adapters/postgresql_adapter.rb:48:in `new'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_adapters/postgresql_adapter.rb:48:in `postgresql_connection'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_adapters/abstract/connection_pool.rb:830:in `new_connection'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_adapters/abstract/connection_pool.rb:874:in `checkout_new_connection'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_adapters/abstract/connection_pool.rb:853:in `try_to_checkout_new_connection'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_adapters/abstract/connection_pool.rb:814:in `acquire_connection'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_adapters/abstract/connection_pool.rb:538:in `checkout'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_adapters/abstract/connection_pool.rb:382:in `connection'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_adapters/abstract/connection_pool.rb:1033:in `retrieve_connection'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_handling.rb:118:in `retrieve_connection'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/connection_handling.rb:90:in `connection'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/tasks/postgresql_database_tasks.rb:12:in `connection'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/tasks/postgresql_database_tasks.rb:21:in `create'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/tasks/database_tasks.rb:119:in `create'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/tasks/database_tasks.rb:139:in `block in create_current'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/tasks/database_tasks.rb:316:in `block in each_current_configuration'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/tasks/database_tasks.rb:313:in `each'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/tasks/database_tasks.rb:313:in `each_current_configuration'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/tasks/database_tasks.rb:138:in `create_current'
/usr/local/bundle/gems/activerecord-5.2.4.2/lib/active_record/railties/databases.rake:29:in `block (2 levels) in <main>'
Tasks: TOP => db:create
(See full trace by running task with --trace)
passwordが違います。設定してないですからそうですね。
では、設定します。
# postgresユーザのpasswordを設定するため、dbコンテナの中に入ります。
$ docker-compose exec db bash
# postgresユーザのpasswordを設定します
root@コンテナid:/# passwd postgres
New password:
Retype new password:
# 更新しましたと返ってきた。 🛫
passwd: password updated successfully
# では、今パスワードを作成したpostgresユーザでログインを試みる
root@コンテナid:/# su - postgres
postgres@コンテナid:~$ psql
psql (12.2 (Debian 12.2-2.pgdg100+1))
# 🌈 やった〜!
# 以下postgresユーザで実行。
postgres=# \du
List of roles
Role name | Attributes | Member of
-----------+------------------------------------------------------------+-----------
postgres | Superuser, Create role, Create DB, Replication, Bypass RLS | {}
当たり前だけど、superuserなので、アプリケーション用のuserを作成することにする。
postgres=# create role app_user_role WITH CREATEDB login password 'password';
CREATE ROLE
postgres=# \du
List of roles
Role name | Attributes | Member o
f
---------------+------------------------------------------------------------+---------
--
app_user_role | Create DB | {}
postgres | Superuser, Create role, Create DB, Replication, Bypass RLS | {}
config/database.yml
default: &default
adapter: postgresql
encoding: unicode
host: db
username: app_user_role
password: password
pool: 5
development:
<<: *default
database: myapp_development
test:
<<: *default
database: myapp_test
よし。
準備は整ったように見える!
$ docker-compose stop
$ docker-compose up -d
$ docker-compose run web rake db:create
Starting xxxx_db_1 ... done
中略
Created database 'myapp_development'
Created database 'myapp_test'
🥳
dbコンテナに入ってデータベースが本当に作成されたかを確認する。
$ docker-compose exec db bash
root@xxxx:/# su - postgres
postgres@xxx:~$ psql
postgres=# \l
List of databases
Name | Owner | Encoding | Collate | Ctype | Access privileges
----------------------+---------------+----------+------------+------------+-----------------------
myapp_development | app_user_role | UTF8 | en_US.utf8 | en_US.utf8 |
myapp_test | app_user_role | UTF8 | en_US.utf8 | en_US.utf8 |
postgres | postgres | UTF8 | en_US.utf8 | en_US.utf8 |
template0 | postgres | UTF8 | en_US.utf8 | en_US.utf8 | =c/postgres +
| | | | | postgres=CTc/postgres
template1 | postgres | UTF8 | en_US.utf8 | en_US.utf8 | =c/postgres +
| | | | | postgres=CTc/postgres
(5 rows)
開発できる状態になった! http://localhost:3000/