diff --git a/docker-compose.admin.yml b/docker-compose.admin.yml index d85c305..bdf4814 100644 --- a/docker-compose.admin.yml +++ b/docker-compose.admin.yml @@ -13,9 +13,11 @@ services: build: context: . dockerfile: docker/admin-api/Dockerfile + extra_hosts: + - "mirror:host-gateway" args: - DOTNET_SDK_IMAGE: ${DOTNET_SDK_IMAGE:-mcr.microsoft.com/dotnet/sdk:10.0} - DOTNET_ASPNET_IMAGE: ${DOTNET_ASPNET_IMAGE:-mcr.microsoft.com/dotnet/aspnet:10.0} + DOTNET_SDK_IMAGE: ${DOTNET_SDK_IMAGE:-171.22.25.73:5002/dotnet/sdk:10.0} + DOTNET_ASPNET_IMAGE: ${DOTNET_ASPNET_IMAGE:-171.22.25.73:5002/dotnet/aspnet:10.0} container_name: meezi-admin-api restart: unless-stopped depends_on: @@ -46,7 +48,11 @@ services: build: context: . dockerfile: docker/admin-web/Dockerfile + extra_hosts: + - "mirror:host-gateway" args: + NODE_IMAGE: ${NODE_IMAGE:-171.22.25.73:5000/library/node:20-alpine} + NPM_REGISTRY: ${NPM_REGISTRY:-http://mirror:8081/repository/npm-group/} NEXT_PUBLIC_ADMIN_API_URL: ${NEXT_PUBLIC_ADMIN_API_URL:-http://localhost:5081} container_name: meezi-admin-web restart: unless-stopped diff --git a/docker-compose.yml b/docker-compose.yml index c5bd71a..da76aea 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -54,9 +54,11 @@ services: build: context: . dockerfile: docker/api/Dockerfile + extra_hosts: + - "mirror:host-gateway" args: - DOTNET_SDK_IMAGE: ${DOTNET_SDK_IMAGE:-mcr.microsoft.com/dotnet/sdk:10.0} - DOTNET_ASPNET_IMAGE: ${DOTNET_ASPNET_IMAGE:-mcr.microsoft.com/dotnet/aspnet:10.0} + DOTNET_SDK_IMAGE: ${DOTNET_SDK_IMAGE:-171.22.25.73:5002/dotnet/sdk:10.0} + DOTNET_ASPNET_IMAGE: ${DOTNET_ASPNET_IMAGE:-171.22.25.73:5002/dotnet/aspnet:10.0} container_name: meezi-api restart: unless-stopped depends_on: @@ -97,7 +99,11 @@ services: build: context: . dockerfile: docker/web/Dockerfile + extra_hosts: + - "mirror:host-gateway" args: + NODE_IMAGE: ${NODE_IMAGE:-171.22.25.73:5000/library/node:20-alpine} + NPM_REGISTRY: ${NPM_REGISTRY:-http://mirror:8081/repository/npm-group/} NEXT_PUBLIC_API_URL: ${NEXT_PUBLIC_API_URL:-http://localhost:5080} container_name: meezi-web restart: unless-stopped @@ -114,7 +120,11 @@ services: build: context: . dockerfile: docker/website/Dockerfile + extra_hosts: + - "mirror:host-gateway" args: + NODE_IMAGE: ${NODE_IMAGE:-171.22.25.73:5000/library/node:20-alpine} + NPM_REGISTRY: ${NPM_REGISTRY:-http://mirror:8081/repository/npm-group/} MEEZI_API_URL: http://api:8080 NEXT_PUBLIC_SITE_URL: ${NEXT_PUBLIC_SITE_URL:-http://localhost:3010} container_name: meezi-website @@ -134,7 +144,11 @@ services: build: context: . dockerfile: docker/finder/Dockerfile + extra_hosts: + - "mirror:host-gateway" args: + NODE_IMAGE: ${NODE_IMAGE:-171.22.25.73:5000/library/node:20-alpine} + NPM_REGISTRY: ${NPM_REGISTRY:-http://mirror:8081/repository/npm-group/} NEXT_PUBLIC_API_URL: ${NEXT_PUBLIC_API_URL:-http://localhost:5080} NEXT_PUBLIC_SITE_URL: ${NEXT_PUBLIC_FINDER_URL:-http://localhost:3103} container_name: meezi-finder diff --git a/docker/admin-api/Dockerfile b/docker/admin-api/Dockerfile index 8cbf8e0..3c017e7 100644 --- a/docker/admin-api/Dockerfile +++ b/docker/admin-api/Dockerfile @@ -4,7 +4,9 @@ ARG DOTNET_ASPNET_IMAGE=mcr.microsoft.com/dotnet/aspnet:10.0 FROM ${DOTNET_SDK_IMAGE} AS build WORKDIR /src -COPY global.json Directory.Build.props Directory.Packages.props nuget.config ./ +COPY global.json Directory.Build.props Directory.Packages.props ./ +# nuget.docker.config points to local Nexus mirror (mirror:8081 via extra_hosts in compose) +COPY nuget.docker.config ./nuget.config COPY src/Meezi.Shared/Meezi.Shared.csproj src/Meezi.Shared/ COPY src/Meezi.Core/Meezi.Core.csproj src/Meezi.Core/ diff --git a/docker/admin-web/Dockerfile b/docker/admin-web/Dockerfile index 4ba6d00..01e43c9 100644 --- a/docker/admin-web/Dockerfile +++ b/docker/admin-web/Dockerfile @@ -1,20 +1,28 @@ -FROM node:20-alpine AS builder -WORKDIR /app +ARG NODE_IMAGE=node:20-alpine -COPY web/admin/ . +FROM ${NODE_IMAGE} AS deps +WORKDIR /app +COPY web/admin/package*.json ./ +ARG NPM_REGISTRY=https://registry.npmjs.org +# Install deps then ensure Alpine (musl) SWC binary is present +RUN npm install --legacy-peer-deps --ignore-scripts --registry ${NPM_REGISTRY} \ + && NEXT_VER=$(node -e "process.stdout.write(require('./node_modules/next/package.json').version)") \ + && ls node_modules/@next/swc-linux-x64-musl 2>/dev/null \ + || npm install --no-save --ignore-scripts --registry ${NPM_REGISTRY} \ + "@next/swc-linux-x64-musl@${NEXT_VER}" + +FROM ${NODE_IMAGE} AS builder +WORKDIR /app ARG NEXT_PUBLIC_ADMIN_API_URL=http://localhost:5081 ENV NEXT_PUBLIC_ADMIN_API_URL=$NEXT_PUBLIC_ADMIN_API_URL - -RUN NEXT_VER=$(node -e "process.stdout.write(require('./node_modules/next/package.json').version)") \ - && rm -rf node_modules/@next/swc-win32-* node_modules/@next/swc-darwin-* 2>/dev/null; \ - ls node_modules/@next/swc-linux-x64-musl 2>/dev/null \ - || npm install --no-save --ignore-scripts "@next/swc-linux-x64-musl@${NEXT_VER}" - ENV NEXT_TELEMETRY_DISABLED=1 + +COPY --from=deps /app/node_modules ./node_modules +COPY web/admin/ . RUN npm run build -FROM node:20-alpine AS runner +FROM ${NODE_IMAGE} AS runner WORKDIR /app ENV NODE_ENV=production @@ -31,5 +39,4 @@ COPY --from=builder --chown=nextjs:nodejs /app/.next/static ./.next/static USER nextjs EXPOSE 3000 - CMD ["node", "server.js"] diff --git a/docker/api/Dockerfile b/docker/api/Dockerfile index 2da1cf9..b36b1a8 100644 --- a/docker/api/Dockerfile +++ b/docker/api/Dockerfile @@ -1,21 +1,18 @@ -# Base images: override via docker-compose build args or .env (see docs/DOCKER.md). -# Default = Microsoft Container Registry (official). Docker Hub dotnet/* often returns -# "insufficient_scope" unless logged in, or is unreachable in some regions. ARG DOTNET_SDK_IMAGE=mcr.microsoft.com/dotnet/sdk:10.0 ARG DOTNET_ASPNET_IMAGE=mcr.microsoft.com/dotnet/aspnet:10.0 FROM ${DOTNET_SDK_IMAGE} AS build WORKDIR /src -COPY global.json Directory.Build.props Directory.Packages.props nuget.config ./ +COPY global.json Directory.Build.props Directory.Packages.props ./ +# nuget.docker.config points to local Nexus mirror (mirror:8081 via extra_hosts in compose) +COPY nuget.docker.config ./nuget.config COPY src/Meezi.Shared/Meezi.Shared.csproj src/Meezi.Shared/ COPY src/Meezi.Core/Meezi.Core.csproj src/Meezi.Core/ COPY src/Meezi.Infrastructure/Meezi.Infrastructure.csproj src/Meezi.Infrastructure/ COPY src/Meezi.API/Meezi.API.csproj src/Meezi.API/ -# NuGet over TLS often fails in Docker when VPN/filter/antivirus breaks HTTPS (bad record mac). -# Retry via nuget.config; offline revocation helps restricted networks. Re-run build if restore fails. ENV NUGET_CERT_REVOCATION_MODE=offline RUN --mount=type=cache,target=/root/.nuget/packages \ dotnet restore src/Meezi.API/Meezi.API.csproj --disable-parallel @@ -28,9 +25,6 @@ RUN dotnet publish src/Meezi.API/Meezi.API.csproj -c Release -o /app/publish /p: FROM ${DOTNET_ASPNET_IMAGE} AS runtime WORKDIR /app -# No apt-get here — avoids Ubuntu mirror downloads during build (Iran/VPN issues). -# Healthcheck uses a TCP probe (see docker-compose.yml). - ENV ASPNETCORE_URLS=http://+:8080 EXPOSE 8080 diff --git a/docker/finder/Dockerfile b/docker/finder/Dockerfile index 7ebd594..71b5d1b 100644 --- a/docker/finder/Dockerfile +++ b/docker/finder/Dockerfile @@ -1,10 +1,12 @@ -FROM node:20-alpine AS deps +ARG NODE_IMAGE=node:20-alpine + +FROM ${NODE_IMAGE} AS deps WORKDIR /app COPY web/finder/package*.json ./ -RUN npm config set registry https://registry.npmmirror.com \ - && npm install --legacy-peer-deps --ignore-scripts +ARG NPM_REGISTRY=https://registry.npmjs.org +RUN npm install --legacy-peer-deps --ignore-scripts --registry ${NPM_REGISTRY} -FROM node:20-alpine AS builder +FROM ${NODE_IMAGE} AS builder WORKDIR /app ARG NEXT_PUBLIC_API_URL=http://localhost:5080 @@ -17,7 +19,7 @@ COPY --from=deps /app/node_modules ./node_modules COPY web/finder/ . RUN npm run build -FROM node:20-alpine AS runner +FROM ${NODE_IMAGE} AS runner WORKDIR /app ENV NODE_ENV=production diff --git a/docker/web/Dockerfile b/docker/web/Dockerfile index 29fcbbd..e1eb758 100644 --- a/docker/web/Dockerfile +++ b/docker/web/Dockerfile @@ -1,10 +1,12 @@ -FROM node:20-alpine AS deps +ARG NODE_IMAGE=node:20-alpine + +FROM ${NODE_IMAGE} AS deps WORKDIR /app COPY web/dashboard/package*.json ./ -RUN npm config set registry https://registry.npmmirror.com \ - && npm install --legacy-peer-deps --ignore-scripts +ARG NPM_REGISTRY=https://registry.npmjs.org +RUN npm install --legacy-peer-deps --ignore-scripts --registry ${NPM_REGISTRY} -FROM node:20-alpine AS builder +FROM ${NODE_IMAGE} AS builder WORKDIR /app ARG NEXT_PUBLIC_API_URL=http://localhost:5080 @@ -15,7 +17,7 @@ COPY --from=deps /app/node_modules ./node_modules COPY web/dashboard/ . RUN npm run build -FROM node:20-alpine AS runner +FROM ${NODE_IMAGE} AS runner WORKDIR /app ENV NODE_ENV=production @@ -32,5 +34,4 @@ COPY --from=builder --chown=nextjs:nodejs /app/.next/static ./.next/static USER nextjs EXPOSE 3000 - CMD ["node", "server.js"] diff --git a/docker/website/Dockerfile b/docker/website/Dockerfile index c285329..1dc5a0e 100644 --- a/docker/website/Dockerfile +++ b/docker/website/Dockerfile @@ -1,23 +1,30 @@ -FROM meezi-node:20-alpine AS builder -WORKDIR /app +ARG NODE_IMAGE=node:20-alpine -COPY web/website/ . +FROM ${NODE_IMAGE} AS deps +WORKDIR /app +COPY web/website/package*.json ./ +ARG NPM_REGISTRY=https://registry.npmjs.org +# Install deps then ensure Alpine (musl) SWC binary is present +RUN npm install --legacy-peer-deps --ignore-scripts --registry ${NPM_REGISTRY} \ + && NEXT_VER=$(node -e "process.stdout.write(require('./node_modules/next/package.json').version)") \ + && ls node_modules/@next/swc-linux-x64-musl 2>/dev/null \ + || npm install --no-save --ignore-scripts --registry ${NPM_REGISTRY} \ + "@next/swc-linux-x64-musl@${NEXT_VER}" + +FROM ${NODE_IMAGE} AS builder +WORKDIR /app ARG MEEZI_API_URL=http://api:8080 ENV MEEZI_API_URL=$MEEZI_API_URL - ARG NEXT_PUBLIC_SITE_URL=http://localhost:3010 ENV NEXT_PUBLIC_SITE_URL=$NEXT_PUBLIC_SITE_URL - -RUN NEXT_VER=$(node -e "process.stdout.write(require('./node_modules/next/package.json').version)") \ - && rm -rf node_modules/@next/swc-win32-* node_modules/@next/swc-darwin-* 2>/dev/null; \ - ls node_modules/@next/swc-linux-x64-musl 2>/dev/null \ - || npm install --no-save --ignore-scripts "@next/swc-linux-x64-musl@${NEXT_VER}" - ENV NEXT_TELEMETRY_DISABLED=1 + +COPY --from=deps /app/node_modules ./node_modules +COPY web/website/ . RUN npm run build -FROM meezi-node:20-alpine AS runner +FROM ${NODE_IMAGE} AS runner WORKDIR /app ENV NODE_ENV=production @@ -31,11 +38,8 @@ RUN addgroup --system --gid 1001 nodejs \ COPY --from=builder /app/public ./public COPY --from=builder --chown=nextjs:nodejs /app/.next/standalone ./ COPY --from=builder --chown=nextjs:nodejs /app/.next/static ./.next/static - -# Blog MDX content is read at runtime by process.cwd() COPY --from=builder /app/src/content ./src/content USER nextjs EXPOSE 3000 - CMD ["node", "server.js"] diff --git a/nuget.docker.config b/nuget.docker.config new file mode 100644 index 0000000..8e82404 --- /dev/null +++ b/nuget.docker.config @@ -0,0 +1,15 @@ + + + + + + + + + + + +