Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: implemented docker support for nextjs app #255

Open
wants to merge 5 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 18 additions & 0 deletions .dockerignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
.env

Dockerfile
./**/*/Dockerfile

.dockerignore

node_modules
./**/*/node_modules

pnpm-debug.log
./**/*/pnpm-debug.log


README.md
.next
.git

2 changes: 1 addition & 1 deletion .nvmrc
Original file line number Diff line number Diff line change
@@ -1 +1 @@
18
18.15.0
39 changes: 39 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,45 @@ No, it does not. The `api` package should only be a production dependency in the

If you need to share runtime code between the client and server, such as input validation schemas, you can create a separate `shared` package for this and import on both sides.

## Docker

To get it running with docker, follow the steps below:

Inside `next.config.mjs` set, you can read more about why we need to set this here: https://nextjs.org/docs/advanced-features/output-file-tracing

```diff
output: "standalone",
```

Option 1:

1. Build and run the images with:

```bash
docker compose up --build
# You can specify a specific service: docker compose up nextjs --build
```

2. Visit `http://localhost:3000` to see your app.

Option 2:

1. Build the images

```bash
docker compose build
# You can specify a specific service: docker compose build nextjs
```

2. Run the images

```bash
docker compose up
# You can specify a specific service: docker compose up nextjs
```

3. Visit `http://localhost:3000` to see your app.

## Quick Start

To get it running, follow the steps below:
Expand Down
55 changes: 55 additions & 0 deletions apps/nextjs/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
##### DEPENDENCIES

FROM --platform=linux/amd64 node:18-alpine AS builder
RUN apk add --no-cache libc6-compat openssl1.1-compat && apk update
WORKDIR /app
RUN yarn global add turbo
COPY . .
RUN turbo prune --scope=@acme/nextjs --docker

FROM --platform=linux/amd64 node:18-alpine AS installer
RUN apk add --no-cache libc6-compat openssl1.1-compat && apk update
WORKDIR /app

ENV NODE_ENV production
ENV CI true
ENV SKIP_ENV_VALIDATION true

COPY .gitignore .gitignore
COPY --from=builder /app/tsconfig.json ./tsconfig.json

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this will not work it on /app/out/tsconfig.ts not in /app/tsconfig.ts i get error as not found when i try run at in server
image

COPY --from=builder /app/out/json .
COPY --from=builder /app/out/pnpm-lock.yaml\* ./

RUN yarn global add pnpm && pnpm fetch --prod && pnpm install -r --offline --prod

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why mix with yarn and pnpm ??



COPY --from=builder /app/out/full .



RUN pnpm turbo build --filter=nextjs

FROM --platform=linux/amd64 node:18-alpine AS runner
RUN apk add --no-cache libc6-compat openssl1.1-compat && apk update
WORKDIR /app

# Don't run production as root
RUN addgroup --system --gid 1001 nodejs
RUN adduser --system --uid 1001 nextjs
USER nextjs
EXPOSE 3000
ENV PORT 3000

ENV NODE_ENV production

# ENV NEXT_TELEMETRY_DISABLED 1 Optional

COPY --from=installer /app/apps/nextjs/next.config.mjs ./
COPY --from=installer /app/apps/nextjs/package.json ./

COPY --from=installer --chown=nextjs:nodejs /app/apps/nextjs/.next/standalone ./
COPY --from=installer --chown=nextjs:nodejs /app/apps/nextjs/.next/static ./apps/nextjs/.next/static
COPY --from=installer --chown=nextjs:nodejs /app/apps/nextjs/public ./apps/nextjs/public


CMD node apps/nextjs/server.js
4 changes: 3 additions & 1 deletion apps/nextjs/next.config.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,12 @@
* Run `build` or `dev` with `SKIP_ENV_VALIDATION` to skip env validation.
* This is especially useful for Docker builds and Linting.
*/
// !process.env.SKIP_ENV_VALIDATION && (await import("./src/env.mjs"));
!process.env.SKIP_ENV_VALIDATION && (await import("./src/env.mjs"));

/** @type {import("next").NextConfig} */
const config = {
/** For docker build, more information: https://nextjs.org/docs/advanced-features/output-file-tracing */
// output: "standalone",
reactStrictMode: true,
/** Enables hot reloading for local packages without a build step */
transpilePackages: ["@acme/api", "@acme/auth", "@acme/db"],
Expand Down
11 changes: 5 additions & 6 deletions apps/nextjs/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -27,18 +27,17 @@
"react": "18.2.0",
"react-dom": "18.2.0",
"superjson": "1.9.1",
"@types/node": "^18.15.11",
"@types/react": "^18.0.31",
"tailwindcss": "^3.3.1",
"postcss": "^8.4.21",
"autoprefixer": "^10.4.14",
Comment on lines +30 to +34
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

im no docker expert but why do these need to be production deps all of a sudden?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

when you run pnpm install --prod it only installs dependencies and when nextjs is trying to create to build it fails because it looks for those dependencies.

"zod": "^3.21.4"
},
"devDependencies": {
"@acme/eslint-config": "^0.1.0",
"@types/node": "^18.15.11",
"@types/react": "^18.0.31",
"@types/react-dom": "^18.0.11",
"autoprefixer": "^10.4.14",
"dotenv-cli": "^7.1.0",
"eslint": "^8.37.0",
"postcss": "^8.4.21",
"tailwindcss": "^3.3.1",
"typescript": "^5.0.3"
}
}
15 changes: 15 additions & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
version: "3.7"

services:
nextjs:
ports:
- "3000:3000"
build:
context: .
dockerfile: ./apps/nextjs/Dockerfile
environment:
- DATABASE_URL=${DATABASE_URL}
- NEXTAUTH_URL=${NEXTAUTH_URL}
- NEXTAUTH_SECRET=${NEXTAUTH_SECRET}
- DISCORD_CLIENT_ID=${DISCORD_CLIENT_ID}
- DISCORD_CLIENT_SECRET=${DISCORD_CLIENT_SECRET}
3 changes: 2 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
"prettier": "^2.8.7",
"prettier-plugin-tailwindcss": "^0.2.6",
"turbo": "^1.8.8",
"typescript": "^5.0.3"
"typescript": "^5.0.3",
"dotenv-cli": "^7.1.0"
}
}
2 changes: 1 addition & 1 deletion packages/db/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -12,11 +12,11 @@
"with-env": "dotenv -e ../../.env --"
},
"dependencies": {
"prisma": "^4.12.0",
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same here - prisma is a devDep, why does it need to be a prod dep now?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

in the turbo.json we declare that before build it should run db:generate, db:generate runs prisma and because we only install dependencies I had to add it.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would recommend leaving the devDependencies and prod dependencies as they are, but limit the number of packages installed with pnpm install --filter @acme/nextjs...

Copy link

@albertilagan albertilagan Jul 20, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As long as you're using output: "standalone" devDep will not get included on the final image, so imo you don't need --prod when running pnpm install, specially since you're doing prune anyway.

"@prisma/client": "^4.12.0"
},
"devDependencies": {
"dotenv-cli": "^7.1.0",
"prisma": "^4.12.0",
"typescript": "^5.0.3"
}
}
Loading