Linux環境でのDockerマウント時のパーミッション問題について調査してみた

はじめに

Dockerコンテナでホストのディレクトリをマウントする際、パーミッションの問題に直面することがあります。具体的にはコンテナ側でマウントしたデータが読み込めなかったり、コンテナで作成したものをホスト側で編集できなかったりなどのケースがあります。UbuntuDesktop環境で実際にいろいろ試してみて、そのよう問題について調査したのでそれを共有します。

確認したいこと

  • ホスト側とコンテナ側でのパーミッションの違いがあるかどうか
  • ホスト側(またはコンテナ側)で権限を変更した場合、どちらにも反映されるか
  • ホスト側(またはコンテナ側)でファイルやディレクトリを作成したとき、もう片方では読み込めるか
  • コンテナを2つ立てて同じように起動すれば、相互でファイルやディレクトリを読み込むことができるか

1. ホスト側とコンテナ側のパーミッションの違い

shareディレクトリをホスト側で作成し、コンテナ側にマウントする。

secはホスト側のユーザー名です。

ホスト:

>ls -al
drwxrwx--- 2 sec sec 4096 11月  1 16:22 share

コンテナ:

>ls-al
drwxrwx--- 2 1000 1000 4096 Nov  1 07:22 share

secユーザーのidを確認する。

sec@sec-System-Product-Name:~/test/docker_bind_mound$ id
uid=1000(sec) gid=1000(sec) groups=1000(sec),4(adm),24(cdrom),27(sudo),30(dip),46(plugdev),100(users),114(lpadmin),984(docker)
user_id,group_id,permissionも一致している

ホストのuser_id,group_id,パーミッションがそのままコンテナのディレクトリに反映されることがわかる。

2. ホスト側(またはコンテナ側)で権限を変更した場合、どちらにも反映されるか

まずコンテナ側でpermissionを770=>700に変更してみる
その操作の後、ホスト側でパーミッションを確認する

>ls -al
drwx------ 2 sec sec 4096 11月  1 16:22 share

変更されている。 user_id,group_idが同じだからできるっぽい。

今度はホスト側でpermissionを700=>770に戻してみる。 その操作の後、コンテナ側でパーミッションを確認した。

=>ちゃんと770に戻っている。

3. ホスト側(またはコンテナ側)でファイルやディレクトリを作成したとき、もう片方では読み込めるか

コンテナ側でファイルを作成してみる。

root@08e5c8531d86:/app/share# touch test.txt
root@08e5c8531d86:/app/share# ls -al
-rw-r--r-- 1 root root    0 Nov  1 07:38 test.txt

rootになっている。
(ユーザーの切替をしていないから当然)

ホスト側で確認すると、所有者やパーミッションはコンテナで作成したものと同じになっている。

sec@sec-System-Product-Name:~/test/docker_bind_mound$ ls -al ./share/
-rw-r--r-- 1 root root    0 11月  1 16:38 test.txt

当たり前だが、この場合だとホスト側ではファイルを編集できない。

sec@sec-System-Product-Name:~/test/docker_bind_mound/share$ echo test >test.txt
bash: test.txt: 許可がありません

今度はホスト側でファイルを作成してみる。
以下はコンテナ側での確認。
ホストのものに合わせて、user_id,group_idが1000になっている。

root@08e5c8531d86:/app/share# ls -al
-rw-rw-r-- 1 1000 1000    0 Nov  1 07:43 host.txt

これを回避するためには、コンテナでユーザーを作成し、そのユーザーのuid,gidをホストのユーザーのものと合わせる必要がある。

下の処理をDockerfileに追加してユーザーを作成し、そのユーザーでコンテナを起動する。

RUN groupadd -g 1000 appuser && \
useradd -u 1000 -g 1000 appuser
USER appuser

コンテナ側でのshareディレクトリの権限を確認する。

appuser@b059849743c4:/$ cd app/
appuser@b059849743c4:/app$ ls -al
drwxrwx--- 2 appuser appuser 4096 Nov  1 07:43 share

ちゃんとappuserになっている。

コンテナ側でファイルを作成してみる。

appuser@b059849743c4:/app$ touch ./share/container.txt
appuser@b059849743c4:/app$ ls ./share/ -al
-rw-r--r-- 1 appuser appuser    0 Nov  1 08:00 container.txt
appuser@b059849743c4:/app$ 

appuserでファイルが作成できた。
ホスト側で確認したところ、問題なくファイルの読み書きができた。

4. コンテナを2つ立てて同じように起動すれば、相互でファイルやディレクトリを読み込むことができるか

=>できる。
各コンテナにおいておなじuid,gidのユーザーを作成しておけば良い。

おわりに

Dockerコンテナでホストのディレクトリをマウントする際のパーミッション問題について調査しました。現在取り組んでいる業務において、デプロイ環境ではUbuntu、開発環境ではMacという状況であるため、実際のUbuntu環境でどのような動作をするのかを確かめることができて良かったです。