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

issue with using CommonJS modules in "svelte/kit build" #928

Closed
henryennis opened this issue Apr 8, 2021 · 37 comments
Closed

issue with using CommonJS modules in "svelte/kit build" #928

henryennis opened this issue Apr 8, 2021 · 37 comments
Labels
Milestone

Comments

@henryennis
Copy link

henryennis commented Apr 8, 2021

App runs normally while running in dev mode, error is thrown on build

svelte.config.cjs

Note the package causing this issue is set to be converted to esm as of the:

optimizeDeps: {
				include: ['carbon-components-svelte', 'clipboard-copy']
		        },

svelte.config.cjs

const sveltePreprocess = require('svelte-preprocess');
const node = require('@sveltejs/adapter-node');
const pkg = require('./package.json');

/** @type {import('@sveltejs/kit').Config} */
module.exports = {
	// Consult https://github.com/sveltejs/svelte-preprocess
	// for more information about preprocessors
	preprocess: sveltePreprocess(),
	kit: {
		// By default, `npm run build` will create a standard Node app.
		// You can create optimized builds for different platforms by
		// specifying a different adapter
		adapter: node(),
		ssr: false,
		// hydrate the <div id="svelte"> element in src/app.html
		target: '#svelte',

		vite: {
			// optimizeDeps: {
			// 	include: ['carbon-components-svelte', 'clipboard-copy']
			//   },
			ssr: {
				noExternal: Object.keys(pkg.dependencies || {})
			},
			plugins: [
				require('vite-plugin-windicss').default()
			  ]
		}
	}
};

importing modules from a commonJS package "carbon-components-svelte" like so:

index.svelte

<script>
  import {
    FluidForm,
    TextInput,
    PasswordInput, Tile
  } from "carbon-components-svelte";
import ButtonFullBleed from "../components/buttons/buttonFullBleed.svelte"
</script>

error

PS C:\Users\henry\sveltekit-dashboard> npm run build

> [email protected] build C:\Users\henry\sveltekit-dashboard
> svelte-kit build

vite v2.1.5 building for production...
✓ 320 modules transformed.
.svelte/output/client/_app/manifest.json                            0.67kb
.svelte/output/client/_app/chunks/index-4d122fc8.js                 5.48kb / brotli: 2.12kb
.svelte/output/client/_app/assets/pages\index.svelte-802f02f9.css   4.19kb / brotli: 0.85kb
.svelte/output/client/_app/start-fbcbe901.js                        15.83kb / brotli: 5.41kb
.svelte/output/client/_app/pages\index.svelte-97280b82.js           59.90kb / brotli: 15.52kb
.svelte/output/client/_app/assets/start-9caedf08.css                459.55kb / brotli: 37.33kb
vite v2.1.5 building SSR bundle for production...
✓ 17 modules transformed.
.svelte/output/server/app.js   544.67kb

Run npm start to try your app locally.

> Using @sveltejs/adapter-node
> Named export 'FluidForm' not found. The requested module 'carbon-components-svelte' is a CommonJS module, which may not support all module.exports as named exports.
CommonJS modules can always be imported via the default export, for example using:

import pkg from 'carbon-components-svelte';
const {FluidForm} = pkg;

file:///C:/Users/henry/sveltekit-dashboard/.svelte/output/server/app.js:8
import {FluidForm} from "carbon-components-svelte";
SyntaxError: Named export 'FluidForm' not found. The requested module 'carbon-components-svelte' is a CommonJS module, which may not support all module.exports as named exports.
CommonJS modules can always be imported via the default export, for example using:

