تخطَّ إلى المحتوى
QuenchWorks

بناء تطبيق .NET

لا يحتاج تطبيق .NET المنشور إلى الـ SDK عند التشغيل، بل إلى بيئة التشغيل المطابقة فقط. لذا نفّذ dotnet publish في مرحلة البناء بصورة الـ SDK، ثم شغّل المخرجات المنشورة على أساس التشغيل النحيل: aspnet لتطبيقات الويب وواجهات البرمجة، وdotnet-runtime لتطبيقات سطر الأوامر والعُمّال. يبقى الـ SDK وذاكرة NuGet خلفهما في مرحلة البناء.

يبني هذا على ghcr.io/quenchworks/images/dotnet:10 (الـ SDK)، ثم يشغّل على ghcr.io/quenchworks/images/aspnet:10 أو ghcr.io/quenchworks/images/dotnet-runtime:10. أبقِ خط التشغيل مطابقًا للـ SDK الذي بنيت به.

ملف Dockerfile المتعدد المراحل

# Build stage: restore, then publish the app.
FROM ghcr.io/quenchworks/images/dotnet:10 AS build
WORKDIR /src
# Restore first so the layer caches when only code changes.
COPY ["App.csproj", "./"]
RUN ["dotnet", "restore", "App.csproj"]
COPY . .
RUN ["dotnet", "publish", "App.csproj", "-c", "Release", "-o", "/app/publish", "--no-restore"]
# Runtime stage: ASP.NET Core runtime, nonroot.
FROM ghcr.io/quenchworks/images/aspnet:10 AS runtime
WORKDIR /app
ENV ASPNETCORE_URLS=http://+:8080
COPY --from=build /app/publish ./
USER 1001
EXPOSE 8080
ENTRYPOINT ["dotnet", "App.dll"]
# Build stage: restore, then publish the worker/console app.
FROM ghcr.io/quenchworks/images/dotnet:10 AS build
WORKDIR /src
COPY ["Worker.csproj", "./"]
RUN ["dotnet", "restore", "Worker.csproj"]
COPY . .
RUN ["dotnet", "publish", "Worker.csproj", "-c", "Release", "-o", "/app/publish", "--no-restore"]
# Runtime stage: the plain .NET runtime, no ASP.NET Core stack.
FROM ghcr.io/quenchworks/images/dotnet-runtime:10 AS runtime
WORKDIR /app
COPY --from=build /app/publish ./
USER 1001
ENTRYPOINT ["dotnet", "Worker.dll"]

ماذا تفعل كل مرحلة

  1. البناء. صورة dotnet هي الـ SDK الكامل. استعِد قبل نسخ بقية المصدر كي تُخزَّن تلك الطبقة، ثم نفّذ dotnet publish بوضع Release إلى مجلّد ثابت. يبقى الـ SDK وذاكرة NuGet والمصدر في هذه المرحلة.
  2. التشغيل. ابدأ من aspnet (للويب) أو dotnet-runtime (لسطر الأوامر)، وانسخ مخرجات النشر، وانزل إلى uid 1001، وشغّل تجميعة الدخول. لا يُشحن أي SDK.

التالي

  • لأصغر بصمة، انشر تطبيقًا مكتفيًا ذاتيًا ومقلّمًا وشغّله على أساس تشغيل، أو جمّع تطبيق سطر أوامر بـ AOT إلى ملف ثنائي أصلي واشحنه على static.
  • ثبّت بالبصمة الرقمية ليجري كل بناء بالضبط على الأساس الذي جرى فحصه وتوقيعه.