nextjs+dockercompose: env variables pass to nextjs.config.js

Viewed 303

I have a next.config.js

module.exports = {
  .........
  env: {
    BASE_URL: 'http://xx.xx.xx.xx:8000',
  },
  ............
};

If I want to change the BASE_URL while building docker image I can do

my Dockerfile file

FROM node:16-alpine3.14

WORKDIR /usr/app

COPY ./package.json ./

RUN yarn install

ENV BASE_URL=http://yy.yyy.yy.yy:80

# Copy all files
COPY ./ ./

RUN yarn build

SO ENV BASE_URL=http://yy.yyy.yy.yy:80 in your docker file will set an environment variable BASE_URL to it's value, you need to read it for that variable.

//next.config.js
module.exports = {
  .........
  env: {
    BASE_URL: process.env.BASE_URL || 'http://xx.xx.xx.xx:8000', //read the value from env id empty use default value.
  },
  ............
};

But how can I make this image more generic, So that while running the service in dockercompose i can pass the BASE_URL

Is that possible.

Else for every different BASE_URL, i have to create different images.

1 Answers

Yes it's possible to pass environment variables from docker-compose file to Dockerfile at runtime. So from your example if we want a generic BASE_URL variable here's how to do it:

In Dockerfile:

ARG BASE_URL
ENV BASE_URL=${BASE_URL}

Set environement variable like above then build an image: docker build -t my-web-app .

In docker-compose.yml:

version: '3.5'
services:
  my-web-app:
    container_name: my-web-app
    image: my-web-app
    restart: always
    ports:
      - 3000:3000
    environment:
      - BASE_URL=https://my-web-app.io

In next.config.js:

module.exports = {
  serverRuntimeConfig: {
    BASE_URL: process.env.BASE_URL, // only visible on server side
  },
  publicRuntimeConfig: {
    // Put variables here if you need them on client side
  },
};

For this to work, you need to install dotenv (npm install dotenv), and simply import it at your app's entry point, so either _app.js or _document.js

import 'dotenv/config';

Now you can set any value to BASE_URL from the docker-compose.yml file and do a docker-compose up, for BASE_URL to be visible on server side.

Related