Docker備忘録 「Python実行環境の作成」

# はじめに
* 何となくで使っていたDockerについて技術の再現性を高めるためにもまとめておく

# Dockerあれこれ
## 概要
* コンテナ型仮想環境を作成・実行・管理するためのプラットフォーム
* Dockerのソフトウェア自体はGo言語で書かれている

:::note info
メモ「Go言語とは」
Go言語はGoogleが開発しているオープンソースのプログラミング言語
標準パッケージが豊富・省略ができないものがありプログラマーの記述差異を減らせる
:::

## コンテナ型仮想環境の構成イメージ
* 以下であった資料を参考に作成
　https://www.udemy.com/course/docker-k/

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2479387/d05ea649-91b8-32f3-4359-1d0e4bc9ae77.png)

## Dockerの実行イメージ
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2479387/01700082-3d63-0e69-8833-e00aba8a9d73.png)



## 利用するメリット
* プログラムの実行環境を素早く立ち上げることができる
* PC環境を汚さない
    * ローカルに直にインストール必要がない
    * インフラ起因で発生するエラーを減らせる(?)
    * 直でインストールした場合にそれぞれのパッケージ管理もしないといけない
:::note warn
メモ「Pythonのpipenvによる"仮想化"とDockerによる"仮想化"の違い」
まず前提として上記で用いられている"仮想化"という言葉は全く関係のないもの
* DockerではOSレベルで仮想化を実現するもの
    * 一つのPC上で複数のOS環境を同時に稼働させることができる
* pipenvではアプリケーションレベルの仮想化を実現するもの
    * 異なったライブラリをインストールした複数のPython環境を手軽に作ることができる
:::

# 今回検証に利用したWindwosの仕様と環境
| 大項目 | 小項目 | 詳細 |
|:------|:------|:------|
|OS  |エディション  |Windows 11 Pro  |
|  |バージョン  |21H2  |
|  |OSビルド  |22000.556  |
|プログラミング言語  |Python  |3.10.2  |
|Docker  |Docker Desktop  |4.5.1  |
|IDE  |Microsoft Visual Studio  |1.64.2  |

# 1.Dockerのインストール
* すでにインストール済みの場合は、スキップ
1. 以下のリンクからwindows用のDockerDesktopをインストールする
https://hub.docker.com/editions/community/docker-ce-desktop-windows

2. Configurationの画面がでたらそのままOK
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2479387/83784f5e-199b-721b-89da-a6a31eba17e8.png)

3. 以下の画面がでたら再起動し、インストール完了
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2479387/fb7e6745-342c-759c-69e3-140f485e78ed.png)

4. 再起動後に立ち上がらなかった場合
以下のリンクからLinuxカーネルの更新プログラムパッケージをDL/インストールする
https://docs.microsoft.com/ja-jp/windows/wsl/install-manual#step-4---download-the-linux-kernel-update-package


:::note warn
メモ「Dockerの有償化について」

Docker Desktop remains free for small businesses （fewer than 250 employees AND less than $10 million in annual revenue）, personal use, education, and non-commercial open source projects.

執筆時点では個人で利用する分には無料ですが、企業単位で利用する場合には有料の場合があるので注意が必要
https://twitter.com/Docker/status/1432739340266913797
https://www.docker.com/pricing
:::

# 2.各ファイル(dockerfile/dockercompose/実行したいpythonファイル)の準備

0.ファイル構成

```
tcpフォルダ　
L Dockerfile
L docker-compose.yml
L optフォルダ
　L サンプルテスト.py
```

1.Dockerfile
```dockerfile:Dockerfile
FROM python
USER root

RUN apt-get update
RUN apt-get -y install locales && \
    localedef -f UTF-8 -i ja_JP ja_JP.UTF-8
ENV LANG ja_JP.UTF-8
ENV LANGUAGE ja_JP:ja
ENV LC_ALL ja_JP.UTF-8
ENV TZ JST-9
ENV TERM xterm

RUN apt-get install -y vim less
RUN pip install --upgrade pip
RUN pip install --upgrade setuptools
RUN python -m pip install jupyterlab
```

2.Docker-compose.yml

```yml:Docker-compose.yml
version: '3'
services:
  python3:
    restart: always
    build: .
    container_name: 'test'
    working_dir: '/root/'
    tty: true
    volumes:
      - ./opt:/root/opt
```

3.サンプルテスト.py

```python:サンプルテスト.py
import sys

def main():
  val1 = float(sys.argv[1])
  val2 = float(sys.argv[2])
  print(val1*val2)

if __name__ == "__main__":
  main()

```

# 3.Dockerイメージの作成、コンテナのビルド、コンテナの起動

1.コンテナのビルド実行

```md:ターミナル
$ cd tcp
$ docker compose up -d --build
```
- 結果
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2479387/34f3aaa2-f142-8e8f-c495-4a1797cc5345.png)



2.dockerイメージの確認 

```md: ターミナル
$ docker images
```
- 結果
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2479387/8735a90d-4f20-5eba-3ce2-300a32bf7a74.png)

3.docker コンテナの確認 

```md: ターミナル
$ docker container ls
```

- 結果
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2479387/0259fa75-e60c-2801-d9b2-f0d0aa4d2ec1.png)


# 4.コンテナの接続

いずれかのコマンドを実行する

```md: ターミナル
$ docker exec test bash
```

```md: ターミナル
$ docker-compose exec python3 bash
```



:::note info
メモ「コンテナ接続の違い」

* docker exec コンテナ名 bash
* docker-compose exec サービス名 bash

どちらともdocker-compose.ymlに定義しているので要確認
 
:::


# 5.pythonのファイルをDocker上で実行

```
$python サンプルテスト.py 1 5
```
* コマンドライン引数に好きな数字を2つ入れる
* 結果
  ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2479387/dc1fc7c3-39a1-cd02-8b0a-a45d8dae7a66.png)




:::note info
メモ「コンテナ1つならイメージビルドだけでいいのでは？」という疑問

上記の疑問に対して、聞いてみたところ、以下のようなメリットからdocker composeを使う
1. docker run などに与える引数をyamlファイルに定義できる
   * 引数大量になってしまうところをすっきりさせることができるメモとして残せる。

2. 起動オプションまで合わせてgit管理できる
   * 変更管理もできます。複数人で共有するならなおさら必要不可欠。

3. いろいろやってるとコンテナ増える
   * 複数でコンテナを管理することの方が多いので慣れておく意味でも使ってみたほうがいい。

:::

# 残課題
* win32comやtkinterといったライブラリのインストールができなかったので解消したい
* 複数コンテナの管理

# 参考記事・URL
https://qiita.com/jhorikawa_err/items/fb9c03c0982c29c5b6d5

https://qiita.com/tsuboyataiki/items/90dbe94553d3dea39b19

https://docs.docker.jp/engine/reference/commandline/toc.html

https://www.udemy.com/course/docker-k/