# Multi-stage build for AdonisJS 6 application # Stage 1: Dependencies installation FROM node:20-alpine AS dependencies WORKDIR /app # Copy package files COPY package*.json ./ # Install all dependencies (including devDependencies for building) RUN npm ci # Stage 2: Build application FROM node:20-alpine AS builder WORKDIR /app # Copy package files first COPY package*.json ./ # Copy dependencies from previous stage COPY --from=dependencies /app/node_modules ./node_modules # Copy source code COPY . . # Build the application (compiles TypeScript and creates production build in build/) # Using npm run build ensures proper environment setup RUN npm run build # Stage 3: Production runtime FROM node:20-alpine AS production # Install dumb-init for proper signal handling + ca-certificates for HTTPS RUN apk add --no-cache dumb-init ca-certificates WORKDIR /app # Create non-root user for security RUN addgroup -g 1001 -S nodejs && \ adduser -S adonisjs -u 1001 # Copy built application from builder stage COPY --from=builder --chown=adonisjs:nodejs /app/build ./ # Install production dependencies only # The build folder contains its own package.json with production dependencies RUN npm ci --omit=dev # Set environment to production ENV NODE_ENV=production ENV PORT=3333 ENV HOST=0.0.0.0 # Expose application port EXPOSE 3333 # Switch to non-root user USER adonisjs # Use dumb-init to handle signals properly (for graceful shutdown) ENTRYPOINT ["dumb-init", "--"] # Start the application CMD ["node", "bin/server.js"]