Docker: 悪いアドバイス

Docker: 悪いアドバイス

私が車の運転を習っていたとき、最初のレッスンで教官が逆走して交差点に進入し、それは絶対にやってはいけないと言われました。 私はこのルールをすぐに覚えて、一生忘れませんでした。

グリゴリー・オスターの『悪いアドバイス』を子供たちに読み聞かせると、子供たちはこれをすべきではないということがいかに簡単かつ自然に理解できるかがわかります。

Dockerfile を正しく記述する方法については、多くの記事が書かれています。 しかし、間違った Dockerfile を作成する方法についての説明は見つかりませんでした。 このギャップを埋めているんです。 そしておそらく、私がサポートを受けているプロジェクトでは、そのような dockerfile は少なくなるでしょう。

すべての登場人物、状況、Dockerfile は架空のものです。 本人が気づいていたら、ごめんなさい。

Dockerfile の作成、不気味で恐ろしい

Peter (上級 java/rubby/php 開発者): 同僚の Vasily さん、新しいモジュールを既に Docker にアップロードしましたか?
Vasily (ジュニア): いいえ、時間がありませんでした。この Docker では理解できませんでした。 記事が多すぎて目まぐるしいです。

ピーター: XNUMX年前に締め切りがありました。 お手伝いさせてください。その過程で解決します。 何がうまくいかないのか教えてください。

ヴァシリー: 最小限でありながら、必要なものがすべて揃っている基本的な画像を選択することはできません。
Peter: ubuntu イメージを例に挙げると、必要なものがすべて含まれています。 そして、たくさんの不要なものは、後で役に立ちます。 バージョンが常に最新になるように、latest タグを忘れずに付けてください。

そして、最初の行が Dockerfile に表示されます。

FROM ubuntu:latest

Peter: 次は何ですか。モジュールを作成するために何を使用しましたか?
Vasily: それで、Ruby さん、Web サーバーがあり、いくつかのサービス デーモンが起動されるはずです。
Peter: はい、何が必要ですか: Ruby、bundler、nodejs、imagemagick、その他何... そして同時に、確実に新しいパッケージを入手するためにアップグレードを実行してください。
Vasily: それで、root にならないようにユーザーを作成しないのですか?
ピーター: くそったれ、それならまだ権利をごまかさなければなりません。
ヴァシリー: すべてを 15 つのコマンドにまとめるのに XNUMX 分ほど時間が必要です。読んだのですが...
(ピーターは几帳面で非常に賢い後輩を無礼にさえぎった。)
Peter: コマンドを分けて書いたほうが読みやすくなります。

Dockerfile は次のように成長します。