import pkg from 'carbon-components-svelte';
const {FluidForm} = pkg;

    at ModuleJob._instantiate (internal/modules/esm/module_job.js:98:21)
    at async ModuleJob.run (internal/modules/esm/module_job.js:143:5)
    at async Loader.import (internal/modules/esm/loader.js:165:24)
    at async prerender (file:///C:/Users/henry/sveltekit-dashboard/node_modules/@sveltejs/kit/dist/chunks/index6.js:513:14)
    at async AdapterUtils.prerender (file:///C:/Users/henry/sveltekit-dashboard/node_modules/@sveltejs/kit/dist/chunks/index6.js:745:4)
    at async adapt (C:\Users\henry\sveltekit-dashboard\node_modules\@sveltejs\adapter-node\index.js:26:4)
    at async adapt (file:///C:/Users/henry/sveltekit-dashboard/node_modules/@sveltejs/kit/dist/chunks/index6.js:767:2)
    at async file:///C:/Users/henry/sveltekit-dashboard/node_modules/@sveltejs/kit/dist/cli.js:633:5

Note that:

The same issue happens when a Svelte component that imports a CommonJS module is imported in to a vanilla JS Vite project.

You can see the issue for yourselves by importing and instantiating the svelte-nano-donate component at this commit: small-tech/svelte-nano-donate@0d7bcf9 (works, QRious library is inlined) and the one before it (doesn’t work, QRious library is imported from node modules). Note that the second one will also work if you npm install the component via a local file path instead of from npm (I thought everything was fine until I tried to install the component in a Vite/SvelteKit project via npm).
(I’m going to go check on the Vite project to see if there are any related issues as we cannot be the first ones to get bitten by this.)

Credit: aral


other information
Node version: v14.15.0
OS: windows 10 10.0, build 19041

@aral
Copy link

aral commented Apr 8, 2021

Seeing the same thing on build. Also seems to manifest as a 500 import not found: default error on npm run dev if a svelte component that uses a CommonJS module is installed from npm (works correctly if installed via a local file reference). Happy to open a separate issue for that but it feels like they’re the same one.

@henryennis
Copy link
Author

Seeing the same thing on build. Also seems to manifest as a 500 import not found: default error on npm run dev if a svelte component that uses a CommonJS module is installed from npm (works correctly if installed via a local file reference). Happy to open a separate issue for that but it feels like they’re the same one.

I will adapt the post accordingly

@henryennis henryennis changed the title issue with using CommonJS modules in svelte/kit build issue with using CommonJS modules in "svelte/kit build" Apr 9, 2021
@aral
Copy link

aral commented Apr 9, 2021

I will adapt the post accordingly

Note that:

  1. The same issue happens when a Svelte component that imports a CommonJS module is imported in to a vanilla JS Vite project.

  2. You can see the issue for yourselves by importing and instantiating the svelte-nano-donate component at this commit: small-tech/svelte-nano-donate@0d7bcf9 (works, QRious library is inlined) and the one before it (doesn’t work, QRious library is imported from node modules). Note that the second one will also work if you npm install the component via a local file path instead of from npm (I thought everything was fine until I tried to install the component in a Vite/SvelteKit project via npm).

(I’m going to go check on the Vite project to see if there are any related issues as we cannot be the first ones to get bitten by this.)

@benmccann
Copy link
Member

benmccann commented Apr 9, 2021

I would suggest trying all the tips in https://github.com/sveltejs/kit/blob/master/documentation/faq/70-packages.md as a first step

Unfortunately, CommonJS is somewhat of a known pain point with Vite at the moment: vitejs/vite#2579

@benmccann benmccann added the vite label Apr 9, 2021
@aral
Copy link

aral commented Apr 9, 2021

@benmccann That’s hugely useful, thank you.

@tolu
Copy link

tolu commented Apr 11, 2021

Just had the same issue and weirdly this solution from layercake issue tracker 👇 worked for me (but with @sanity/client dependency that needs prebundling)

Move vite config to own file vite.config.cjs so that

// vite.config.cjs
const pkg = require('./package.json');

/** @type {import('vite').UserConfig} */
export default {
  ssr: {
    noExternal: Object.keys(pkg.dependencies || {})
  },
};
// svelte.config.cjs
const sveltePreprocess = require('svelte-preprocess');
const node = require('@sveltejs/adapter-node');

/** @type {import('@sveltejs/kit').Config} */
module.exports = {
  preprocess: sveltePreprocess(),
  kit: {
    adapter: node(),
    target: '#svelte',

    // vite: {
    /* moved to vite.config.cjs */
    // }
  }
};

@henryennis
Copy link
Author

weirdly this solution from layercake issue tracker 👇 worked for me (with @sanity/client dependency)

Move vite config to own file vite.config.cjs so that

// vite.config.cjs

const pkg = require('./package.json');



/** @type {import('vite').UserConfig} */

export default {

  ssr: {

    noExternal: Object.keys(pkg.dependencies || {})

  },

};

Are u saying to seperate vite config from svelte config cjs?

@tolu
Copy link

tolu commented Apr 11, 2021

Are u saying to seperate vite config from svelte config cjs?

Yes, at least that worked for me 👍 I'll update my original comment to be more clear!

@benmccann benmccann added this to the 1.0 milestone Apr 12, 2021
@RemyDekor
Copy link

RemyDekor commented Apr 16, 2021

I'm not sure I understand how noExternal is supposed to work, but just removing the vite config from the svelte.config.cjs worked for me

@benmccann
Copy link
Member

The original issue description referred to carbon-components-svelte. For that library, I'm going to close this in favor of vitejs/vite#3024

For other libraries, the couple I tested seem to have been fixed by removing noExternal from the default template

If people are still having issues, please file a new issue with the specific library you're using and steps to reproduce or a repo that reproduces the issue

@sjmcdowall
Copy link

sjmcdowall commented Apr 25, 2021

@benmccann -- Sorry to post to a closed issue -- but I have no idea if this is related or not at all . I am trying to use Antony's svelte-mapbox in my new Sveltekit app -- and as soon as I uncomment out the import Map statement -- I am getting a 500 error in the browser --

The requested module '/node_modules/fastq/queue.js?v=0e439b33' does not provide an export named 'default'

SyntaxError: The requested module '/node_modules/fastq/queue.js?v=0e439b33' does not provide an export named 'default'

Is this similar or different than this issue? I tried the vite noExternal thing above but that didn't change anything ... TIA!

/Steve

@benmccann
Copy link
Member

@sjmcdowall there's an issue over in that repo that describes how to use it with SvelteKit: beyonk-group/svelte-mapbox#44

@sjmcdowall
Copy link

@benmccann -- Thank you! Sort of embarrassed I didn't see that myself. Cheers!

@ecstrema
Copy link
Contributor

For the original issue, it can be resolved (partly) by using the carbon's import preprocessor, since it avoids going through index.js

Dan6erbond added a commit to Dan6erbond/sk-auth that referenced this issue May 25, 2021
Dan6erbond added a commit to Dan6erbond/sk-auth that referenced this issue May 25, 2021
Dan6erbond added a commit to Dan6erbond/sk-auth that referenced this issue May 25, 2021
* 👷 Switch to ESM build

* 🔧 Use `module` instead of `main` config fields

* 📌 Reinstall sk-auth

* 🏷️ Fix type errors

* 🔧 Create separate Vite config JS according to sveltejs/kit#928

* Revert "🔧 Create separate Vite config JS according to sveltejs/kit#928"

This reverts commit 83d23a5.

* ➕ Add `build-esm` as dev and peer dependency

* 👷 Compile CJS module

* 📌 Reinstall deps

* 🔧 Switch to ESM build

* Revert "🔧 Switch to ESM build"

This reverts commit c908a57.

* 🔧 Use `main` instead of `module` in `package.json`
@praveenkpatare
Copy link

Facing the same issue with jsonwebtoken library.. here is the screnshot of the error --

image

@benmccann
Copy link
Member

We'll work on improved CJS support for Vite. But in the meantime see auth0/node-jsonwebtoken#785 auth0/node-jsonwebtoken#655 to improve that library

@brgrz
Copy link

brgrz commented Aug 16, 2021

Facing the same issue with nanoid, specifically importing strings from nanoid-dictionary.

SyntaxError: Named export 'nolookalikes' not found. The requested module 'nanoid-dictionary' is a CommonJS module, which may not support all module.exports as named exports.
CommonJS modules can always be imported via the default export, for example using:
import pkg from 'nanoid-dictionary';
const { nolookalikes } = pkg;
import { customAlphabet } from 'nanoid';
import { nolookalikes } from 'nanoid-dictionary';
export const nanoid = customAlphabet(nolookalikes, 10);

nanoid and nanoid-dictionary both export as ES.
https://github.com/CyberAP/nanoid-dictionary#nolookalikes

@benmccann
Copy link
Member

That library is using an old version of style-value-types. Here's a PR to upgrade it: micha-lmxt/svelte-motion#10. I didn't test if it solves the issue you're having, but it's possible it does since it updates the exports map

@Marcosaurios
Copy link

@benmccann thank you so much for that! 👏✌️

dnotes added a commit to dnotes/solitairetable that referenced this issue Oct 20, 2021
see sveltejs/kit#928

```
Named export 'faAsterisk' not found. The requested module '@fortawesome/free-solid-svg-icons' is a CommonJS module, which may not support all module.exports as named exports.
CommonJS modules can always be imported via the default export, for example using:

import pkg from '@fortawesome/free-solid-svg-icons';
const { faArrowLeft, faArrowRight, faAsterisk, faArrowRotateLeft, faFolderPlus, faEllipsis } = pkg;
```
@ogrotten
Copy link

Edit:
Apparently adding the failing dependencies to SSR noExternal property of vite config, make it work, as @benmccann said before:

This is the solution that worked for me.

ssr: {
	noExternal: ["svelte-hero-icons", '@googlemaps/js-api-loader'],
},

@BillBuilt
Copy link

Edit:
Apparently adding the failing dependencies to SSR noExternal property of vite config, make it work, as @benmccann said before:

I was having this exact issue with @FortAwesome icons and this fixed it

ssr: {
	noExternal: ['@fortawesome/free-brands-svg-icons', '@fortawesome/free-regular-svg-icons', '@fortawesome/free-solid-svg-icons']
},

@benmccann
Copy link
Member

A better solution for icon libraries is to use this option for performance reasons: https://github.com/sveltejs/vite-plugin-svelte/blob/main/docs/config.md#prebundlesveltelibraries

@BillBuilt
Copy link

Hi, thanks for the tip! Unfortunately, unless I am doing it wrong, this has no effect. Is this supposed to be uses in addition to the ssr.noExternal setting?

/** @type {import('@sveltejs/kit').Config} */
const config = {
	// Consult https://github.com/sveltejs/svelte-preprocess
	// for more information about preprocessors
	preprocess: preprocess(),

	kit: {
		adapter: adapter(),
		vite: {
			experimental: {
				prebundleSvelteLibraries: true
			},
			resolve: {
				alias: {
					$lib: path.resolve('./src/lib'),
					$comp: path.resolve('./src/components')
				}
			},
		}
	}
}

Produces: SyntaxError: Named export 'faBars' not found. The requested module '@fortawesome/free-solid-svg-icons' is a CommonJS module, which may not support all module.exports as named exports.

I did see this at the link you provided and I deleted the folder but it did not help: When updating the Svelte compiler options in svelte.config.js or vite.config.js, delete the node_modules/.vite folder to trigger pre-bundling in Vite again.

@benmccann
Copy link
Member

It doesn't go under vite. It goes directly in the root like:

const config = {
	experimental: {
		prebundleSvelteLibraries: true
	}
}

@BillBuilt
Copy link

hmmm still no change...

/** @type {import('@sveltejs/kit').Config} */
const config = {
	// Consult https://github.com/sveltejs/svelte-preprocess
	// for more information about preprocessors
	preprocess: preprocess(),
	experimental: {
		prebundleSvelteLibraries: true
	},
	kit: {
		adapter: adapter(),
		vite: {
			resolve: {
				alias: {
					$lib: path.resolve('./src/lib'),
					$comp: path.resolve('./src/components')
				}
			},
		}
	}
}

produces at build time:

import { faBars, faHome, faInfo, faTools, faEnvelope } from "@fortawesome/free-solid-svg-icons";
         ^^^^^^
SyntaxError: Named export 'faBars' not found. The requested module '@fortawesome/free-solid-svg-icons' is a CommonJS module, which may not support all module.exports as named exports.

whereas this works fine:

/** @type {import('@sveltejs/kit').Config} */
const config = {
	// Consult https://github.com/sveltejs/svelte-preprocess
	// for more information about preprocessors
	preprocess: preprocess(),

	kit: {
		adapter: adapter(),
		vite: {
			resolve: {
				alias: {
					$lib: path.resolve('./src/lib'),
					$comp: path.resolve('./src/components')
				}
			},
			ssr: {
				noExternal: ['@fortawesome/free-brands-svg-icons', '@fortawesome/free-regular-svg-icons', '@fortawesome/free-solid-svg-icons']
			},
		}
	}
}

I tried swapping out the adapters and noticed that when using adapter-auto it builds but produces the error upon running npm run preview. When using adapter-node it fails at build time.

@benmccann
Copy link
Member

I'm personally using fort-awesome icons without ssr.noExternal or experimental.prebundleSvelteLibraries in one of my projects by using svelte-awesome:

<script>
	import Icon from 'svelte-awesome';
	import { faTwitter } from '@fortawesome/free-brands-svg-icons';
<script>

<Icon data={faTwitter} scale="1.4"/>

@BillBuilt
Copy link

BillBuilt commented Feb 18, 2022

I too am using svelte-awesome but for some reason just wants to be finicky!

	import Icon from 'svelte-awesome'
	>>> FAILS: -> import { faBars, faHome, faInfo, faEnvelope, faTools } from '@fortawesome/free-solid-svg-icons'

I'll settle for having to use ssr.noExternal - slightly degraded performance is better than none at all!

@benmccann
Copy link
Member

Hmm. That seems quite strange. I wonder if you have an old version of Vite or something. You can run rm -rf node_modules package-lock.json && npm install to update. If that still doesn't fix it, please share a repository that reproduces the issue

@BillBuilt
Copy link

Hey @benmccann,
Sorry for the delayed response - here is a repo you can use to test. I tried deleting and re-installing but with identical results. I'm sure I'm probably just overlooking something.

src/routes/index.svelte has the imports in it. Thanks

https://github.com/BillBuilt/icontest

@Mnigos
Copy link

Mnigos commented Mar 18, 2022

Just had the same issue and weirdly this solution from layercake issue tracker 👇 worked for me (but with @sanity/client dependency that needs prebundling)

Move vite config to own file vite.config.cjs so that

// vite.config.cjs
const pkg = require('./package.json');

/** @type {import('vite').UserConfig} */
export default {
  ssr: {
    noExternal: Object.keys(pkg.dependencies || {})
  },
};
// svelte.config.cjs
const sveltePreprocess = require('svelte-preprocess');
const node = require('@sveltejs/adapter-node');

/** @type {import('@sveltejs/kit').Config} */
module.exports = {
 preprocess: sveltePreprocess(),
 kit: {
   adapter: node(),
   target: '#svelte',

   // vite: {
   /* moved to vite.config.cjs */
   // }
 }
};

I tried that and still got error ReferenceError: require is not defined in ES module scope, you can use import instead

jirihon added a commit to jirihon/euclid.js that referenced this issue Apr 6, 2022
This allows modern build systems (vite) to properly use the correct module type (ESM). See sveltejs/kit#928 for more details.
plegner pushed a commit to mathigon/euclid.js that referenced this issue Apr 9, 2022
* Add package.json exports property

This allows modern build systems (vite) to properly use the correct module type (ESM). See sveltejs/kit#928 for more details.
@MrEmanuel
Copy link

MrEmanuel commented Jun 5, 2022

I had similar problems as other people here in the thread.
My use case it that I'm trying to use @googlemaps/js-api-loader.

I got the same error saying it doesn't export a default. So I did a dynamic import in the onMount lifecycle method. Seems to work both in dev and the package compiles a prod build. I also had to update my config.

	onMount(() => {
		// Import loader on mount, because it doesn't have default export, and svelte doesn't like esm modules
		import('@googlemaps/js-api-loader').then((val) => {
			new val.Loader(loaderOptions).load().then(() => {
				map = new google.maps.Map(document.getElementById('map') as HTMLElement, {
					center: startPos,
					zoom: 8,
					styles: mapStyle
				});
			});
		});
	});
/** @type {import('@sveltejs/kit').Config} */
const config = {
	// Consult https://github.com/sveltejs/svelte-preprocess
	// for more information about preprocessors
	preprocess: preprocess(),

	kit: {
		adapter: adapter({
			pages: 'public',
			assets: 'public',
			fallback: null,
			precompress: false
		}),
		prerender: {
			default: false  // 👈
		}
	}
};

@ZodiacWind
Copy link

hi, I used sveletkit and plotly.js-dist-min in my project. yarn dev could work, but yarn build not. The error message is that:

E:\Projects\leakage-detector\node_modules\rollup\dist\shared\rollup.js:19908
var err = new SyntaxError(message);
^

SyntaxError: Unexpected token (37:121525) in E:/Projects/leakage-detector/node_modules/plotly.js-dist-min/plotly.min.js
at Parser.pp$4.raise (E:\Projects\leakage-detector\node_modules\rollup\dist\shared\rollup.js:19908:13)
at Parser.pp$9.unexpected (E:\Projects\leakage-detector\node_modules\rollup\dist\shared\rollup.js:17202:8)
at Parser.pp$5.parseIdent (E:\Projects\leakage-detector\node_modules\rollup\dist\shared\rollup.js:19839:10)
at Parser.pp$5.parsePropertyName (E:\Projects\leakage-detector\node_modules\rollup\dist\shared\rollup.js:19643:109)
at Parser.pp$5.parseProperty (E:\Projects\leakage-detector\node_modules\rollup\dist\shared\rollup.js:19570:8)
at Parser.pp$5.parseObj (E:\Projects\leakage-detector\node_modules\rollup\dist\shared\rollup.js:19524:21)
at Parser.pp$5.parseExprAtom (E:\Projects\leakage-detector\node_modules\rollup\dist\shared\rollup.js:19259:17)
at Parser.pp$5.parseExprSubscripts (E:\Projects\leakage-detector\node_modules\rollup\dist\shared\rollup.js:19075:19)
at Parser.pp$5.parseMaybeUnary (E:\Projects\leakage-detector\node_modules\rollup\dist\shared\rollup.js:19041:17)
at Parser.pp$5.parseExprOps (E:\Projects\leakage-detector\node_modules\rollup\dist\shared\rollup.js:18968:19) {
pos: 1407827,
loc: {
column: 121525,
file: 'E:/Projects/leakage-detector/node_modules/plotly.js-dist-min/plotly.min.js',
line: 37
},
raisedAt: 1407828,

……

id: 'E:/Projects/leakage-detector/node_modules/plotly.js-dist-min/plotly.min.js',
hook: 'transform',
code: 'PLUGIN_ERROR',
plugin: 'commonjs',

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests