【超初心者向け】Docker入門
はじめに
プログラミングを少しやったことのある方なら、Dockerの名前を聞いたことがあるのではないでしょうか?
Dockerは、近年のクラウドサービスの利用拡大に伴って急速に普及した技術です。「GitとDockerは必須」とか、その重要性を説く言葉を良く耳にします。
しかし、新しい技術はまずは概念の理解が難しく、特に私のような独学者にとって、手を出すのは少しハードルが高いと思います。公式サイトを訪れ、絶望してブラウザを閉じたことがあるのは私だけではないはずです。
私は、公式サイトに少なくとも10回も追い出されています。初めて訪れてたのは、2019年くらいだったでしょうか、、、。そんな私ですが、ついに腰を据えてDockerと向き合う機会が訪れました。
このサイトに使っているフレームワークのバージョンアップをしたら、コンパイル時にメモリを喰うようになり、本番環境でのコンパイルが出来なくなってしまったのです。
Windowsでコンパイルしたものが、Linuxでも動けばいいのに、、、!!そう思ったとき、Dockerのことを思い出し、再度公式サイトに訪れることになりました。
今まで敬遠してしまったDockerですが、Docker Imageやコンテナの概念を掴めば、基本的な使い方はさほど難しくありません。また、どういう場合に使えば便利なのか分かれば、覚えるモチベーションにもなるかと思います。
私も入門的な使い方は覚えたので、紹介していきたいと思います。
この記事の内容
超初心者向けの内容です。主に、公式サイトのGet Startedの解説となります。
- Docker image、コンテナの解説
- Dockerfileの書き方
- コンテナ操作
- volume、bindについて
docker-composeやDocker Desktopの使い方は触れませんのでご了承ください。
前提
Dockerのインストールについて
既にインストールは済んでいるものとし、今回は触れません。もしまだの方がいたら、Windows に Docker Desktop をインストールを参考にインストールしてください。
Docker DesktopやKubernetesのように、今回は触れない機能も含まれますが、Windowsをご利用ならリンクの手順のとおり、まとめて入れたほうが良いかと思います。途中、Docker Hubのアカウント作成も求められます。アカウントがないと基本的には使えないので、スキップせずに作りましょう。
環境について
私の環境は以下のとおりです。
- 開発PC(Windows)
> ver
Microsoft Windows [Version 10.0.22621.1848]
- Dockerのバージョン
> docker --version
Docker version 20.10.23, build 7155243
Dockerとは
Dockerはアプリケーションを実行環境ごとイメージ化し、インフラ(ホスト・マシーン等)の他のプロセスから分離した状態で実行する技術です。
これだけだと意味不明かもしれません。例えば、このサイトは本番機はLinux(ubuntu)、開発マシンはWindowsで、JavaScript(Node.js)で作っています。なので、Ubuntu、WindowsそれぞれにNode.jsをインストールしたり、環境設定を入れたり、必要なパッケージを入れたり、環境を構築しています。
普通と言えば普通のやり方かと思いますが、OSが異なるため、「開発機では動くのに本番では動かない」ことも起こり得ます。加えて、そもそも開発機と本番機ではそれぞれ 環境を構築するのが面倒でもあります。私の場合、同じバージョンのNode.jsを入れるところで既に苦戦していました。
Dockerを使えば、WindowsであろうとLinuxであろうと、例えば「Linux(alpine)で動くNode.jsアプリ」のような形で、実行環境ごとアプリを作成することができます。
ホスティング・サービス等で、サーバの仮想化技術は昔から良く使われていましたが、Dockerは「アプリを実行環境ごと仮想化」する技術だと考えればイメージが付きやすいかもしれません。
Dockerの基礎を語るうえで、重要な概念が2つあります。docker imageとコンテナです。それぞれ見ていきたいと思います。
docker imageとは
docker imageは、コンテナのテンプレートです。アプリをその実行環境ごとイメージ化したものです。WindowsとかLinuxのOSのイメージファイルを扱ったことがあるかたなら想像しやすいのではないでしょうか。
「Ubuntu22.04」とか、「alpineで動くNode.js」とか、「buster(debian)で動くpython3」のように、公式リポジトリ(Docker Hub)で公開されているdocker imageを使って、自分のimageを作ることになります。
Dockerfileというファイルで、imageを構築するための記述をするのですが、これは後で解説します。
コンテナとは
docker imageから作られた、アプリとそのアプリの動作環境も含んだ実行可能なソフトウェアです。ホストマシーンの他のプロセスから分離して実行されるので、ホストマシーンがWindowsであれLinuxであれMacであれ、同じように動いてくれます。
コンテナはアプリの実行コードだけでなく、それを動かす環境も内包しています。なので、ファイルへの書き込みがある場合、コンテナ内のファイルシステム上で行われます。ホストマシーン上ではありません。また、コンテナからはホストマシーン上のファイルにアクセス出来ませんし、ホストマシーンからコンテナ内のファイルにはアクセス出来ません。
コンテナを作成するためには、Docker Hubにあるimageを使って、Dockerfileで自分のimageを作成し、そこからコンテナを作成して実行する、というのが基本的な流れになります。
Dockerfileの基礎
自分のdocker imageの構成は、Dockerfileに記述します。まずは基礎的なDockerfileの記述を見ていきます。
Node.jsでhello,worldを出力するimageを作る例で説明したいと思います。
image化するNode.jsのスクリプト
ちゃちゃっと作ってしまいます。ファイル名は何でも良いですが、ここではhello.jsにしておきます。
console.log("hello,world!");
Dockerfile
本丸です。Dockerfile
という名前のテキストファイルを作成します。.txtのような拡張は付けません。
Dockerfileを以下のように編集します。
# コメントも入るよ。
FROM node:18-alpine
WORKDIR /app
COPY hello.js ./
CMD ["node","hello.js"]
これがimageを作成するための指示達です。後述しますが、これをdockerのコマンドでbuildすればimageが出来上がります。まずは1つ1つ見ていきます。
FROMでベースとなるimageを指定
FROM node:18-alpine
の部分です。ベースとなるimageを指定します。基本的には、公式リポジトリのDocker Hubから引っ張ってこられます。
image名:タグのように記載します。今回の例では、image名がnode、18-alpineがタグに対応しています。「alpine(軽量Linux)で動くNodeのv18」という意味になります。
どういうタグが使えるかは、リポジトリを確認する必要があります。Nodeなら別のバージョンもありますし、debian系のLinuxのものもあります。
タグを省略した場合、暗黙的にlatestを指定したものと見なされます。基本は直近のバージョンが入るものと思いますが、厳密にはリポジトリ上latestとしてタグ付けされているものが引っ張られてきます。
他にも、FROM node:18-alpine AS 任意の名前
のように、別名を付けることが可能です。
FROMは複数入れることもできるので、前のFROM句で作成したイメージを使って、さらに処理を加える、ということも出来ます。
WORKDIRでコンテナ内のパスを指定
WORKDIRでCOPYやCMD命令の作業ディレクトリを指定できます。ホストマシーンのディレクトリでなく、コンテナ側のディレクトリです。絶対パス※で指定します。
COPYやRUN命令等でファイルを追加したり、パッケージをインストールしたりするので、ルートにどかどかとファイルが置かれるより、指定したディレクトリに入ったほうが個人的には好みです。なので/appとかの名前でとりあえず指定しておけば良いかと思います。他のサンプル見てもだいたい指定しているので。
※ WORKDIRは複数入れることが出来ます。初回は絶対パスで指定する必要がありますが、2回目移行は(絶対パスからの)相対パスでの指定も出来ます。
COPYでコンテナにファイル等をコピー
COPY hello.js ./
の部分です。これは直感的に分かりやすいかもしれません。左側のhello.jsがホストマシーンのファイル、右側がコンテナ側のパスです。
今回の例だと、WORKDIR /appを指定しているので、/app直下にhello.jsが配置されます。
ディレクトリでの指定も可能ですが、コピー元のディレクトリ自体はコピーされません。中身のみがコピーされます。
なお、コピー元のファイルやフォルダは、プロジェクトフォルダ(Dockerfileと同階層)にある必要があります。../project-folder/some-file.txtのように、上の階層のファイル等を指定することは出来ません。これは、絶対パスで指定も出来ません。
他にも、COPY . .
のように指定して、全てのファイルをコピーすることも可能です。これは便利ですが、npmパッケージのnode_moduleやpythonのキャッシュの__pycache__のように、コピーしたくないものもあると思います。この場合、.dockerignoreファイルで除外するファイルを指定することができます。gitの.gitignoreのdocker版ですね。
基本は左側はホスト側のファイルを指定することになりますが、FROM命令が複数ある場合は、--from
オプションを付けることでFROMで作ったイメージを指定することも可能です。multi-stage-buildと呼ばれるようです。入門としては高度な使い方だと思うので、今回は紹介のみです。
CMDでコンテナを動かす時の処理を登録
コンテナを動かす時に、実行したい処理をCMD命令で登録します。
CMD ["コマンド","引数1","引数2",...]
のように記述します。
前述のとおり、docker imageからコンテナを作ります。出発点として、コンテナ化したいプログラムがあると思うので、そのプログラムのエントリーポイントとなる処理を記述すれば大丈夫です。
今回の例だと、動かしたいプログラムはhello.jsです。Node.jsのプログラムなので、普段はコマンドラインでnode hello.js
のように入力すると思います。
これをCMD命令で記述すると、CMD ["node","hello.js"]
となります。
docker imageをビルド
ビルドのコマンド
上で作成したDockerfileから、imageを作成します。
コマンドラインでDockerfileと同じ階層に移動し、以下のコマンドを打ちます。
docker build -t hello .
- docker buildがビルド用のコマンドです。
- -tは作成されるイメージにつけるタグです。helloというタグをつけています。
- 最後の「.」はDockerfileのパスです。同じ階層にいるので、「.」となります。
こんな感じでビルド結果がコンソールに出力されました。
なお、imageの一覧は以下のコマンドで確認できます。
docker images
# もしくは、以下のコマンドでも同じです。
docker image ls
一番上が、今回作ったイメージです。タグに指定したhelloがリポジトリ名になっていることが確認できます。
私もはじめ驚きましたが、Docker imageは結構容量が大きいです。今回軽量Linuxのイメージをベースにしていますが、175MBもあります。
danglingしたイメージ
Dockerfileを少し修正したり、COPY元のファイルを少し修正し、同じタグで再度ビルドを行ったとします。
以前のimageが上書きされるのではなく、以下のようにリポジトリ名が(none)となりそのまま残ります。
上から2つ目がそれです。
このような古いイメージを、danglingした状態と言うようです。
imageを作る時、Dockerfile自身を修正したり、中に入れるファイルを修正したりして、何回かはビルドすることになります。気が付くと(none)のイメージが貯まっていたりします。 結構容量を食うので、不要ならば定期的に削除してしまいましょう。
以下のコマンドで削除できます。IMAGE_IDにはimageのIDを入力します。
docker rmi IMAGE_ID
# 以下のコマンドでも同じです。
docker image rm IMAGE_ID
dagnling状態のimageをまとめて消す方法もあります。
docker image prune
入力すると以下のように確認の警告が出ます。
WARNING! This will remove all dangling images. Are you sure you want to continue? [y/N]
yを入力して確定させれば削除されます。
imageを削除する時にエラーになる場合
imageから生成したコンテナが存在している場合、以下のエラーが表示されます。
Error response from daemon: conflict: unable to remove repository reference "hello" (must force) - container b8a0c5474b98 is using its referenced image ff397759a43a
コンテナを削除してからイメージを削除しましょう。コンテナ関連の操作は後述します。
もしくは、-fオプションを付けて強制的にコンテナごとimageを削除することも可能です。IMAGE_TAGはimageにつけたタグ名を指定します。
docker rmi -f IMAGE_TAG
コンテナを動かす
docker imageからコンテナを作成します。以下のコマンドを打つと、コンテナの生成と実行が行われます。
> docker run hello
hello,world!
hello
の部分はDocker imageのタグ名を入れています。
hello,world!が出力されており、DockerfileのCMD命令で登録したスクリプトが実行されたことが分かります。
コンテナの状態を確認
コンテナの状態は以下のコマンドで確認できます。
- 稼働中のコンテナの一覧を表示
docker ps
今回コンテナ化したスクリプトはhello,worldを出力するだけなので、ここでは表示されないと思います。処理に時間のかかるものや、Webサーバのように常時稼働するものなら表示されます。
コンテナの削除や再起動等に必要なコンテナIDもこのコマンドから確認が出来ます。
- 全てのコンテナを表示
docker ps -a
1行目が今回作成したコンテナです。
STATUS列がExitedになっていることが確認できます。
ここで分かるように、コンテナのステータスがExitedでも、コンテナは消えずに残っています。
もう一回実行したいときに、docker run
を実行すると別のコンテナが新たに生成されます。コンテナ内のファイルにデータを書き込む処理がある場合、書き込んだデータは別のコンテナから見ることは出来ません。書き込んだデータを活かしたい場合、別のコンテナを作成するのでなく、対象のコンテナを再起動する必要があります。
コンテナを再起動する
docker ps -a
等で、対象のコンテナIDを調べ、docker restart コンテナID
とコマンドを打ちます。
> docker restart 4ecc281c5abc
4ecc281c5abc
docker run
の時はCMDで登録したスクリプトの実行結果が返ってきましたが、コンテナIDが返ってきています。スクリプトの出力結果を確認するには、コンテナのログを確認する必要があります。
コンテナのログを確認する
docker logs コンテナID
で確認できます。
上記で作成したimageからコンテナをdocker runで作成後、docker restartで再起動した後に、ログを確認してみます。
> docker logs 4ecc281c5abc
hello,world!
hello,world!
hello,world!が2つ確認できます。1つ目はdocker runでコンテナを作成した際のログです。2つ目は、restart時のログです。
コンテナを止める
例えばWebサーバのように常時稼働し続けるコンテナの場合、実行中のコンテナを止めることも出来ます。コマンドは以下のとおりです。
docker stop コンテナID
上記の例示のスクリプトでは、docker run後にコンテナのステータスがExitedになるため、使う場面はないと思います。
コンテナを削除する
上述の通り、docker runで作成したコンテナはステータスがExitedになっても残り続けます。
不要になったコンテナは以下のコマンドで削除してしまいましょう。ただし、コンテナ内のデータも消える点は注意です。
docker rm コンテナID
なお、実行中のコンテナは以下のエラーが表示され、削除できません。
Error response from daemon: You cannot remove a running container 8bd9944~~略. Stop the container before attempting removal or force remove
エラーに表示されているとおり、docker stopでコンテナを止めてから削除するか、強制的に削除する必要があります。
強制削除は、-fオプションを付けて実行します。
docker rm -f コンテナID
Dockerfileの応用
Dockerfileの基礎では、docker imageを作成する際に、ローカルのファイルを1つCOPYしただけでした。もう少し処理の入ったimageを作成してみます。
今回は、npmのパッケージをimageに組み込む例を紹介します。入れるパッケージはNode.jsのWebフレームワークであるExpressにします。
npmパッケージをimageに組み込むのが本題ですので、Expressの使い方が分からなくても問題ありません。
コンテナ化するスクリプト
実際に動かすスクリプトはserver.jsの名前で、以下の内容にします。
const express = require("express");
const app = express();
app.get("/", (req, res) => {
res.send("hello,world!")
})
app.listen(3000, () => {
console.log("listening on port 3000...")
})
http://localhost:3000
にGETでアクセスすると、hello,world!のテキストを返すWebサーバです。
ポート3000を利用しています。
.dockerignoreで除外
.dockerignoreのファイル名で、以下の内容を保存します。拡張子は不要です。
node_modules
hello.js
ここに登録されたフォルダやファイルは、dockerfileのCOPY等の命令で除外してくれます。gitの.gitignoreと同じ感じです。
node_modulesはNode.jsのパッケージが格納されるフォルダです。
imageを作成する際、ホストマシーンのnode_modulesをCOPYするのではなく、ビルド時にimage側に組み込む形にするため除外しています。
上段で利用したhello.jsは単純に今回使わないので除外しただけです。
Dockerfile
以下の内容でDockerfileを編集します。
FROM node:18-alpine
WORKDIR /app
# プロジェクトフォルダ直下全てをコピー
# .dockerignoreで登録したファイルは除外
COPY . .
# パッケージインストール
# package-lock.jsonからclean install
RUN npm ci
CMD ["node","server.js"]
イメージ作成の流れは以下の通りです。
- ベースのimageとしてnode:18-alpineを指定
- コンテナ側の作業ディレクトリを/appに指定
- .dockerignoreに登録されたフォルダ・ファイルを除き、プロジェクトフォルダ直下のファイル全てをコンテナ側にコピー(package.json,package-lock.json,server.jsがコピーされる)
- package-lock.jsonからパッケージをクリーンインストール
- CMDでスクリプト登録
今回新たにRUN命令を使用しています。
RUN命令
コマンドを実行し、その結果をイメージに組み込みます。上の例で実行されるのは、npm ci
です。これにより、npm ciの実行結果がイメージとして登録されます。
コマンドはLinux系のイメージなら"/bin/sh"のコマンドが利用できます。
今回利用しているベースのimageはNode.jsやnpm、yarnが使えるimageなので、npmコマンドの利用が出来ています。
alpineは軽量Linuxなので、必要最低限の機能しか入っていません。例えば、cURLのようなコマンドが必要であれば、RUN命令でインストールしてimageに組み込むことが出来ます。
ビルド
イメージのビルド方法は、前の例と同じです。タグ名はhello-serverにします。最後の「.」を忘れずに(Dockerfileと同じ階層でコマンドを流す前提です)。
docker build hello-server .
コンテナ化
こちらも、前の例と同じくdocker run イメージタグ名
を実行します。
今回コンテナ化するアプリは、ポート3000を利用します。コンテナは、ポートもホストマシーンとは別に持っています。そのため、前の例と同じ形でそのまま実行すると、コンテナのポートにアクセスすることが出来ません。
コンテナのポートにアクセスするためには、ホストマシーンのポートとコンテナのポートをマッピングする必要があります。
以下のように実行します。
docker run -dp 5000:3000 hello-server
-pオプションで、コンテナのポート3000を、ホストマシーンのポート5000に割り当てています。
-dオプションは、コンテナをバックグラウンドで実行させるために指定しています。これを入れないと、コンテナ起動中はコマンドラインを占有してしまいます。
ブラウザでhttp://localhost:5000/
を開くと、hello,world!が表示されることが確認できます。
ホストマシーンのポート5000が、コンテナのポート3000にマッピングされていることが分かるかと思います。
稼働中のコンテナの中に入る
docker ps
コマンドでステータスを確認してみます。
Statusに稼働時間が表示されており、稼働していることが分かります。
稼働しているコンテナであれば、コンテナの中を確認できます。以下のコマンドを打ちます。
docker exec -it コンテナID sh
- -itオプションは、コンテナをコマンドラインから操作するために必要なオプションです。
- 最後のshはコンテナに対して実行するコマンドです。今回はalpineを使っており、bashは入っていないため、shを指定しています。
実際にコマンドを打ってみます。
> docker exec -it 7783f6b2d9a7 sh
/app
DockerfileでWORKDIRに指定したappディレクトリにいることが分かります。lsコマンドを打つと、COPY命令でコピーしたファイルや、RUN命令で作成されたnode_modulesなどが確認できます。
/app ls
Dockerfile node_modules oldDockerfile package-lock.json package.json server.js
一つ上の階層をlsすると、いかにもlinuxらしいディレクトリが並んでいることがわかります。
/app ls ../
app bin dev etc home lib media mnt opt proc root run sbin srv sys tmp usr var
ここでいろいろ見てみると、コンテナの理解が少し深まるかと思います。
コンテナ削除
稼働中のコンテナはそのまま消せないため、一度止めてから削除します。
# コンテナを止める
docker stop コンテナID
# コンテナを削除
docker rm コンテナID
もしくは稼働中のコンテナを強制的に削除も可能です、
docker rm -f コンテナID
volumeについて
プログラムをコンテナ化すると、ファイルへの書き込み等もコンテナのファイルシステムに対して行われます。つまり、コンテナを削除してしまうと、そのファイルも消えてしまいます。
データを残す必要がある場合、volumeを利用します。volumeは自分で名前を付けて作成することも出来ますが、今回は指定せず自動で作成してもらう方法で説明します。
なお、dockerのvolumeは、dockerが管理する領域にデータが書き込まれます。自分で保存先を指定することは出来ません。不便なようですが、ホストマシーンのディレクトリ構造に依存せずに保存ができるため、移行などがしやすくなるといったメリットがあります。
コンテナ化するスクリプト
Dockerfileの応用で使ったserver.jsを、以下のように書き換えます。
const fs = require("node:fs")
const express = require("express");
const app = express();
app.get("/", (req, res) => {
const rnd = Math.floor(Math.random() * 1000)
fs.writeFileSync(__dirname + "/data/number.txt", rnd.toString())
res.send(rnd.toString())
})
app.listen(3000, () => {
console.log("listening on port 3000...")
})
localhost:3000
にGETでアクセスすると、0~999のランダムな整数を、/app/data/number.txtに書き込む処理を加えています。
ビルド
Dockerfileは基本的にはDockerfileの応用と同じですが、1行dataフォルダを作成するRUN命令を加えています。
FROM node:18-alpine
WORKDIR /app
# プロジェクトフォルダ直下全てをコピー
# .dockerignoreで登録したファイルは除外
COPY . .
# パッケージインストール
# package-lock.jsonからclean install
RUN npm ci
# 追加行。dataフォルダを作成
RUN mkdir data
CMD ["node","server.js"]
imageのタグ名はvolume-testにしておきます。
コンテナ作成&実行
volumeのマウントは、コンテナ作成時にmountオプションを使って行います。今回は、コンテナの/app/dataフォルダをホストマシーンのvolumeにマウントします。
docker run -dp 5000:3000 --mount type=volume,target=/app/data volume-test
- type: volumeで固定
- target: ホストマシーンに保存する、コンテナ側のディレクトリの絶対パス
- src: volumeの名前(省略した場合、Dockerが自動生成)
これで、localhost:5000にアクセスすると、コンテナの/app/data/number.txtに値が書き込まれた値が、ホストマシーン上のvolumeに書き込まれます。
volumeの保存先
volumeは所定の場所に書き込まれます。以下のコマンドで、マウント先の情報が得られます。
docker inspect コンテナID
情報量が多いですが、Mountsのところが該当します。Sourceがホストマシーン上の保存場所です。
"Mounts": [
{
"Type": "volume",
"Name": "f3de72e92330b0f44fbd9f80241c4dfb5f02db6ac17a38f73b070f28b47dec9c",
"Source": "/var/lib/docker/volumes/f3de72e92330b0f44fbd9f80241c4dfb5f02db6ac17a38f73b070f28b47dec9c/_data",
"Destination": "/app/data",
"Driver": "local",
"Mode": "z",
"RW": true,
"Propagation": ""
}
],
Windowsの場合でも、上記のように表示されますが、実体は\\wsl$\docker-desktop-data\data\docker\volumes
に格納されています。
このフォルダの、Nameのフォルダの中に入っています。
実際にlocalhost:5000にアクセスし、上記のフォルダを確認すると、同じ値が入ったnumber.txtが格納されていることが確認できます。
bindについて
コンテナのファイルとホストマシーンのファイルを同期することも出来ます。bindを使います。
volumeとの違いは、同期先のホストマシーン上のフォルダやファイルを指定できることです。
コンテナ化するスクリプト
volumeについてで使ったserver.jsをそのまま使います。
ビルド
volumeについてと同じDockerfileを使います。
imageのタグ名はbind-testにします。
コンテナ作成&実行
今回は、ホストマシーンのプロジェクト直下のnumber.txtと、コンテナの/app/data/number.txt
をbindしてみます。なお、ホスト側に同期されるファイルが無いと、Dockerが勝手にディレクトリとして作成します。今回はファイルを同期するので、ホスト側にnumber.txtがない場合、空ファイルを作成しておきましょう。
bindは、コンテナ作成時にmountオプションを使って行います。
docker run -dp 5000:3000 --mount type=bind,src="$(pwd)\number.txt",target=/app/data/number.txt bind-test
とても長くなりました。mountオプションにて、以下を設定します。
- type: bind固定
- src: ホストマシーンの絶対パス
- target: コンテナの絶対パス
これで、localhost:5000にアクセスすると、プロジェクト直下にnumber.txtにランダムな数値が書き込まれます。これは、コンテナの/app/data/number.txtに値がまず書き込まれ、このファイルがホストマシーンに同期されています。
逆に、ホストマシーンのnumber.txtを手で適当な値に修正し、コンテナの中に入ってnumber.txtを確認すると、修正した値が反映されていることが確認できます。
bindの状況はvolumeと同じdocker inspect コンテナID
で確認できます。同じく、Mountsのところが該当します。
"Mounts": [
{
"Type": "bind",
"Source": "C:\\Users\\bathi\\Desktop\\test\\docker\\blog\\number.txt",
"Destination": "/app/data/number.txt",
"Mode": "",
"RW": true,
"Propagation": "rprivate"
}
],
最後に
簡単なDockerfileの書き方と、imageのビルド方法、コンテナの作成方法を中心に解説しました。
Dockerは大規模プロジェクトの開発環境の構築や、実際のプロダクトの本場稼働に使われるイメージがあって、何となく個人レベルでの利用はハードルが高いと思っていました。でも、これだけならそこまで難しくないですね!やはり環境を選ばずに実行できるのは便利だと感じます。
ただ、複数のコンテナを連携させたり、Kubernetes等でコンテナ達を管理させたり、もっともっと覚えることが多くありそうです、一方、個人レベルでそこまで必要かな?という気持ちもあります。まずは、使えるところから使っていきたいと思います。
とはいえ、もしまだgitのようなバージョン管理ツールを使っていないのであれば、順番的にはDockerより優先して学んだほうが良い気がします。私の個人的な意見ですが、独学者にとっての優先順位は、プログラム書く>>Git等のバージョン管理>>Dockerです。
参考
- Windows に Docker Desktop をインストール: https://docs.docker.jp/docker-for-windows/install.html
- Getting Started: https://docs.docker.com/get-started/
- Docker Hub: https://hub.docker.com/