Dockerコンテナーにユーザーを追加する方法


285

いくつかのプロセス(uwsgiおよびcelery)が内部で実行されているdockerコンテナーがあります。アクセス許可を割り当てるために、これらのプロセスのセロリユーザーとuwsgiユーザー、および両方が属するワーカーグループを作成します。

RUN adduser uwsgiRUN adduser celeryをDockerfileに追加してみましたが、これらのコマンドは入力を要求するため、問題が発生しています(以下のビルドからの応答を投稿しました)。

Dockerコンテナーにユーザーを追加して、コンテナーで実行されているワーカーのアクセス許可を設定する最良の方法は何ですか?

私のDockerイメージは公式のUbuntu14.04ベースから構築されています。

adduserコマンドを実行したときのDockerfileからの出力を次に示します。

Adding user `uwsgi' ...
Adding new group `uwsgi' (1000) ... 
Adding new user `uwsgi' (1000) with group `uwsgi' ... 
Creating home directory `/home/uwsgi' ...
Copying files from `/etc/skel' ... 
[91mEnter new UNIX password: Retype new UNIX password: [0m 
[91mpasswd: Authentication token manipulation error
passwd: password unchanged
[0m 
[91mUse of uninitialized value $answer in chop at /usr/sbin/adduser line 563.
[0m 
[91mUse of uninitialized value $answer in pattern match (m//) at /usr/sbin/adduser line 564.
[0m 
Try again? [y/N] 
Changing the user information for uwsgi
Enter the new value, or press ENTER for the default
    Full Name []: 
Room Number []:     Work Phone []:  Home Phone []:  Other []: 
[91mUse of uninitialized value $answer in chop at /usr/sbin/adduser line 589.
[0m 
[91mUse of uninitialized value $answer in pattern match (m//) at /usr/sbin/adduser line 590.
[0m 
Is the information correct? [Y/n] 
---> 258f2f2f13df 
Removing intermediate container 59948863162a 
Step 5 : RUN adduser celery 
---> Running in be06f1e20f64 
Adding user `celery' ...
Adding new group `celery' (1001) ... 
Adding new user `celery' (1001) with group `celery' ... 
Creating home directory `/home/celery' ...
Copying files from `/etc/skel' ... 
[91mEnter new UNIX password: Retype new UNIX password: [0m 
[91mpasswd: Authentication token manipulation error
passwd: password unchanged
[0m 
[91mUse of uninitialized value $answer in chop at /usr/sbin/adduser line 563.
[0m 
[91mUse of uninitialized value $answer in pattern match (m//) at /usr/sbin/adduser line 564.
[0m 
Try again? [y/N] 
Changing the user information for celery
Enter the new value, or press ENTER for the default
    Full Name []:   Room Number []:     Work Phone []: 
Home Phone []:  Other []: 
[91mUse of uninitialized value $answer in chop at /usr/sbin/adduser line 589.
[0m 
[91mUse of uninitialized value $answer in pattern match (m//) at /usr/sbin/adduser line 590.
[0m 
Is the information correct? [Y/n] 

回答:


489

秘訣はuseradd、インタラクティブなラッパーの代わりに使用することですadduser。私は通常、次のユーザーを作成します。

RUN useradd -ms /bin/bash newuser

これにより、ユーザーのホームディレクトリが作成され、bashがデフォルトのシェルになることが保証されます。

次に追加できます:

USER newuser
WORKDIR /home/newuser

あなたのdockerfileに。その後のすべてのコマンドとインタラクティブセッションは、ユーザーとして実行されますnewuser

docker run -t -i image
newuser@131b7ad86360:~$

newuserユーザーコマンドを呼び出す前に、実行するプログラムを実行する権限を与える必要がある場合があります。

セキュリティ上の理由から、コンテナ内で非特権ユーザーを使用することは良い考えです。また、いくつかの欠点もあります。最も重要なのは、スーパーユーザー権限でコマンドを実行する前に、イメージからイメージを取得するユーザーがrootに戻る必要があることです。


141
短いオプションの代わりに、スクリプトのようにDockerfileでフルネームオプションを使用することをお勧めします(対話的にIMOを使用する場合に使用します)。 useradd --create-home --shell /bin/bash同僚にとってより理解しやすい/読みやすいです。
Baptiste Mathus

25
:セットパスワードするために、次のようなchpasswd使用することができますRUN echo 'newuser:newpassword' | chpasswd
iuridiniz

3
大きなユーザーIDで新しいユーザーを作成している場合、Dockerがlastlog-大規模なスパースファイルを作成しようとするとハング/クラッシュする可能性があることに注意してください。--no-log-initオプションを使用してこれを回避しますuseradd
davidA

10
いいヒント、@ iuridiniz!前に呼び出すことを忘れないでくださいUSER newuser。ユーザーにroot権限も必要な場合は、も含めることができますadduser <username> sudo
山猫2016

6
/bin/sh: useradd: not foundalpine linux
deathangel908

91

adduserによるインタラクティブな質問を回避するには、次のパラメーターを使用して呼び出すことができます。

RUN adduser --disabled-password --gecos '' newuser

--gecosパラメータは、追加情報を設定するために使用されます。この場合は空です。

(Alpineなどの)busyboxが搭載されたシステムでは、

RUN adduser -D -g '' newuser

busybox adduserを参照してください


3
ありがとう!のようなadduser低レベルの関数を使用するよりも、高レベルのソリューションの方が一般的に好ましいようuseraddです。
akhmed 2015年

adduser: unrecognized option: gecosこれはアルパインでは機能しないようです。
weberc2 2018

--disabled-passwordの機能と、Dockerfileで同時にユーザーにパスワードを設定するにはどうすればよいですか?
ホセイン

72

Ubuntu

で次の行を試してくださいDockerfile

RUN useradd -rm -d /home/ubuntu -s /bin/bash -g root -G sudo -u 1001 ubuntu
USER ubuntu
WORKDIR /home/ubuntu

useraddオプション(参照:)man useradd

  • -r--systemシステムアカウントを作成します。参照:システムアカウント作成の影響
  • -m--create-homeユーザーのホームディレクトリを作成します。
  • -d--home-dir HOME_DIR新しいアカウントのホームディレクトリ。
  • -s--shell SHELL新しいアカウントのログインシェル。
  • -g--gid GROUPプライマリグループの名前またはID。
  • -G--groups GROUPS補足グループのリスト。
  • -u--uid UIDユーザーIDを指定します。参照:Dockerコンテナでのuidとgidの仕組みを理解する
  • -p--password PASSWORD新しいアカウントの暗号化されたパスワード(例:)ubuntu

デフォルトのユーザーのパスワードを設定する

ユーザーパスワードを設定するには、コマンドに追加-p "$(openssl passwd -1 ubuntu)"しますuseradd

または、次の行をに追加しますDockerfile

SHELL ["/bin/bash", "-o", "pipefail", "-c"]
RUN echo 'ubuntu:ubuntu' | chpasswd

最初のシェル命令は、パイプが含まれる-o pipefail前にオプションが有効になっていることを確認RUNすることです。もっと読むHadolintを:あなたのDockerfileリンティング


2
ユーザーがルートグループに含まれるのはなぜですか?重要なのは、セキュリティ目的で非rootユーザーを作成することではありません
Novaterata

5
@Novaterata用途によって異なります。rootグループは、それらがルートアクセスを持っていることを示すのではなく、いくつかのファイル(ログなど)への読み取りアクセスを増やしただけです。これは便利ですが、プロジェクトによって異なります。
kenorb

これが機能することがわかります。私は自動的にユーザーとしてログインしていますが、まだrootが所有するファイルを生成しています。ローカルユーザーとグループのユーザー名は「user」なので、「USERユーザー」を使用しました。それでもルート所有ファイルを生成します。他に何かすべきことはありますか?私は基本的に、コードベースをコンパイルするDockerコンテナーを作成しています。したがって、svnからコードをチェックアウトし、bashソースを使用して変数を設定します。rootパスワードを要求されなかったとしても、bashコマンドはrootとして動作しますか?
JoeManiaci

14

Dockerにユーザーを追加し、そのユーザーの下でアプリを実行することは、セキュリティの観点から非常に良い習慣です。そのためには、以下の手順をお勧めします。

FROM node:10-alpine

# Copy source to container
RUN mkdir -p /usr/app/src

# Copy source code
COPY src /usr/app/src
COPY package.json /usr/app
COPY package-lock.json /usr/app

WORKDIR /usr/app

# Running npm install for production purpose will not run dev dependencies.
RUN npm install -only=production    

# Create a user group 'xyzgroup'
RUN addgroup -S xyzgroup

# Create a user 'appuser' under 'xyzgroup'
RUN adduser -S -D -h /usr/app/src appuser xyzgroup

# Chown all the files to the app user.
RUN chown -R appuser:xyzgroup /usr/app

# Switch to 'appuser'
USER appuser

# Open the mapped port
EXPOSE 3000

# Start the process
CMD ["npm", "start"]

上記の手順は、NodeJSプロジェクトファイルのコピー、ユーザーグループとユーザーの作成、プロジェクトフォルダーのユーザーへのアクセス許可の割り当て、新しく作成されたユーザーへの切り替え、そのユーザーでのアプリの実行の完全な例です。


1
addgroupが失敗しました、ステップ11/15:RUN addgroup -S username ---> db9fd22d469dでの実行オプションsがあいまいです(シェル、システム)adduser [--home DIR] [--shell SHELL] [--no-create -home] [--uid ID] [--firstuid ID] [--lastuid ID] [--gecos GECOS] [--ingroup GROUP | --gid ID] []-パスワードを--disabled [--disabled-ログイン] [--encrypt-ホーム] USERは、通常のユーザを追加
teoring

9

オープンソースのDockerfileを模倣できます。次に例を示します。

ノード: node12-github

RUN groupadd --gid 1000 node \
    && useradd --uid 1000 --gid node --shell /bin/bash --create-home node

スーパーセット: superset-github

RUN useradd --user-group --create-home --no-log-init --shell /bin/bash 
    superset

オープンソースをフォローする良い方法だと思います。


3

誰もが個人的なお気に入りを持っています、そしてこれは私のものです:

RUN useradd --user-group --system --create-home --no-log-init app
USER app

リファレンス:man useradd

RUNラインは、ユーザーやグループを追加しますapp

root@ef3e54b60048:/# id app
uid=999(app) gid=999(app) groups=999(app)

app画像をベース画像として再利用する場合よりも具体的な名前を使用してください。余談--shell /bin/bashですが、本当に必要な場合は含めてください。


一部クレジット:Ryan Mによる回答


1

あるいは、このようにすることもできます。

RUN addgroup demo && adduser -DH -G demo demo

最初のコマンドは、demoというグループを作成します。2番目のコマンドは、デモユーザーを作成し、以前に作成したデモグループに追加します。

フラグは以下を意味します:

-G Group
-D Don't assign password
-H Don't create home directory

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.