Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Next.js pass NODE_ENV to client

Tags:

I'm building a React SSR App, using Next.js.

I want to be able to access the NODE_ENV on the client side, as this will tell my app which API endpoints to use.

I'm struggling to find a decent approach for this. I'd like to define the NODE_ENV as a window variable when I first render the page on the server, and then in my helper function where I make the API call, I would check if the code is being called on the server or the client, and using the window or process.env objects as required.

Does anyone have a good solution for such a problem? It must be a common issue but I can't find any good solutions.

like image 821
Jack Wild Avatar asked Nov 12 '18 16:11

Jack Wild


People also ask

Does NextJS set NODE_ENV?

next start and next build will set NODE_ENV to production by default, but if there's a custom NODE_ENV it won't be replaced.

Can you overwrite NODE_ENV?

You cannot override NODE_ENV manually. This prevents developers from accidentally deploying a slow development build to production.

Does npm run build set NODE_ENV?

The value of NODE_ENV is set automatically to development (when using npm start ), test (when using npm test ) or production (when using npm build ).


1 Answers

1. You can include it in webpack configuration (using dotenv-webpack dependency):

require('dotenv').config()

const path = require('path')
const Dotenv = require('dotenv-webpack')

module.exports = {
  webpack: (config) => {
    config.plugins = config.plugins || []

    config.plugins = [
      ...config.plugins,

      // Read the .env file
      new Dotenv({
        path: path.join(__dirname, '.env'),
        systemvars: true
      })
    ]

    return config
  }
}

Reference: here


2. using babel plugin to import the variable towards the entire app:

env-config.js

const prod = process.env.NODE_ENV === 'production'

module.exports = {
  'process.env.BACKEND_URL': prod ? 'https://api.example.com' : 'https://localhost:8080'
}

.babelrc.js

const env = require('./env-config.js')

module.exports = {
  presets: ['next/babel'],
  plugins: [['transform-define', env]]
}

index.js

export default () => (
  <div>Loading data from { process.env.BACKEND_URL }</div>
)

Reference: here

3. Using next/config:

next.config.js

module.exports = {
  publicRuntimeConfig: {
    API_URL: process.env.API_URL
  }
}

index.js

import React from 'react'
import getConfig from 'next/config'

const {publicRuntimeConfig} = getConfig()
const {API_URL} = publicRuntimeConfig

export default class extends React.Component {
  static async getInitialProps () {
    // fetch(`${API_URL}/some-path`)
    return {}
  }

  render () {
    return <div>
            The API_URL is {API_URL}
    </div>
  }
}

Reference: here

like image 177
Darryl RN Avatar answered Sep 28 '22 03:09

Darryl RN