SSH サーバープロセスを実行する DockerイメージをMacで作成

## バージョン
* Mac
    * macOS Mojave 10.14.3

* Docker
    * 18.09.1
 
## Docker Desktop for Mac のインストール
* 次の Docker Hub ページの 「Download from Docker Hub」
https://docs.docker.com/docker-for-mac/install/

* Docker Hub サイトにログインしていない場合は「Please Login To Download」
Docker Hub のアカウントを作成してログイン状態になり 「Get Docker」

* Docker.dmg を Mac にインストール

* インストール後 Dokcerが起動すると、Macの上部メニューの側に Docker アイコンが表示されるので、クリックして 「Sing in」
"Docker ID" のところはメールアドレスでもログインできるが、docker pullでエラーになるので、Docker ID を入力する。
![image.png](https://qiita-image-store.s3.amazonaws.com/0/148868/8a4ae0fc-0769-c803-21b9-5fe3d091bc61.png)
![image.png](https://qiita-image-store.s3.amazonaws.com/0/148868/19539895-9c7e-7a97-6e8b-c522c49a6c4b.png)

*　ターミナルから docker バージョンの確認
<pre>
$ docker version
Client: Docker Engine - Community
 Version:           18.09.1
 API version:       1.39
 Go version:        go1.10.6
 Git commit:        4c52b90
 Built:             Wed Jan  9 19:33:12 2019
 OS/Arch:           darwin/amd64
 Experimental:      false

Server: Docker Engine - Community
 Engine:
  Version:          18.09.1
  API version:      1.39 (minimum version 1.12)
  Go version:       go1.10.6
  Git commit:       4c52b90
  Built:            Wed Jan  9 19:41:49 2019
  OS/Arch:          linux/amd64
  Experimental:     false
</pre>

## Docker イメージを作成
### 基にする Docker イメージの確認
今回は、Docker Hub レジストリにある 公式の amazonlinux イメージを利用する

* リポジトリの確認
<pre>
$ docker search amazonlinux --limit 1
NAME                DESCRIPTION                                     STARS               OFFICIAL            AUTOMATED
amazonlinux         Amazon Linux provides a stable, secure, and …   572                 [OK]
</pre>
* amazonlinuxリポジトリのタグの確認
<pre>
$ curl -s https://registry.hub.docker.com/v2/repositories/library/amazonlinux/tags/ | jq '.results[].name' | sort
"1"
"1-with-sources"
"2"
"2-with-sources"
"2.0.20190207"
"2.0.20190207-with-sources"
"2018.03-with-sources"
"2018.03.0.20190207-with-sources"
"latest"
"with-sources"
</pre>

### Dockerコンテナー内のSSHサーバーにログインするためのキーペアを作成
<pre>
$ ssh-keygen -t rsa -m PEM
</pre>
「-m PEM」とは
https://qiita.com/tonishy/items/91066b1391e5e772622f

### Dockerfile の作成
* Mac の適当なフォルダに次の内容で Dockerfile を作成する
* サーバアカウントのuid/gidとか、sudo 設定は EC2 Amazon Linux のそれに寄せている
* 
<pre>
FROM amazonlinux:1
RUN yum install -y shadow-utils    ← groupadd コマンドを使うためにインストール
RUN groupadd -g 500 ec2-user
RUN adduser -u 500 -g 500 ec2-user
RUN usermod -aG wheel ec2-user
RUN mkdir -m 0700 /home/ec2-user/.ssh
RUN echo "公開鍵" > /home/ec2-user/.ssh/authorized_keys    ← 上で作成したものの中身をそのまま貼り付け
RUN chmod 0600 /home/ec2-user/.ssh/authorized_keys
RUN chown -R ec2-user.ec2-user /home/ec2-user/.ssh
RUN echo 'root:適当なものに' | chpasswd    ← 念の為に root のパスワードを設定
RUN yum install -y sudo
RUN echo "ec2-user ALL = NOPASSWD: ALL" > /etc/sudoers.d/cloud-init
RUN echo "ec2-user ALL=(ALL) NOPASSWD:ALL" >> /etc/sudoers.d/cloud-init
RUN chmod 0440 /etc/sudoers.d/cloud-init    ← ファイル名は何でもよい、とりあえず EC2 Amazon Linux のデフォに合わせた
RUN yum install -y openssh-server
RUN /usr/bin/ssh-keygen -A    ← SSH サーバーホスト鍵を作成
EXPOSE 22
CMD ["/usr/sbin/sshd", "-D"]
</pre>

### Dockerfile をビルド
* Dockerfiles ファイルのある同じフォルダで次を実行
※最初のビルドでは、Docker Hub レジストリから amazonlinux:1 のイメージをダウンロードするのでインターネットに接続していること
<pre>
$ ls
Dockerfile
　
$ docker build -t amazonlinux1 .
</pre>

* 出来上がったイメージを確認
<pre>
$ docker images
REPOSITORY          TAG                 IMAGE ID            CREATED             SIZE
amazonlinux1        latest              f61c2d171ce7        26 seconds ago      363MB
amazonlinux         1                   7f001bfb59e5        32 hours ago        168MB
</pre>下のイメージが amazonlinux:1 のオリジナルイメージ
上のイメージがオリジナルイメージをDockerfileの内容でカスタマイズしたイメージ
　
Dockerfile を変更して再ビルドする場合は、上のイメージだけ削除して、下のイメージを残しておけば、ビルドのたびに Docker Hub レジストリから amazonlinux:1 のイメージをダウンロードする必要がない。

## コンテナー作成とSSH接続確認
* 次のコマンドで Dockerイメージからコンテナーを作成する
<pre>
$ docker run -d -p 127.0.0.1:2222:22 --name amazonlinux1 amazonlinux1
</pre>
「-p 127.0.0.1:2222:22」 はポートフォワーディング設定
ローカルの 127.0.0.1:2222 接続を、コンテナーの22(ssh)へ繋げる

* コンテナー確認
<pre>
$ docker ps
CONTAINER ID        IMAGE               COMMAND               CREATED             STATUS              PORTS                    NAMES
6d43e67dcb8b        amazonlinux1        "/usr/sbin/sshd -D"   3 seconds ago       Up 1 second         127.0.0.1:2222->22/tcp   amazonlinux1
</pre>

* Mac のターミナルからコンテナーのSSHサーバープロセスへSSHログイン
<pre>
$ ssh -i 秘密鍵 -l ec2-user 127.0.0.1 -p 2222
[ec2-user@6d43e67dcb8b ~]$ ← コンテナーのプロンプト
</pre>

## コンテナーの停止・削除、イメージの削除
撤収

* コンテナーを停止<br />
停止するコンテナーの CONTAINER ID を確認
<pre>
$ docker ps
CONTAINER ID        IMAGE               COMMAND               CREATED             STATUS              PORTS                    NAMES
6d43e67dcb8b        amazonlinux1        "/usr/sbin/sshd -D"   4 minutes ago       Up 4 minutes        127.0.0.1:2222->22/tcp   amazonlinux1
</pre>コンテナーIDを指定して stop
<pre>
$ docker stop 6d43e67dcb8b
6d43e67dcb8b
</pre>
* コンテナーを削除<br />
削除するコンテナーの CONTAINER ID を確認
<pre>
$ docker ps -a
CONTAINER ID        IMAGE               COMMAND               CREATED             STATUS                          PORTS               NAMES
6d43e67dcb8b        amazonlinux1        "/usr/sbin/sshd -D"   6 minutes ago       Exited (0) About a minute ago                       amazonlinux1
</pre>コンテナーIDを指定して削除<pre>
$ docker rm 6d43e67dcb8b
6d43e67dcb8b
</pre>
* イメージを削除<br />
削除するイメージの IMAGE ID あるいは REPOSITORY:TAG を確認
<pre>
$ docker images
REPOSITORY          TAG                 IMAGE ID            CREATED             SIZE
amazonlinux1        latest              f61c2d171ce7        17 minutes ago      363MB
amazonlinux         1                   7f001bfb59e5        32 hours ago        168MB
</pre>上のイメージから削除<br />今回は REPOSITORY:TAG を指定して削除<pre>
$ docker rmi amazonlinux1:latest
$ docker rmi amazonlinux:1
</pre>