Macで .NET Core+NginxをDockerで動かしてみた

はじめまして。プラットフォームチームの青木です。

初投稿です。

簡単に自己紹介させていただきますと、 自分はテックリードとして活動しておりまして、新規プロダクトのアーキテクチャの選定や導入を行っています。

またvisumo(ビジュモ)という、Webサービスの開発も担当していて、スクラムマスターとして開発チームの運営やファシをしています。

ちなみにプライベートではスマートホーム化をはじめ、 4KプロジェクターとかFire stick 4Kを購入して、インドアライフを満喫しています!

このあたりのことはそのうち別途記事にしていこうかと思ってますので、ご興味ある方はチラ見いただけますと嬉しいです!

visumo.asia

はじめに

さて今回は「やってみた」シリーズです。

タイトルの通り、MacでASP.NET Core + Nginx でDockerコンテナを実行しWebページが表示されるまでの流れを紹介します。

普段はWindows版のVisual Studioで開発を行っているのですが、プライベートではMacをメインで使っています。 .NET Coreはクロスプラットフォーム対応なので、試す意味でもMacでASP.NET Coreのアプリケーション構築をやってみようと思います!

.NET Coreについては是非こちらを参照してください! blog.ecbeing.tech

環境

  • macOS Mojave
  • Docker Desktop 2.0.0.2

ディレクトリ構成

最終的にはこんな感じのディレクトリ構成になります。

/app
|--docker-compose.yml
|--helloworld_netcore
|  |--Dockerfile
|  |--Models
|  |--Views
|  |--appsettings.Development.json
|  |--appsettings.json
|  |--bin
|  |--helloworld_netcore.csproj
|  |--wwwroot
|--nginx
|  |--Dockerfile
|  |--default.conf

.Net Core SDKのダウンロード&インストール

はじめに、.NET Core SDKをMacにインストールします。

dotnet.microsoft.com

バージョンはv2.2(2019/04/03現在)をダウンロードしました。

正しくインストールされていれば、ターミナルでバージョンを確認することができます。

$ dotnet --version

.Net Coreアプリの作成と実行

まずは、.NET CoreのWebアプリケーションを作成しましょう。 今回は、.Net Core CLIでシンプルなWebアプリケーションを作成します。

[dir]/app/

$ dotnet new mvc -o helloworld_netcore

dotnet newは、.NET Core MVCでhelloworld_netcoreというアプリケーションのテンプレートを出力する命令です。

こんな感じでプロジェクトファイルやcsファイルが生成されてればOKです。

f:id:ecb_yaoki:20190403175241p:plain

つづいて、ちゃんと動くかアプリケーションをビルドして実行しましょう!

[dir] /app/helloworld_netcore/

$ dotnet run

たったこれだけで、.NET Coreアプリが動きます。 dotnet runだけでビルドと実行を同時にやってくれますので超ラクチンです!

アプリケーションログは以下の通り。

info: Microsoft.AspNetCore.DataProtection.KeyManagement.XmlKeyManager[0]
      User profile is available. Using '/Users/XXXX/.aspnet/DataProtection-Keys' as key repository; keys will not be encrypted at rest.
Hosting environment: Development
Content root path: /app/helloworld_netcore
Now listening on: https://localhost:5001
Now listening on: http://localhost:5000
Application started. Press Ctrl+C to shut down.

見ての通り、5000, 5001ポートをlistenします。 http://localhost:5000にアクセスすると、.NET CoreのシンプルなWebアプリが表示されます。

f:id:ecb_yaoki:20190403182505p:plain

確認したら、Ctrl + Cでアプリケーションをシャットダウンしてください

.Net Core アプリのイメージ化

つづいて、Dockerで動かすために.NET Coreアプリをイメージ化します。

Dockerfileを用意しましょう。

[file] /app/helloworld_netcore/Dockerfile

# .NET Coreの実行環境のイメージ
FROM microsoft/dotnet:2.2-aspnetcore-runtime AS base
WORKDIR /app

# 5000ポートで受け付けるように設定する
ENV ASPNETCORE_URLS http://+:5000
EXPOSE 5000

# .NET Coreのビルド環境のイメージ
FROM microsoft/dotnet:2.2-sdk AS publish
WORKDIR /src
COPY . .

# ビルド環境でソースコードをビルドし、実行に必要な依存関係を含めて出力
RUN dotnet publish -c Release -o /out

FROM base AS final
WORKDIR /app

# .NET Coreの実行環境へビルド結果をコピーする
COPY --from=publish /out .

# .NET Coreのアプリを実行する
CMD ["dotnet", "/app/helloworld_netcore.dll"]

ポイントは、ビルド環境と実行環境のイメージを分けているという点です。 ビルド環境のイメージは2GBほどですので、イメージを小さくするためには、実行環境へビルド結果のみをコピーするという設定が必要です。

f:id:ecb_yaoki:20190405164608p:plain

それではdocker buildでイメージを作成してみましょう。

[dir] /app/helloworld_netcore/

$ docker build ./ -t helloworld_netcore

つづいて、.NET CoreアプリのDockerコンテナを実行しましょう。 http://localhost:5000でアクセスすると、Docker上で動いているのが確認できると思います。

$ docker run —rm -it -p 5000:5000 helloworld_netcore

Nginxのイメージ化

今度は、WebサーバーであるNginxのDockerfileを用意します。

見ての通り、Nginxの設定default.confをコピーしてイメージ化するだけです。

[file] /app/nginx/Dockerfile

FROM nginx:latest
COPY default.conf /etc/nginx/conf.d

今回はシンプルに80ポートでlisthenするようにして、すべてのリクエストを.NET Coreアプリに投げつけるようにしました。

[file] /app/nginx/default.conf

server {
    listen 80 default_server;
    listen [::]:80 default_server;
    location / {
        proxy_pass         http://webapp:5000;
    }
}

docker-compose.ymlでコンテナを管理

docker-compose.ymlは、複数のコンテナを一元管理することができます。 今回は、Nginxと.NET Coreアプリを同時に実行するので、以下のように設定してみました。

[file] /app/docker-compose.yml

version: '3'
services:
  nginx:
    build: ./nginx
    image: 'my_nginx'
    container_name: 'my_nginx'
    ports:
    - "80:80"
  webapp:
    build: ./helloworld_netcore
    image: 'my_webapp'
    container_name: 'my_webapp'
    ports:
    - "5000:5000"

docker-compose.ymlはbuildでDockerfileの場所を指定していて、 あとはdocker runのオプション部分を指定します。

完成!!

最後はdocker-composeを実行するだけで、いい感じにコンテナが起動します。 Nginx→.Net Coreにproxyしていますので、http://localhostへアクセスでOKです。

[dir] /app/

$ docker-compose up -d

まとめ

いかがでしたか? .NET CoreはイメージがDocker Hubで公式サポートされてるので、わずかなステップでコンテナ上に乗せることが出来ました!

Dockerを使うと本番環境との開発環境の差が限りなく少なくできますし、 デバッグもめっさ楽になると思います。

ちなみに、現在 Docker+.NET Core(AWS上) で新規アプリを絶賛開発中です!公開できるタイミングが来ましたら、これも記事にしていきたいと思います。

ふと思ったこと...

実際、Macで.NET Core開発している方はどれくらいいるのだろうか? Visual Studio For MacやVisual Studio Codeを使えば、エディットとデバッグ実行ぐらいは簡単にできるけど、コード分析ツールとか差異は結構ありそうな予感。

それでは、この辺で!

青木

~ただいまガジェット好き .NET系エンジニアを絶賛募集中です!!~ www.softcreate-holdings.co.jp