forge icon indicating copy to clipboard operation
forge copied to clipboard

Typescript ESM forge.config.ts error

Open codec-xyz opened this issue 1 year ago • 7 comments

Pre-flight checklist

  • [X] I have read the contribution documentation for this project.
  • [X] I agree to follow the code of conduct that this project uses.
  • [X] I have searched the issue tracker for a bug that matches the one I want to file, without success.

Electron Forge version

7.4.0

Electron version

v31.3.1

Operating system

Windows 11

Last known working Electron Forge version

No response

Expected behavior

To not get an error when using a Typescript ESM forge.config.ts.

Actual behavior

Error are listed under the steps to reproduce section.

Steps to reproduce

Run npm init [email protected] my-new-app -- --template=vite-typescript

Add "type": "module", to package.json

[!Note]

To make other parts of the template work with "type": "module"

In vite.main.config change formats: ['cjs'], to formats: ['es'],

In vite.preload.config change format: 'cjs', to format: 'es',

In src/main.ts change

if (require('electron-squirrel-startup')) {
  app.quit();
}

			↓↓↓

import electronSquirrelStartup from 'electron-squirrel-startup';
if(electronSquirrelStartup) app.quit();

and replace __dirname with import.meta.dirname

You can also npm install --save-dev @types/electron-squirrel-startup and in tsconfig.json change "module": "commonjs","module": "ESNext", to make typescript happy.

Run npm run start

This result in this error...

› Must use import to load ES Module: C:\path\my-new-app\forge.config.ts
  require() of ES modules is not supported.
  require() of C:\path\my-new-app\forge.config.ts from C:\path\my-new-app\node_modules\@electron-forge\core\dist\util\forge-config.js is an ES
  module file as it is a .ts file whose nearest parent package.json contains "type": "module" which defines all .ts
  files in that package scope as ES modules.
  Instead change the requiring code to use import(), or remove "type": "module" from
  C:\path\my-new-app\package.json.

An unhandled rejection has occurred inside Forge:
Error: Must use import to load ES Module: C:\path\my-new-app\forge.config.ts
require() of ES modules is not supported.
require() of C:\path\my-new-app\forge.config.ts from C:\path\my-new-app\node_modules\@electron-forge\core\dist\util\forge-config.js is an ES module file as it is a .ts file whose nearest parent package.json contains "type": "module" which defines all .ts files in that package scope as ES modules.
Instead change the requiring code to use import(), or remove "type": "module" from C:\path\my-new-app\package.json.

However changing forge.config.ts to forge.config.js (and removing the type definitions) makes the error go away. So seemingly JS ES modules work but TS ES modules do not work.

Another option is changing the forge.config.ts to a forge.config.cts but it does not work with "module": "ESNext" (or other ES module options) in the tsconfig.json which gives the error...

  › Cannot use import statement outside a module

Failed to load: C:\path\my-new-app\forge.config.cts

An unhandled rejection has occurred inside Forge:
SyntaxError: Cannot use import statement outside a module

Additional information

No response

codec-xyz avatar Aug 13 '24 08:08 codec-xyz

@codec-xyz I have found the same inconsistent behavior and to be honest I just tried every which combination until something was working for us (but feels very fragile and certainly not ideal long term). For us we went with using forge.config.cts and had to set module: commonjs which is not what we want overall but works for us right now. As you can see by my comments in the screenshot below, we also could not get ESNext to work which is what led us to settling on commonjs.

I believe it is related to:

  • #3506

Screenshot of tsconfig tweaks that finally got it to work for us:

image

GitMurf avatar Aug 21 '24 18:08 GitMurf

@codec-xyz I am just glad I am not crazy and that you came to the same conclusion as me! I spent way too many hours (days) trying to figure this out and the imposter syndrome was starting to become real strong for me! haha

GitMurf avatar Aug 21 '24 18:08 GitMurf

I also encountered this problem. When I wanted to migrate to ESM according to the latest version of electron-store, I found that forge.config.ts did not support ESM.

