🐡

【学習メモ】Dockerを本気で理解しにかかる 〜#1-1 Docker概要〜

2024/01/27に公開

概要

雑談(学習の経緯)

この業界に来て 4 年経過しましたが、最近とても感じてる「なんか全部が中途半端だな...」

ということで 2024 年に入り、今年の目標を立てました!
今までは、勉強すべきこと、したいことがたくさんあって、表面を撫でるように満遍なく一つ一つの技術を学習してきましたが、今年は本当に必要な技術に対して深掘るという作業をしていきたいと思います!

そこで今年の目標は

  1. 毎月一つの技術、知識を深掘る。→ 技術の専門化
  2. 毎月一つ、簡単なものでもいいからアプリケーションを開発する。→ アプリケーション開発は数打って慣れる

です!
学習したことをアウトプットとして、zenn の記事にしたいなと思い、どうせなら自分にプレッシャーをかけてやらざるを得ない状況にしてやろうということで
「本気で理解しにかかるシリーズ」として毎月 1 トピックを投稿していこうと思います。

今月は Docker に関することを 1 ヶ月かけて学習していこうと思います!

Docker・コンテナ

概要

まずはコンテナとは?Docker とは?という概要の部分を見ていきたいと思います!

そもそもコンテナとは

簡潔にいうと「隔離され、パッケージ化された環境」となります。

コンテナイメージ

よく見る図を再現してみましたが、絶望的に下手でした...
このように貨物船の上に載っている貨物、箱のことを実際にコンテナと呼ぶそうです。そのためコンテナ船とも呼ぶそう。
話は脱線しましたが、コンテナ化技術とは、船のコンテナのイメージのようにそれぞれが隔離された環境化で、必要最小限のものだけを用意してアプリケーションやミドルウェアが動作する環境を作ることを指します。

言葉だけではイメージがつきにくいので、実際にアプリケーションを開発するケースを考えてみると以下のようになるかと思います!

  • 例:フロント:React、バックエンド:PHP、DB:PostgreSQL
    コンテナイメージ2

かなりざっくり書きましたが、このように基本的には一つのアプリケーション、ツールが動作する環境を一つのコンテナに閉じ込めるイメージです!
上記はフロントとバックエンドが分離されており、バックエンドは API で Json を返すだけといったイメージのアプリケーションをイメージしてざっくり記述しております。もう少し本格的なアプリケーション環境となると、フロントエンドに nginx を入れたり、バックエンドにも Laravel みたいなフレームワークを入れる必要があるでしょう。
まあこれでイメージはかなりついたかと思います!

Docker とは

Dockerイメージ

上記でコンテナ化技術について見ていきましたが、Docker とはコンテナを管理するためのツールとなっております。
そもそも Docker のようなコンテナを管理するツールは他にもあるようです

    • LinuxContainers
    • Hyper-V コンテナ

    など
    他にもあるようですが、今のところ Docker 一強といったところでしょうか。

Docker に話を戻すと、つまり Docker とは

  • コンテナ仮想化技術を使って、コードとライブラリなどの依存関係を一つのまとまりとしてパッケージ化することができるもの
  • 正確には、コンテナ=Docker ではないが、コンテナの技術を開発者が扱いやすいようツール化されたものが Docker

といった感じでしょうか!

VM(仮想マシン) vs Docker

仮想化技術について、VM 仮想化とコンテナ仮想化(Docker)はよく比較される対象です。以下ざっくりしたイメージ図とよく比較される部分をまとめておきます。

vm vs docker

  • コード化(IaC)

    • VM はコード化できないが、Docker は Dockerfile や docker-compose.yml でコード化できる(コード化のメリットは後述)
  • ゲスト OS

    • VM はゲスト OS が必要。Docker は不要。よって、Docker の方が軽量かつ起動が高速。
  • データの保存

    • VM はデータが永続化されるが、Docker は基本的に一時的なデータとなる。(Docker はデフォルトだとコンテナが削除される度にデータが消える。必要な場合はデータの永続化も可能)

Docker を使用するメリット

上記の VM との比較で Docker を使用することでのメリットも出てきましたが、改めてまとめると以下です。

  • インフラのコード化が可能
    • 「Infrastracture As aCode」いわゆる IaC
    • コード化のメリット
      • コードを読むことでインフラ構成が分かる
      • 受け渡しが可能で、コマンド一つで全員同じ環境が構築できる。(簡単に環境構築できるかつ、環境差異をなくせる)
  • 軽量かつ高速(VM と比較して)
  • 開発環境と本番環境の差異もなくせるかつ、デプロイが容易

DockerHub とは

GitHub がオンラインでコードの管理、共有するためプラットフォームであるように、DockerHub は Docker イメージを管理共有するためのプラットフォームです。
そのため、Git を利用されている方には馴染み深いpullコマンドもあります。

Dockerfile と Docker イメージ と コンテナ

コンテナ仮想化を学ぶ上で混乱してしまう要因は、Dockerfile とイメージとコンテナがそれぞれどういった関係性なのかが曖昧なまま、コマンドを叩いてしまうことだと思っています。なので、以下に図にしてまとめました。

DockerfileとDockerイメージ

上記の図のとおり、Docker コンテナを作成するためには必ず Docker イメージが必要。
Docker イメージを作成するためには、Dockerfile をビルド、もしくはコマンドで直接 DockerHub からイメージを取得する必要があります。いずれの方法を使うにしても Docker イメージは DockerHub からローカルにインストールする必要があるということです!

アプリケーション開発者なら、Docker イメージと Docker コンテナの関係性は、class とインスタンス化されたオブジェクトと言った方がイメージがつきやすいかもしれません。要はイメージは雛形、金型、テンプレートなどなど...コンテナはそれらから作成される実態、インスタンスといったイメージになるでしょう。

Docker イメージの仕組み

Docker イメージはブラックボックスのように見えて仕組みは単純です!

Dockerイメージ

  • 最下層:まっさらな Linux(CentOS や Ubuntu)
  • レイヤー層:必要なコマンドが必要な順番でレイヤー構造になっている(例:sudu yum update -y みたいな)

というだけです!

Docker イメージのタグと注意点

Docker イメージのタグとは簡潔にいうとバージョンを指定することです。
このタグは必ず指定しましょう。なぜなら指定しない場合、latest となってしまうからです。
現時点の最新バージョンが欲しいから latest でいいやという安易な結論にはなりません。
先ほど、Docker のメリットで見たように Dockerfile を渡すだけで全員同じ環境になる点をあげましたが、latest の場合、実行するタイミングによって作成される環境が変わってしまい予期せぬトラブルを生んでしまうからです。

docker-compose とは?

上記で Dockerfile から Docker コンテナを作成する一連の流れを説明しましたが、先述したとおり、一つのコンテナには一つのサービスやツールが動作するかつ、各コンテナは隔離された空間となります。アプリケーションを作成しようと思うと、API サーバーは DB サーバーと通信する必要がありますし、フロントは API を呼び出したいとなると思いますが、隔離されているため通信できません。これらを解決してくれるのが docker-compose です!

要は

  • 複数のコンテナを管理
  • 複数コンテナ間の連携(通信)を可能にする

なので、アプリケーションを開発するための環境を構築するには docker-compose は必須だと考えて問題ないと思います!

まとめ

今回記載したことは以下になります。

  • Docker とは?コンテナとは?
  • VM 仮想化とコンテナ仮想化の違い
  • Dockerfile、Docker イメージ、コンテナの関係性
  • docker-compose とは?

まずはこれらの概要を押さえたところで、次回はコマンドについてまとめいようと思います。

GitHubで編集を提案

Discussion