Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Azure_Container_as_a_Service_v0.2.24.0301.pdf

 Azure_Container_as_a_Service_v0.2.24.0301.pdf

これからコンテナ技術に取り組むアプリケーション開発者向けの勉強会スライドです。
コンテナの基礎からクラウドサービス(Azure)へのデプロイまでを紹介しています。

Ayumu Inaba

March 11, 2024
Tweet

More Decks by Ayumu Inaba

Other Decks in Technology

Transcript

  1. Agenda コンテナ技術の概要 Azure のコンテナサービス DEMO : ASP.NET on Web App

    for Container Appendix コンテナアプリ開発のお作法 オーケストレーターを意識した開発 2
  2. Why Container ? 4 ‘Write-once, Run-anywhere’ マイクロサービス アーキテクチャ対応 Dev/Test の効率化

    確実な Production 環境の配置 Developer Community の成長 アプリケーションのポータビリティ 開発, QA, 運用環境の標準化 OS やインフラ環境の抽象化 リソース配分の最適化 高速起動、スケーラビリティの確保 DevOps Developers Operations
  3. コンテナと仮想マシンの違い 7 ハードウェア ハイパーバイザー (Hyper-V、vSphereなど) 仮想マシン 仮想マシン OSカーネル OSカーネル コンテナー

    コンテナー ランタイム/ ライブラリー アプリ ランタイム/ ライブラリー ランタイム/ ライブラリー アプリ アプリ 分離 コンテナーイメージ 軽量 再利用 ランタイム/ ライブラリー アプリ
  4. Docker コンテナー UNIX、BSD、Linuxの世界でコンテナー技術は昔からあった OSの各種リソース管理機能を活用してリソースを分離する dotCloud (現 Docker) 社が自社 PaaS 向けに作ったコンテナー

    の仕組みを OSS にしてブレイク アプリ開発者視点でうれしい機能、周辺ツールに力を入れている イメージ作成、配布の仕組み、差分イメージ形式など 標準化の勢いで Docker の影響力は 弱まりつつあるが広く普及している 8 OS カーネル コンテナー コンテナー ランタイム/ ライブラリー ランタイム/ ライブラリー アプリ アプリ 分離 コンテナーイメージ
  5. コンテナーイメージ コンテナーは コンテナー“イメージ” を元に生成・実行される コンテナーイメージはベースイメージにライブラリやランタ イムを重ねて作る(レイヤー) 重ねるレイヤーは Dockerfile と呼ばれる定義ファイルに 記載してソースコードとして管理

    Dockerfile にはイメージに含めるライブラリ、アプリ、環 境変数、実行コマンドなどを指定 Dockerfile をビルドすると新しいイメージが作成される このレイヤのすべてを開発する必要は ない Web サーバー、ランタイム、アプリなどがインストール済 みの様々なイメージがベンダー各社から公開されている 「自分で開発したアプリ」の動作要件を満たすコンテナイ メージがあればすぐに動かすことが出来る 9 debian:stretch-slim Python:3.6.2-slim html2test, urllib3, sh wordcount.py build build build
  6. Dockerfile サンプル FROM mcr.microsoft.com/dotnet/core/sdk:3.0 WORKDIR /src COPY . . RUN

    dotnet publish -c Release -o /app WORKDIR /app ENV ASPNETCORE_URLS http://+:80 EXPOSE 80 ENTRYPOINT ["dotnet", "docker-demo.dll"] 10 Dockerfile は単なるテキストファイル > ソースコードとセットでバージョン管理と共有が良い > 開発者間や各種実行環境間での再現性の悩みが減る Dockerfile のイメージを紹介するために、ソースコー ドのビルドから実行までを単一コンテナにしているが、 これ自体は良い例ではないので注意 SDK 入りのイメージをベースに ソースをコンテナ内にコピー 実行環境を整えて 起動方法を指示しておく ソースをビルドしてアプリを生成
  7. Public / Private Container Registry Docker Hub Docker 社が運営するコンテナを公開・共有するた めのサービス

    各企業が提供する公式イメージなども多く公開され ている https://hub.docker.com Azure Container Registry コンテナイメージを共有するための Azure の 1 サー ビス(有償) アクセスコントロールによって非公開のレジストリとし て使用する https://myreg.azurecr.io 12 Basic Standard Premium エンタープライズ用途
  8. 開発からデプロイまで 13 ubuntu:17.04 FROM ubuntu:17.04 RUN apt-get –y update RUN

    apt-get install nginx MyWeb:1.0 MyApp:1.0 FROM MyWeb:1.0 RUN git clone https://... RUN dotnet build … RUN dotnet run … From Push Dockerfile Dockerfile Private Registry オンプレミス Azure Virtual Machine Kubernates Service Service Fabric Web App for Container Container Instances Functions Laptop Mobile Servers Azure Stack IoT Edge Any Clouds From Push 宣言的な記述 再実行が容易 Deploy Anywhere 再現性が保証されたイメージを管理 Public Registry Build Build
  9. コンテナアプリの保守 コンテナのバージョンアップは新しいコンテナ イメージを作り 直して「タグ」で区別して世代管理 運用中のコンテナの中を弄ったり、既存のイメージを修正するのではない(してはならない) バグ修正や新機能の追加など、アプリを修正したら、同じ Dockerfile を使ってビルド ランタイムやミドルウェア等のバージョンアップは Dockerfile

    の修正で表現してビルド 14 FROM ベースイメージ RUN 各種インストール COPY アプリコンテンツ ENTRYPOINT 起動処理 Dockerfile Source Source Source Source アプリとランタイム等の一貫性 MyApp:v1 MyApp:v2 Build & Push Deploy (Pull) イメージが不変⇒整合性や再現性を担保 Registry SCM
  10. アプリ開発者からみたメリット アプリの起動が速く、簡単で、再現性が高い 仮想マシンだと OS、ランタイム、ライブラリ、アプリのバージョンを一致させてインストール コンテナなら docker run の 1 行

    インストールが混じらないので依存関係地獄から解放される マシンインスタンス上で複数種・複数バージョンのアプリやライブラリを分離できる 導入先のマシンの環境を壊さない(コンテナにすべて含まれている) 開発のスピードが速く、運用も楽になる 性能拡張をしたいときは同じイメージからコンテナを複製して負荷分散 短時間で元の環境に戻せるので回復性も高く 15
  11. コンテナの利用例 : スケーラブル アプリケーション コンテナのポータビリティやステートレス特性は、スケーラブル なクラウド環境と相性が良い WebUI や API のエンドポイントとして、バックグラウンド

    ジョブやイベント駆動型処理として、 高集約性とオーケストレーションを求められるマイクロサービスとして、etc… 16 Public API endpoints Background processing Event-driven processing Microservices HTTP TRAFFIC REVISION 2 REVISION 1 80% 20% MICROSERVICE B MICROSERVICE C MICROSERVICE A データベース内のデータを 変換する連続実行バック グラウンドプロセスなど メッセージがキューに到着 したときにメッセージを処 理するキュー・リーダー・ア プリケーションなど Dapr と統合するオプショ ンを使用してマイクロサー ビスアーキテクチャをデプロ イおよび管理 Web Applications 頻繁なスケールアウト/スケールインを求められる HTTP(S) ベースの Web アプリや API の実行環境 として
  12. コンテナの利用例 : Dev Container アプリ開発に必要な Runtime だけでなく SDK や各種ツール群も 含めてコンテナ化して開発環境を綺麗に保つ

    Visual Studio Code をコンテナに接続することで、1端末で複数の開発環境の共存が容易に コンテナ自体は GitHub Codespaces 上で動かせば端末そのものはさらにクリーンに 17 Visual Studio Code Windows / MacOS /Linux 占有 Runtime SDK, Tool Source Code Source Code Runtime SDK, Tool Source Code Source Code Container Runtime Runtime SDK, Tool Source Code Source Code GitHub Codespaces
  13. コンテナの利用例 : Azure Cloud Shell Web ブラウザ上で実行できるコマンドラインインタフェース Azure や各種アプリの管理操作に必要な各種ツールの最新版が常にセットアップ済み 永続化したいファイルは

    Azure Files に保存することで、コンテナはステートレスに 18 ブラウザ ユーザー コンテナ Azure Files コンテナ イメージ From Ubuntu Bash, sh, tmux, dig, Azure CLI, AzCopy, vim, nano, git, make, maven, kubectl, sqlcmd, iPython client, .NET core, Go, Java, Node.js, Ansible, etc… アタッチ マウント Pull ホストマシン不要 = 保守・運用コストが不要
  14. コンテナー導入の主なメリットとチャレンジ メリット 起動時間が早くなる。 ⇒ パフォーマンス改善につながる ソフトウェアのライフサイクル管理が容易になる。⇒ アプリ運用が楽になる 可搬性と移植性が高く、開発の自由度が高まる。 ⇒ 移動が楽になる

    個別に専有するリソースが少なくて済む。⇒ インフラコストが下がる チャレンジ コンテナー環境導入や新たな技術習得に伴う必要なリソースとコスト インフラ運用体制の見直し (アプリチームとインフラチームの役割分担の再考) 既存アプリケーションのリファクタリング (コンテナー環境変数への変換) 19
  15. [補足]アプリ配布における仮想マシンの課題 事前セットアップ方式 あらかじめアプリ等をセットアップ済みの VM イ メージを作成(面倒) イメージサイズが大きく、デプロイに時間がかかる デプロイ後セットアップ方式 VM起動後に毎回セットアップが行われるので利 用開始までに時間がかかる

    セットアップ後のテストが難しい 20 ホストマシン 仮想マシン アプリ、ライブ ラリ、ランタイム、 etc… カスタム VM イメージ セットアップ デプロイ マスター VM イメージ ホストマシン 仮想マシン デプロイ アプリ、ライブ ラリ、ランタイム、 etc… セットアップ コンテナ技術によって緩和可能なアプローチ コンテナではあまりやらないアプローチ
  16. CaaS Container Platform Container as a Service PaaS Application Platform

    FaaS Serverless Platform IaaS Infrastructure Platform More Control of execution environment Less Agile development & deployment Less Control of execution environment More Agile development & deployment
  17. コンテナー(標準デプロイ単位)と Azure CaaS 26 Azure App Service Azure Container Instances

    Azure Functions Azure Spring Apps Azure Red Hat OpenShift Azure Kubernetes Service Azure Container Apps Container Apps と他の Azure コンテナー オプションの比較 | Microsoft Docs Azure Batch
  18. コンテナ オーケストレーター デファクトの Kubernates をマネージド サービスとして提供 AKS : Azure Kubernates

    Service 27 コンテナのノードへの 自動配置 コンテナの(再)スケジュール 障害ノード上のコンテナ復旧 手動スケール/オートスケール サービスを DNS 名で解決 自動的な負荷分散 シークレット文字列・設定管理 バッチ実行の管理 自動ローリングアップデート ロールバック Azure 等クラウドストレージ NFS/iSCSI/Gluster 等のマウント Kubernetes core concepts for AKS https://docs.microsoft.com/azure/aks/concepts-clusters-workloads コンテナアプリ
  19. [余談] Microsoft のキーマン 28 Brendan Burns Kubernetesの生みの親 (Co-founder) 2016年にマイクロソフトへ加わる コンテナー関連サービスのみならず、

    Azure Resource Manager、Azure Cloud ShellなどAzureの開発を広く リード Brendan Burns Distinguished Engineer, Microsoft
  20. IaaS の自由度 + PaaS の利便性 29 Infrastructure Host OS Container

    Runtime Infrastructure Host OS Container Runtime Infrastructure Host OS Container Runtime ストレージ サーバー ネットワーク OS ミドルウエア ハイパバイザ ランタイム アプリケーション データ ストレージ サーバー ネットワーク OS ハイパバイザ ランタイム アプリケーション データ ミドルウエア Container Platform IaaS PaaS ミドルウェア ランタイム アプリケーション データ Container Scalability, Reliability, Portability, etc… 依存関係地獄 からの解放 開発制約条件 からの解放
  21. Backend as a Service と一緒に (不可能ではないが)コンテナにデータを保持すべきではない 永続性の必要な “データ” はコンテナ エコシステムを活かした

    CI/CD やクラウドとしてのス ケーラビリティと相性が悪い せっかくクラウドを使うならば PaaS 系のデータサービスに任せてしまった方が良い 30 Application Platform Virtual Machine Kubernates Service Service Fabric Web App for Container Container Instances Functions Data Services SQL DB MySQL PostgreSQL Storage Cosmos DB ステートレス ステートフル
  22. Production QA DevOps 32 ソースコード レポジトリ ビルド&リリース 公式イメージ コンテナレジストリ IDE

    Local Git IDE Local Git git push docker push docker pull Redis cache Web App for Containers Azure Database CDN Application Insights バグ報告 ユーザー FB トレース・性 能・例外 バックログ docker build 再現
  23. コンテナイメージの構築は Dockerfile で行う Dockerfile で明示的に定義した構成をもとにコンテナイメー ジを構築すべき Dockerfile は誰でも再構築と再現が可能となるように、明確な構成管理と自動構築を可能 にするテキストファイル 技術的にはコンテナ内で手動で変更したファイルや設定を

    docker commit コマンドでイ メージとして固めることも可能だが、構成管理が秘伝のタレになるため避けるべき 実行環境の構築が「パラメーターシートと設定手順書」で行われているアプリの場合は、スク リプトで自動化する方式変更が必要になる 36 設定手順書 構築 マニュアル 属人的な ノウハウ 一子相伝 Windows 界隈は GUI ベースの手順書で成立している ケースが多く、Dockerfile 化が困難な場合も多い FROM BaseImage:v1 RUN Install-Commands COPY . . ENV XXX=YYY EXPOSE ZZZ ENTRYPOINT [“run”] docker build 再現性、説明責任、 構築容易、共有可能、 変更管理、一貫性、 レビュー、etc… Dockerfile
  24. コンテナ イメージはイミュータブル(不変)に リポジトリに Push したイメージは基本的に削除せず、実行環 境でそのまま利用し、修正を行わない コンテナイメージはタグでバージョン管理され、それを基盤として品質管理とリリース判定が 行われるため、「変更」すること自体が危険(再現性を失う) アプリや Dockerfile

    でバグが発見された場合も、修正後に新たなコンテナイメージとしてビ ルドし、品質評価と出荷判定を行う イメージの構築(Build)と同様にデプロイと実行(Run)も容易であるため、コンテナそのもの を大事に保守・運用して育てることなく使い捨てる 37 リポジトリ タグ 更新日 テスト Pass 出荷判定 本番展開 MyApp v1 2023-12-25 70% × - MyApp v2 2024-01-22 98% ◦ 済 MyApp v3 2024-02-24 85% × - YourApi v1 2023-11-13 100% ◦ 済 YourApi v2 2024-02-11 96% ◦ 未 build & push Deploy
  25. タグの名前はルールを定めて明確に イメージにつける“タグ”はバージョン管理として重要な意味を持つ ため明確なルールを定めておく タグはそのコンテナに含まれるベースイメージ + 追加パッケージ + アプリのバージョンなどの一貫性 を含んだバージョンを表す文字列 ある環境に配置されているバージョン、あるバグが発見されたバージョン、修正が行われたバージョン

    など、品質管理の観点からきわめて重要な情報 特に最新版を表し既定値でもある “latest” タグは使用しないこと(実質的にバージョン不明にな る) タグの命名規則として保守・運用で分かりやすいルールを定めると よい セマンティック バージョニング : v1.0.0 > v1.1.0 > v1.2.0 > v1.2.1 日付ベースのバージョニング : 2023-12-01 > 2024-01-12-preview > 2024-02-01 タグ自体の表現能力は弱いので、git のコミット ID や タグ、ビルドシステムのビルド ID などと関連 付けておくとよい 38
  26. コンテナイメージはなるべく小さくしよう コンテナの生成・破棄が頻繁に行われるスケーラブルな環境 では小さいイメージが正義 この傾向はサーバーレス環境で特に顕著になり、大きなイメージは Pull > Run に時間がか かるためコールドスタート問題を引き起こす コンテナサイズや実行時サイズに対する従量課金の場合は、大きいというだけで余分にお金

    がかかる コンテナイメージを小さく保つテクニックは様々だが、代表的な ものを押さえておくと良い 小さなベースイメージを選択する レイヤー数を少なく維持する 実行時に必要最低限のモノをインストールする マルチステージビルドを使用する 39
  27. ベースイメージから小さく Build して生成したコンテナイメージが FROM 命令で指定する ベースイメージのサイズを下回ることはない スタート地点となるベースイメージから小さなものを使用して肥大化を抑えるとよい ベースが小さい=余分なものが少ない=アタックサーフェスが狭く脆弱性が見つかるリスクも小さい アプリ実行に必要な依存関係やデバッグに必要になるツール類などを別途インストールする必要はあ るので、利便性とサイズのバランスを取ること

    40 REPOSITORY TAG IMAGE ID CREATED SIZE mcr.microsoft.com/dotnet/aspnet 8.0 c39d0b5b530f 7 weeks ago 217MB redis latest 3ceffe93e5ee 7 weeks ago 138MB debian latest 52f537fe0336 2 weeks ago 117MB ubuntu latest 3db8720ecbf5 2 weeks ago 77.9MB alpine latest 05455a08881e 5 weeks ago 7.38MB gcr.io/distroless/static-debian12 latest 2d37d84052a6 N/A 1.99MB distroless は非常にサイズが小さいが、シェルやパッケージマネージャーすら含まれていない
  28. マルチ ステージ ビルドを使おう アプリをビルドするための SDK やツール類は実行時には必 要ないので含めないこと マルチ ステージ ビルドというテクニックを使用することで、ビルドシステムにもコンテナのメリッ

    トを適用することが出来る 障害調査やデバッグに必要なツールは後からインストールしても持ち込むことが可能な場合 もあるので、「事前インストールすべきか」は考慮するとよい 42 FROM mcr.microsoft.com/dotnet/core/sdk:3.0 WORKDIR /src COPY . . RUN dotnet publish -c Release -o /app WORKDIR /app ENV ASPNETCORE_URLS http://+:80 EXPOSE 80 ENTRYPOINT ["dotnet", "docker-demo.dll"] FROM mcr.microsoft.com/dotnet/core/sdk:3.0 AS build WORKDIR /src COPY . . RUN dotnet publish -c Release -o /app FROM mcr.microsoft.com/dotnet/core/aspnet:3.0 WORKDIR /app COPY --from=build /app ./ ENV ASPNETCORE_URLS http://+:80 EXPOSE 80 ENTRYPOINT ["dotnet", "docker-demo.dll"] Dockerfile Dockerfile(マルチステージ) SDK ツール、ソースコード、コン パイル時の一時ファイルなどが コンテナイメージ内に残存 SDK ツール、ソースコード、コン パイル時の一時ファイルなどは ビルド用のコンテナに ランタイムとアプリコンテンツ のみのイメージを作成
  29. 1コンテナ:1プロセスの原則を守ろう 1つのコンテナ内で複数のプロセスを起動すべきではない コンテナは Entrypoint や CMD で起動された最初のプロセス(PID=1)とライフサイクルが一致す る仕組みになっている オーケストレーターは基本的に PID1のプロセスが実行されているか否かで、コンテナが正常に実行

    されている状態か否かを判断する またオーケストレーターがスケールインが必要と判断した場合は、PID1のプロセスに SIGTERM が 送信されコンテナを終了させようとする(=それ以外は完治しない) マルチプロセス コンテナの場合は PID1のプロセスがサブプロセスのライフサイクルを管理する責務 を担うことになり、実装が複雑化してしまう 45 PID=1 PID=X PID=Y コンテナ オーケストレーター 管理 大丈夫?
  30. 正常性プローブに対応しよう オーケストレーターは正常性プローブを使用してコンテナアプリが 「正常な状態か」をより詳しく判定することが出来る 前述の通りプロセスの生死判定だけでは、アプリとしての正常性を的確に判断することは出来ないこ とが多く、オーケストレーターに追加の情報を与えてやる必要がある オーケストレーターによって正常性の判定方法は様々だが、以下は Kubernetes および(その亜種) で利用可能な判定方法 Liveness

    Prove : アプリが正常に動作可能な状態か否か(フリーズやデッドロックしていないかなど) Readiness Prove : アプリがイングレスなどの負荷分散から処理を受け付けられる状態か否か Startup Prove : 開始処理が終了して Liveness/Readiness Prove を受け付けられるか否か 48 PID=1 起動終わった? 終了コード 開始 元気? 生きてる? 仕事振っていい? 各プローブは HTTP/TCP/コマ ンドを定期的に実行する
  31. Graceful Shutdown に対応しよう オーケストレーターからの終了指示を受けて、安全にプロセス を終了するように実装する オーケストレーターはスケールイン、再配置、メンテナンスなどが必要と判断した場合、コンテ ナに対して SIGERM + SIGKILL

    を送信してコンテナを終了する 実行中のアプリからすれば外部から勝手に強制終了させられることになるため、仕掛かり中 の処理や永続化していないデータがあると問題になる 終了指示を適切にハンドリングすることで安全に終了(Graceful Shutdown)できるように 備えておくべき 50 Σ(゚Д゚) !! オーケストレーター SIGTERM SIGKILL さよなら~
  32. 設定ファイル DB=LOCAL 環境依存設定は環境変数から取得する コンテナはデプロイ先の環境に設定された環境変数から各種設定 を読み込むことで適応的に動作すると良い 開発・テスト・本番の各環境において、外部 API のエンドポイント URL 、データベースの接続文字

    列、ログ出力の詳細度などが代表的な環境依存の設定値 従来は配置時に「設定ファイル」を入れ替えることで対応していたケースも多いが、コンテナ環境では この設定ファイルもコンテナイメージに固められてしまい修正が容易ではない(すべきでもない) 多くのオーケストレーターは各コンテナに対して環境変数を差し込む機能を持っているため、環境変数 から読み込んだ設定値を最優先するようにアプリを開発する 51 Source 設定 ファイル Source build コンテナイメージ Deploy Deploy ENV DB=Test ENV DB=Prod 開発環境
  33. 必要な CPU とメモリを宣言しよう 各コンテナが必要とする最低・最大のリソース量を指定することで、 配置先を適切に判定することが出来る 何も設定しない場合は各コンテナが必要として CPU とメモリを割り当ててしまうため、以下のような 問題が起こりうる リソースを大量消費するコンテナと同じノードで動作するコンテナが性能的な影響を受ける(ノイジーネイバー)

    コンテナが動作するために最低限必要なメモリが確保できないノードにデプロイされてしまい、起動に失敗する CPU やメモリに対して Request/Limit を指定することでオーケストレーターがコンテナのスケジュー ルを管理できるようになる 52 4core/12GB 欲しい 2core/4GB 欲しい 1core/2GB 欲しい 8core/32GB 8core/32GB 8core/32GB OK NG OK NG