Docker: ASP.NET Core Uygulamalarını Dockerize Etmek
Merhaba sevgili okur,
ASP.NET Core’da yazılmış bir uygulama için nasıl docker image’ı oluşturabileceğinizi anlatmaya çalışacağım. Bir önce ki yazım da Docker: Dockerfile ile Image Oluşturmak’ı paylaşmıştım. Keyifli okumalar.
Hemen başlayalım; “dotnet cli”yı kullanarak bir web api projesi oluşturalım.
dotnet new webapi --name "MyApp"
Uygulamayı çalıştıralım
Uygulamayı test amaçlı çalıştıralım ve devam edelim.
dotnet run
Dockerfile
Uygulamamızın ana dizinine Dockerfile dosyasını ekleyelim. Temel (base) image tanımımızı yapacağız.
# Dockerfile
# Builder
FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS builder
Not: Microsoft resmi image’larını Dockerhub üzerinden paylaştığı gibi aynı zaman da kendi container registry’si üzerinden de paylaşıyor.
Not: Temel (base) image’mıza dikkatli baktığımızda bir ASP.NET Core SDK’sı olduğu anlaşılıyor. Fakat bizim uygulamamızın çalışması için ASP.NET Core Runtime’ı yeterli iken neden SDK image’ını kullanıyoruz. Aslında yerine değil, birlikte. SDK image’ını uygulamayı derlemek için, Runtime image’ını ise uygulamayı çalıştırmak için kullanacağız. Detaylı bilgi için dokümantasyon sayfasına göz atabilirsiniz. (keyword: multi-stage)
Not: Uygulamanızı kendi bilgisayarınızda belirli işletim sistemleri için kişileştirilmiş ayarlar ile derleyebilir ve bu çıktılar üzerinden de image oluşturabilirsiniz. Fakat bu yöntem tavsiye edilmiyor!
Not: ASP.NET Core uygulamalarını Runtime’ı ile birlikte paketlemek ve yayınlamak mümkündür. Fakat dosya boyutunu ciddi oranda artıracaktır.
Konteyner’da ki çalışma dizinini “/source” olarak ayarlayalım. İsimlendirme tamamen sizin insiyatifinize kalmış. Bu dizini uygulama kaynak kodlarını kopyalamak için kullanacağız.
# Dockerfile
# Builder
FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS builder
WORKDIR /source
Uygulama kaynak kodlarını “/source” dizinine kopyalayalım.
# Dockerfile
# Builder
FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS builder
WORKDIR /source
COPY src/ .
Not: Geliştirme (development) ortamında kopyalama işlemi yapacağımız için, uygulama dizini içerisinde çalışma zamanından kalan dosyalar, geliştirme (development) ortamına ait ayar dosyaları veya code editörüne ait istenmeyen dosyalar olabilir. Bunlara benzer istenmeyen veya ihtiyaç olmayan dosyaları konteyner içine kopyalamak istemeyebilirsiniz. Problemi çözmek adına uygulamamızın ana dizinine “.dockerignore” dosyasını ekleyelim ve konteyner’a aktarmak istemediğimiz dosyaları belirleyelim.
# .dockerignore
.git
.gitignore
.vscode
Dockerfile
README.md
**/.DS_Store
Image’ın temelini oluşturan işletim sistemi (minimal) üzerinde bulunan paketleri güncelleyelim. Bu adım uygulamaların ihtiyaç duyabileceği paketlerin yüklenebilmesi veya güncellenmesi için örnek olarak eklenmiştir.
# Dockerfile
# Builder
FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS builder
WORKDIR /source
COPY src/ .
RUN apt update
Kaynak kodlarımız artık konteyner içinde olduğuna göre derleme aşamasına geçebiliriz. Konteyner’da ki çalışma dizinini “/source/MyApp” olarak değiştirelim. Burada ki dizin sizin uygulamızın ana dizinidir.
# Dockerfile
# Builder
FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS builder
WORKDIR /source
COPY src/ .
RUN apt update
WORKDIR /source/MyApp
Uygulamamızı restore edelim.
# Dockerfile
# Builder
FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS builder
WORKDIR /source
COPY src/ .
RUN apt update
WORKDIR /source/MyApp
RUN dotnet restore MyApp.csproj
Uygulamayı “/app” dizini altına publish alalım.
# Dockerfile
# Builder
FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS builder
WORKDIR /source
COPY src/ .
RUN apt update
WORKDIR /source/MyApp
RUN dotnet restore MyApp.csproj
RUN dotnet publish MyApp.csproj --output /app/ --configuration Release
Evet uygulamamız artık yayınlamaya hazır hale geldi. Şimdi asıl image’ı oluşturacak dockerfile talimatlarına geçelim. Temel (base) image tanımımızı yapalım.
# Dockerfile
# Builder
FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS builder
WORKDIR /source
COPY src/ .
RUN apt update
WORKDIR /source/MyApp
RUN dotnet restore MyApp.csproj
RUN dotnet publish MyApp.csproj --output /app/ --configuration Release
# ------------------------------------------------------------
# Runtime
FROM mcr.microsoft.com/dotnet/core/aspnet:3.1 AS runtime
Konteyner’da ki çalışma dizinini “/app” olarak ayarlayalım.
# Dockerfile
# Builder
FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS builder
WORKDIR /source
COPY src/ .
RUN apt update
WORKDIR /source/MyApp
RUN dotnet restore MyApp.csproj
RUN dotnet publish MyApp.csproj --output /app/ --configuration Release
# ------------------------------------------------------------
# Runtime
FROM mcr.microsoft.com/dotnet/core/aspnet:3.1 AS runtime
WORKDIR /app
Önceki katmanlar da publish işlemini halletmiştik. Şimdi bu işlemlerin sonucunda oluşan derlenmiş uygulamamızı “/app” dizinine kopyalayalım.
# Dockerfile
# Builder
FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS builder
WORKDIR /source
COPY src/ .
RUN apt update
WORKDIR /source/MyApp
RUN dotnet restore MyApp.csproj
RUN dotnet publish MyApp.csproj --output /app/ --configuration Release
# ------------------------------------------------------------
# Runtime
FROM mcr.microsoft.com/dotnet/core/aspnet:3.1 AS runtime
WORKDIR /app
COPY --from=builder /app .
Konteyner başlatılırken çalışacak olan komutları ekliyoruz.
# Dockerfile
# Builder
FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS builder
WORKDIR /source
COPY src/ .
RUN apt update
WORKDIR /source/MyApp
RUN dotnet restore MyApp.csproj
RUN dotnet publish MyApp.csproj --output /app/ --configuration Release
# ------------------------------------------------------------
# Runtime
FROM mcr.microsoft.com/dotnet/core/aspnet:3.1 AS runtime
WORKDIR /app
COPY --from=builder /app .
Dockerize Edelim
Dockerfile’mız hazır olduğuna göre artık dockerize etme kısmına geçebiliriz. “docker build” komutunu çalıştırarak image oluşturmakla başlayalım.
docker build -t anilatalay/my_dotnetcore_app:1.0.1 .
Artık uygulamamızın bir image’ı mevcut, bu image’ı kullanarak bir konteyner oluştuyoruz.
docker run --rm -p 8080:80 anilatalay/my_dotnetcore_app:1.0.1
Uygulama konteyner içinde “8080” portunu kullanırken dışarıya “80” portu üzerinden yayınlanıyor. (http://localhost:8080/WeatherForecast)
Uygulama Image’nı Paylaşalım
Docker cli üzerinden dockerhub’a giriş yapıyoruz.
docker login
Dockerhub’a image’mızı gönderiyoruz.
docker push anilatalay/my_dotnetcore_app
Hayırlı olsun. Dockerhub üzerinde nur topu gibi image’mız var. (hub.docker.com) Artık isteyen herkes image’mızı çekebilir :)
Öğrenilecek çok şey, gezilecek çok yer var. Bir sonraki postumda görüşmek üzere.