Docker php-apacheを自己証明書でSSL対応（自分メモ）

[前回の記事](https://qiita.com/ukei2021/items/1fe95004d4b7e11a3413)でphp-apache+mysqlを作りましたが、今回はそれを自己証明書を作り、SSL対応するまでを書いていきます。
ゴールはchromeから警告なしで、アクセスできるようになるまでです。


# 環境
マシン macOS Catalina 10.15.7

# 構成

前回終了時こんな感じで終わり

```
任意のディレクトリ
  │
  ├── docker-compose.yml
  │
  ├── html/
  │   └── index.html
  │
  ├── mysql/
  │   ├── Dockerfile
  │   ├── data/
  │   ├── init/
  │   │   └── init.sql
  │   └── my.cnf
  │
  ├── php-apahce/
      ├── Dockerfile
      └── php.ini
```


↓


今回はこんな感じになります。

```
任意のディレクトリ
  │
  ├── docker-compose.yml　更新
  │
  ├── html/
  │   └── index.html
  │
  ├── mysql/
  │   ├── Dockerfile
  │   ├── data/
  │   ├── init/
  │   │   └── init.sql
  │   └── my.cnf
  │
  ├── php-apahce/
      ├── Dockerfile　更新
      ├── ssl.conf　追加
      └── ssl/
          ├──ssl.key　追加
          └──ssl.crt　追加
```

# 構築
さっそく始めましょう
## 自己証明書の作成
まずは自己証明書を作りましょう
とりあえずディレクトリ作って移動

```
ksk@ksknoMacBook-Pro work % mkdir php-apache/ssl
ksk@ksknoMacBook-Pro work % cd php-apache/ssl
```

### 秘密鍵作成

```
ksk@ksknoMacBook-Pro ssl % openssl genrsa -out ssl.key 2048

Generating RSA private key, 2048 bit long modulus
............+++
.+++
e is 65537 (0x10001)
```


### CSR作成
Common Nameだけ「localhost」と入力して、後全部Enter

```
ksk@ksknoMacBook-Pro ssl % openssl req -new -sha256 -key ssl.key -out ssl.csr
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) []:
State or Province Name (full name) []:
Locality Name (eg, city) []:
Organization Name (eg, company) []:
Organizational Unit Name (eg, section) []:
Common Name (eg, fully qualified host name) []:localhost
Email Address []:
error, no objects specified in config file
problems making Certificate Request
```


### san.txt作成
最近の自己証明書でchromeの警告回避するには、これがいるとかいらないとか

```
ksk@ksknoMacBook-Pro ssl % echo "subjectAltName = DNS:localhost" > san.txt
```

### 証明書の作成
10年とかにしたら警告が出た気がするんで、1年にしました。

```
ksk@ksknoMacBook-Pro ssl % openssl x509 -req -sha256 -days 365 -signkey ssl.key -in ssl.csr -out ssl.crt -extfile san.txt
```

証明書の準備は完了

### ssl.conf
ssl.confを前回作った既存のコンテナのssl.confを基にして作りたい為、とりあえずコンテナの状態確認

```
ksk@ksknoMacBook-Pro ssl % cd ../
ksk@ksknoMacBook-Pro php-apache % docker container ls -a
CONTAINER ID   IMAGE             COMMAND                  CREATED          STATUS          PORTS                                         NAMES
4c43e97e5c37   work_mysql        "docker-entrypoint.s…"   20 minutes ago   Up 20 minutes   0.0.0.0:3306->3306/tcp, 33060/tcp             db
35889b716286   work_php-apache   "docker-php-entrypoi…"   20 minutes ago   Up 20 minutes   0.0.0.0:8080->80/tcp                          web
```

webコンテナの方のコンテナIDを使いssl.confをローカルにコピー

```
ksk@ksknoMacBook-Pro php-apache % docker cp 35889b716286:/etc/apache2/sites-available/ssl.conf ./
```

ssl.conf編集
/etc/httpd/ssl/に配置するものとする。

```ssl.conf
〜〜〜
SSLCertificateFile    /etc/httpd/ssl/ssl.crt
SSLCertificateKeyFile /etc/httpd/ssl/ssl.key
〜〜〜
```

### Dockerfile編集
前回の記事からすると、
RUN mkdir -p /etc/httpd/ssl
以降を追記してます。

```Dockerfile
FROM php:7.4-apache
COPY ./php.ini /usr/local/etc/php/
RUN apt-get update
RUN apt-get install -y zip unzip vim libpng-dev libpq-dev
RUN docker-php-ext-install pdo_mysql

RUN mkdir -p /etc/httpd/ssl
RUN a2enmod ssl
COPY ./ssl.conf /etc/apache2/sites-available/ssl.conf
COPY ./ssl/ssl.key /etc/httpd/ssl/ssl.key
COPY ./ssl/ssl.crt /etc/httpd/ssl/ssl.crt
RUN a2ensite ssl

CMD ["/usr/sbin/apache2ctl", "-D", "FOREGROUND"]
```

### docker-compose.ymlの編集
8443から443ポートに接続できるようにします

```docker-compose.yml
version: '3'
services:
  php-apache:
    build: ./php-apache/
    volumes:
      - ./html:/var/www/html
    ports:
      - 8080:80
      - 8443:443
    container_name: web
  mysql:
    build: ./mysql/
    volumes:
      - "./mysql/data:/var/lib/mysql"
      - "./mysql/init:/docker-entrypoint-initdb.d"
    environment:
      - MYSQL_ROOT_PASSWORD=docker
      - MYSQL_DATABASE=mydb
      - MYSQL_USER=appuser
      - MYSQL_PASSWORD=appuser1
    container_name: db
    ports:
      - 3306:3306
```

これでとりあえず準備完了

### 再度build&起動
まず前のやつ残ってたら消します。

```
ksk@ksknoMacBook-Pro cd ../
ksk@ksknoMacBook-Pro work docker container stop web
ksk@ksknoMacBook-Pro work docker container rm web
ksk@ksknoMacBook-Pro work docker container stop db
ksk@ksknoMacBook-Pro work docker container rm db
```

build と 起動

```
ksk@ksknoMacBook-Pro work docker-compose build
ksk@ksknoMacBook-Pro work docker-compose up -d
```

起動確認

```
ksk@ksknoMacBook-Pro work % dodker container ls -a
CONTAINER ID   IMAGE             COMMAND                  CREATED          STATUS          PORTS                                         NAMES
4c43e97e5c37   work_mysql        "docker-entrypoint.s…"   20 minutes ago   Up 20 minutes   0.0.0.0:3306->3306/tcp, 33060/tcp             db
35889b716286   work_php-apache   "docker-php-entrypoi…"   20 minutes ago   Up 20 minutes   0.0.0.0:8080->80/tcp, 0.0.0.0:8443->443/tcp   web
```

### 証明書の登録
先ほどのssl.crtが入っているフォルダにアクセスして
![qiita_20200118_01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1032988/a586f6fb-0eac-0914-fc9d-c6881d3e3816.png)
これをダブルクリック

キーチェーンはシステムで追加を押してください。
![qiita_20200118_02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1032988/94042ad3-dc6c-00fd-3eb9-75b51a22874f.png)

キーチェーン開くと、先ほど登録した証明書がドメイン名で現れるので、ダブルクリックします。
「この証明書を使用する時」を「常に信頼」にすると全てが「常に信頼」になるので、それでこのウィンドウを閉じてください。
![qiita_20200118_03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1032988/4780663b-34bd-6f22-d964-bcadef5b2e0c.png)

最後は画面にアクセスして確認
警告なしに、アドレスの横の鍵マークも不穏な空気を出さずにアクセスできました。
![qiita_20200118_04.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1032988/5eba58bb-ea8a-6c4b-94ef-4d0d7ecf0b46.png)


以上！