FROM ubuntu:latest
RUN apt-get update
RUN apt-get upgrade
RUN apt-get -y install libpq-dev imagemagick gsfonts ruby-full
RUN gem install bundler
RUN curl -sL https://deb.nodesource.com/setup_9.x | sudo bash -
RUN apt-get install -y nodejs
RUN bundle install --without development test --path vendor/bundle
RUN rm -rf /usr/local/bundle/cache/*.gem 
RUN apt-get clean 
RUN rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/*

その後、DevOps (ただし、Dev というよりも Ops) の Igor Ivanovich がオフィスに乱入し、次のように叫びました。

AI: ペティア、あなたの開発者はまた食品データベースを破壊しました、いつ終わるのでしょう...

小さな小競り合いの後、イーゴリ・イワノビッチは冷静になり、同僚がここで何をしているのかを調べ始めます。

アイ:何をしてるんですか?
Vasily: Peter は、新しいモジュール用の Dockerfile の作成を手伝ってくれています。
AI: 見てみましょう... ここに何を書いたのですか。別のコマンドでリポジトリをクリーンアップします。これは追加のレイヤーです... しかし、Gemfile をコピーしていない場合、依存関係をどうやってインストールするのでしょうか。 そして一般的に、これは良くありません。
Peter: どうぞ、仕事に取り組んでください。何とか解決します。

イゴール・イワノビッチは悲しそうにため息をつき、誰がデータベースを破ったのかを突き止めるために立ち去ります。

Peter: はい、でもコードに関しては彼の言うことは正しかったので、それを画像にプッシュする必要があります。 そして、すぐに ssh とスーパーバイザをインストールしましょう。そうでない場合は、デーモンを起動します。

Vasily: 次に、最初に Gemfile と Gemfile.lock をコピーし、次にすべてをインストールし、次にプロジェクト全体をコピーします。 Gemfile が変更されない場合、レイヤーはキャッシュから取得されます。
Peter: なぜ皆さんはこのようなレイヤーを持っているのですか、一度にすべてをコピーしてください。 すぐにコピーしてください。 一番最初の行。

Dockerfile は次のようになります。

FROM ubuntu:latest
COPY ./ /app
WORKDIR /app
RUN apt-get update
RUN apt-get upgrade
RUN apt-get -y install libpq-dev imagemagick gsfonts ruby-full ssh supervisor
RUN gem install bundler
RUN curl -sL https://deb.nodesource.com/setup_9.x | sudo bash -
RUN apt-get install -y nodejs

RUN bundle install --without development test --path vendor/bundle
RUN rm -rf /usr/local/bundle/cache/*.gem 
RUN apt-get clean 
RUN rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/* 

ピーター: それで、次は何ですか? スーパーバイザー用の設定はありますか?
ヴァシリー: いや、いや。 でも、すぐにやりますよ。
ピーター: それならあなたがやりますよ。 それでは、すべてを起動する init スクリプトをスケッチしてみましょう。 さて、nohup を使用して ssh を起動して、コンテナに接続して何が問題になったのかを確認します。 次に、同様にスーパーバイザを実行します。 そうですね、あとは乗客を走らせるだけです。
Q: しかし、Docker が何か問題が発生したことを認識してコンテナーを再起動できるように、プロセスは XNUMX つである必要があると読みました。
P: くだらないことで頭を悩ませないでください。 そして一般的にはどうやって? これらすべてを XNUMX つのプロセスで実行するにはどうすればよいでしょうか? イゴール・イワノビッチに安定性について考えさせてください、彼が給料を受け取るのは当然のことです。 私たちの仕事はコードを書くことです。 そして一般的には、私たちが彼のために Dockefile を書いてくれたことに感謝を伝えましょう。

10 分後、猫に関するビデオを XNUMX つ視聴します。

Q: 全てをやり遂げました。 さらにコメントを追加しました。
P:見せてよ!

Dockerfile の最新バージョン:

FROM ubuntu:latest

# Копируем исходный код
COPY ./ /app
WORKDIR /app

# Обновляем список пакетов
RUN apt-get update 

# Обновляем пакеты
RUN apt-get upgrade

# Устанавливаем нужные пакеты
RUN apt-get -y install libpq-dev imagemagick gsfonts ruby-full ssh supervisor

# Устанавливаем bundler
RUN gem install bundler

# Устанавливаем nodejs используется для сборки статики
RUN curl -sL https://deb.nodesource.com/setup_9.x | sudo bash -
RUN apt-get install -y nodejs

# Устанавливаем зависимости
RUN bundle install --without development test --path vendor/bundle

# Чистим за собой кэши
RUN rm -rf /usr/local/bundle/cache/*.gem 
RUN apt-get clean 
RUN rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/* 

# Запускаем скрипт, при старте контейнера, который запустит все остальное.
CMD [“/app/init.sh”]

P: 素晴らしい、気に入っています。 コメントはロシア語で、便利で読みやすく、誰もがそのように機能します。 私が全部教えたので、残りは自分でやってください。 コーヒーを飲みに行きましょう...

さて、これで完全にひどい Dockerfile が出来上がりました。Igor Ivanovich はそれを見ると辞めたくなり、一週間は目が痛くなるでしょう。 もちろん、Dockerfile はさらに悪い可能性があり、完璧には限界がありません。 しかし、最初はこれで十分です。

最後にグリゴリー・オスターの言葉を引用して終わりたいと思います。

まだわからない場合は
私たちが選んだ人生の道は、
そして、あなたはその理由を知りません
出産の旅を始めましょう。
廊下の電球を割る -
人々はあなたに「ありがとう」と言うでしょう。
あなたは人々を助けるでしょう
電気を節約。

出所: habr.com

コメントを追加します