23

I am using NextJS (https://nextjs.org/) Version 9.0.6.

My next.config.js looks like this:

/* eslint-disable */
const withLess = require("@zeit/next-less");
const lessToJS = require("less-vars-to-js");
const fs = require("fs");
const path = require("path");

// Where your antd-custom.less file lives
const themeVariables = lessToJS(
  fs.readFileSync(path.resolve(__dirname, "./assets/antd-custom.less"), "utf8")
);

module.exports = withLess({
  lessLoaderOptions: {
    javascriptEnabled: true,
    modifyVars: themeVariables // make your antd custom effective
  },
  webpack: (config, {
    isServer,
    defaultLoaders
  }) => {
    const originalEntry = config.entry;
    config.entry = async() => {
      const entries = await originalEntry();

      if (
        entries["main.js"] &&
        !entries["main.js"].includes("./polyfills.js")
      ) {
        entries["main.js"].unshift("./polyfills.js");
      }

      return entries;
    };

    config.module.rules.push({
      test: /\.scss$/,
      use: [
        defaultLoaders.babel,
        {
          loader: require("styled-jsx/webpack").loader,
          options: {
            type: "scoped",
            javascriptEnabled: true
          }
        },
        "sass-loader"
      ]
    });

    if (isServer) {
      const antStyles = /antd\/.*?\/style.*?/;
      const origExternals = [...config.externals];
      config.externals = [
        (context, request, callback) => {
          if (request.match(antStyles)) return callback();
          if (typeof origExternals[0] === "function") {
            origExternals[0](context, request, callback);
          } else {
            callback();
          }
        },
        ...(typeof origExternals[0] === "function" ? [] : origExternals)
      ];

      config.module.rules.unshift({
        test: antStyles,
        use: "null-loader"
      });
    }
    return config;
  }
});

My package.json looks like this:

{
  "name": "test",
  "version": "0.0.1beta",
  "scripts": {
    "dev": "next",
    "build": "next build",
    "start": "next start",
    "export": "next export"
  },
  "dependencies": {
    "@material/react-chips": "^0.15.0",
    "@zeit/next-less": "^1.0.1",
    "antd": "^3.24.3",
    "babel-plugin-import": "^1.12.2",
    "less": "3.10.3",
    "less-vars-to-js": "1.3.0",
    "next": "9.0.6",
    "null-loader": "3.0.0",
    "react": "^16.11.0",
    "react-country-flag": "^1.1.0",
    "react-device-detect": "^1.9.10",
    "react-dom": "^16.11.0",
    "react-proptypes": "^1.0.0",
    "react-redux": "^7.1.1",
    "react-string-replace": "^0.4.4",
    "redux": "^4.0.4",
    "redux-devtools-extension": "^2.13.8",
    "redux-persist": "^6.0.0"
  },
  "devDependencies": {
    "babel-eslint": "^10.0.3",
    "eslint": "^6.6.0",
    "eslint-config-airbnb": "^18.0.1",
    "eslint-plugin-babel": "^5.3.0",
    "eslint-plugin-import": "^2.18.2",
    "eslint-plugin-jsx-a11y": "^6.2.3",
    "eslint-plugin-react": "^7.16.0",
    "node-sass": "^4.13.0",
    "prettier": "^1.18.2",
    "prettier-eslint": "^9.0.0",
    "sass-loader": "8.0.0"
  },
  "license": "ISC"
}

What I did:

-Deleted the out and the .next folder.

Then:

yarn build
yarn export

The pages will be generated, but they are broken (CSS not loaded, no Javascript).

This worked at the beginning of the project, but no it does not.

Is here someone who has an idea why it could be broken ?

leonheess
  • 16,068
  • 14
  • 77
  • 112
Gutelaunetyp
  • 2,144
  • 4
  • 15
  • 40
  • Vote on [this proposal](https://meta.stackoverflow.com/questions/354583/disentangle-the-yarn) to ease the tag confusion. – leonheess Feb 10 '20 at 12:25

6 Answers6

50

I just came across the same issue and landed on this question. I think Taha explained the problem correctly, but for me a small adaption in the next.config.js did the trick:

module.exports = {
  assetPrefix: './'
}

The topic is also described in the NextJS docs.

Philipp Schemel
  • 943
  • 8
  • 19
12

I came across this question when I had the same problem, I've figured it out.

Inside your index.html file (in the out directory), find the link tag at the beginning of the file:

<link
      rel="preload"
      href="/_next/static/css/d849fb1b42015bc13208.css"
      as="style"
/>

<link
      rel="stylesheet"
      href="/_next/static/css/d849fb1b42015bc13208.css"
      data-n-g=""
/>

Just add a dot "." at the beginning of href attribute, like this:

<link
      rel="preload"
      href="./_next/static/css/d849fb1b42015bc13208.css"
      as="style"
/>
<link
      rel="stylesheet"
      href="./_next/static/css/d849fb1b42015bc13208.css"
      data-n-g=""
/>

This fixed it for me.

I do not know why the "." is not included by default.

Taha
  • 346
  • 3
  • 8
  • On the path `.` means current location. See below. [Difference between Relative path and absolute path](https://stackoverflow.com/questions/21306512/) – myeongkil kim Dec 25 '20 at 05:27
  • Yes, I know... But I don't know why Next.js doesn't include the `.` by default in the paths of the exported index.html file. – Taha Dec 26 '20 at 14:35
  • I believe this is because Nextjs assumes the content is served by a server, in which case it would work as normal, because `/` would be an absolute reference to the http root. – Webber Mar 22 '22 at 10:48
  • That's the lazy part of nextjs developers. Not every website is served from root www folder. – cikatomo May 01 '22 at 15:53
  • Serving from a local server is broken too, so it's just broken. – Marek Maurizio Aug 22 '23 at 12:26
10

I had the same issue recently while trying to export a static version of my app, and was surprised to see no recent issue about that on Next.js repository.

Actually when run through a web server, the use of absolute path for CSS/Js files works correctly. When run as local files in the browser, you have to change them to relative paths yourself.

As for why Next.js team do not provide an option to export with local path, Tim Neutkens (the lead maintainer) states in this issue that "it would involve a lot of work for very minimal gains".

Roman Mkrtchian
  • 2,548
  • 1
  • 17
  • 24
  • I was afraid once I deployed it wont work. Since opening the static site on your local do not work due the path issue. Thanks ! – ronnie bermejo Feb 10 '21 at 14:20
  • lot of work with minimal gains. So we have to do the work. Did you find any script that adjust the paths? – cikatomo May 01 '22 at 15:50
  • No, I actually just run a server locally if I need it locally. eg. you can run the command `python3 -m http.server` in the folder of your built files. – Roman Mkrtchian May 09 '22 at 07:01
1

if you are using VS Code and liveserver the problem is that liveserver is defaulting to the root of the project when it needs to set the root to the out folder or wherever you have the rendered files.

This is a setting which you can set per workspace.

Live Server › Settings: Root

Set Custom root of Live Server. To change root the the server to sub folder of workspace, use '/' and relative path from workspace. Example: /subfolder1/subfolder2

Then in the workspace settings.json I have:

{
  "liveServer.settings.root": "/out"
}

Ron
  • 1,121
  • 9
  • 19
0

Apart from @Philipp Schemels answer if anyone is using custom fonts via FontSource with StyledComponents, The built CSS file will not point to the correct font files, You will have to manually change those URLs,

The browser console should print a descriptive error which you can use to identify the CSS files that are causing the issue. Custom fonts are usually put in out/_next/static/media

0

I ran into this issue when building for Github Pages. I tried applying assetPath: "." in my next.config.js, but that wasn't working.

I manually fixed my css by moving my style.css file to the "public" folder, and then referring to it in the main jsx file with

<link rel="style" href="style.css" />
HMM
  • 27
  • 3
  • Note that the next js compiler/builder will complain, but I can't find a better way – HMM Jun 30 '23 at 16:37