AmbitionsXXXV avatar Sep 04 '24 01:09 AmbitionsXXXV

Using the template shared in the issue below worked for me initially, But later I needed to change the preload script output to cjs and moduleResolution to Node because some issues started showing up, Not sure if it was a problem on my end but with those changes everything seem to work fine.

https://github.com/electron/forge/issues/3502#issuecomment-2211449451

justgo97 avatar Sep 04 '24 07:09 justgo97

Having the same issue.

SRichner avatar Sep 07 '24 18:09 SRichner

This issue should be related to rechoir dependency that currently doesn't support ESM (https://github.com/gulpjs/rechoir/issues/43).

Electron forge v7.5.0 add support with ESM but, for this issue, nothing is changed.

Repro

  • yarn init -y

  • yarn set version berry

  • yarn add -D @electron-forge/cli @electron-forge/plugin-vite electron ts-node typescript vite (note ts-node dependency related to #3609)

  • Create an empty forge.config.ts file

  • yarn electron-forge start

  • Output:

    ✔ Checking your system
    ✔ Locating application
    ✖ Loading configuration
      ›
      1. Must use import to load ES Module: C:\<PROJECT_PATH>\forge.config.ts
      require() of ES modules is not supported.
      require() of C:\<PROJECT_PATH>\forge.config.ts from
      C:\Users\<USER>\AppData\Local\Yarn\Berry\cache\@electron-forge-core-patch-50fd2dab5c-10c0.zip\node_modules\@electron-forge\core\helper\dynamic-import.js is an  
      ES module file as it is a .ts file whose nearest parent package.json contains "type": "module" which defines all .ts files in that package scope as ES modules.   
      Instead change the requiring code to use import(), or remove "type": "module" from C:\<PROJECT_PATH>\package.json.
    
      2. Unknown file extension ".ts" for C:\<PROJECT_PATH>\forge.config.ts
    ◼ Preparing native dependencies
    ◼ Running generateAssets hook
    
    Failed to load: C:\<PROJECT_PATH>\forge.config.ts
    
    An unhandled rejection has occurred inside Forge:
    Error:
    1. Must use import to load ES Module: C:\<PROJECT_PATH>\forge.config.ts
    require() of ES modules is not supported.
    require() of C:\<PROJECT_PATH>\forge.config.ts from C:\Users\<USER>\AppData\Local\Yarn\Berry\cache\@electron-forge-core-patch-50fd2dab5c-10c0.zip\node_modules\@electron-forge\core\helper\dynamic-import.js is an ES module file as it is a .ts file whose nearest parent package.json contains "type": "module" which defines all .ts files in that package scope as ES modules.
    Instead change the requiring code to use import(), or remove "type": "module" from C:\<PROJECT_PATH>\package.json.
    
    2. Unknown file extension ".ts" for C:\<PROJECT_PATH>\forge.config.ts
    

Maybe rechoir dependency can be replaced with another dependency (e.g. tsx https://github.com/electron/forge/issues/3676#issuecomment-2365217539) that support ESM or we can contribute to https://github.com/gulpjs/rechoir/issues/43.

FYI @erickzhao @MarshallOfSound

rtritto avatar Sep 21 '24 12:09 rtritto

Related/duplicated/same issues: #3230 #3502 #3608

rtritto avatar Sep 21 '24 12:09 rtritto

I found that rechoir supports esbuild. You can remove ts-node from your devDependencies and replace it with esbuild-register and then forge.config.ts can be loaded successfully.

With Yarn:

yarn remove ts-node
yarn add --dev esbuild-register

chetbox avatar Oct 30 '24 20:10 chetbox

I found that rechoir supports esbuild. You can remove ts-node from your devDependencies and replace it with esbuild-register and then forge.config.ts can be loaded successfully.

With Yarn:

yarn remove ts-node yarn add --dev esbuild-register

Thanks it works (youn need to install also esbuild because it's a peer dependencies of esbuild-register).

I updated title of #3609 and added a comment (https://github.com/electron/forge/issues/3609#issuecomment-2448470724).

rtritto avatar Oct 30 '24 21:10 rtritto

I am running into the issue as well but with webpack. Anyone else have this issue?

Steps to reproduce

Run npm init electron-app@latest my-new-app -- --template=webpack-typescript

Add "type": "module", to package.json

Error

Failed to load: electron-test/issue-3671/forge.config.js

An unhandled rejection has occurred inside Forge: Error [ERR_REQUIRE_ESM]:

  1. require() of ES Module electron-test/issue-3671/forge.config.js from electron-test/issue-3671/node_modules/@electron-forge/core/helper/dynamic-import.js not supported. Instead change the require of forge.config.js in electron-test/issue-3671/node_modules/@electron-forge/core/helper/dynamic-import.js to a dynamic import() which is available in all CommonJS Modules.

fras2560 avatar Dec 09 '24 17:12 fras2560

rename forge.config.js to forge.config.cjs for supporting commonjs format

uzwebline avatar Dec 10 '24 14:12 uzwebline

A work-around I found is calling the Forge cli command script's with something like tsx. So in your package.json add this...

"scripts": {
	"start": "tsx node_modules/@electron-forge/cli/src/electron-forge-start",
	"package": "tsx node_modules/@electron-forge/cli/src/electron-forge-package",
	"make": "tsx node_modules/@electron-forge/cli/src/electron-forge-make",
	"publish": "tsx node_modules/@electron-forge/cli/src/electron-forge-publish"
}

codec-xyz avatar Dec 10 '24 15:12 codec-xyz

@codec-xyz u crazy dawg

so crazy it worked

woo

sebbean avatar Jan 15 '25 20:01 sebbean

So weird!!!!!! first okay! than error? WTH?

ArrayIterator avatar Feb 07 '25 23:02 ArrayIterator

FWIW I think this should be fixed if you upgrade your system Node.js to 22.13 or above, but you will run into DEP0174 due to some legacy Electron Packager code: https://github.com/electron/forge/issues/3828

erickzhao avatar Feb 08 '25 00:02 erickzhao

@chetbox method is the one working for me with:

yarn remove ts-node
yarn add --dev esbuild esbuild-register

@codec-xyz method unfortunately doesn't work on Ubuntu. It worked fine on Windows and Mac but on Linux it gives this on electron-forge package:

An unhandled rejection has occurred inside Forge:
TypeError: Cannot read properties of undefined (reading 'build')
at <anonymous> (/home/rychu/Desktop/filemail-desktop/Filemail-Desktop-Electron/node_modules/@electron-forge/plugin-vite/src/VitePlugin.ts:161:12)
    at new Promise (<anonymous>)
    at VitePlugin.VitePlugin.build (/home/rychu/Desktop/filemail-desktop/Filemail-Desktop-Electron/node_modules/@electron-forge/plugin-vite/src/VitePlugin.ts:159:25)
    at async Promise.all (index 0)
    at async <anonymous> (/home/rychu/Desktop/filemail-desktop/Filemail-Desktop-Electron/node_modules/@electron-forge/plugin-vite/src/VitePlugin.ts:95:11)
    at async <anonymous> (/home/rychu/Desktop/filemail-desktop/Filemail-Desktop-Electron/node_modules/@electron-forge/core/src/util/plugin-interface.ts:116:28)
    at async _Task.taskFn (/home/rychu/Desktop/filemail-desktop/Filemail-Desktop-Electron/node_modules/@electron-forge/tracer/src/index.ts:51:14)
    at async _Task.run (/home/rychu/Desktop/filemail-desktop/Filemail-Desktop-Electron/node_modules/listr2/dist/index.cjs:2063:11)

At VitePlugin.ts:161 there is simply reference to the vite so it seems that the import vite from 'vite'; doesn't work on Linux for some reason.

Rychu-Pawel avatar Mar 21 '25 15:03 Rychu-Pawel