I am using prettier
programmatically, in code, with the format(jsCodeString)
function.
The code works locally, but when I bundle it with esbuild
, in production prettier fails when it tries to dynamically import some module.
I get the following error:
The argument 'filename' must be a file URL object, file URL string, or absolute path string. Received undefined
I don't know what prettier is looking for so I don't know how to fix it. I haven't found this error anywhere else on the internet.
I think it is a combination of my build process and prettier. It is hard to look into prettier to find this part of the code and see what it might want because it is uglyfied in production when the error happens.
This is the line of code that breaks in production: Image
This is how I'm using prettier's format
function:
import { format } from 'prettier';
await format(inputCode, { parser: 'babel' })
Any pointers are much appreciated!!!
In my situation, I'm building for a NodeJS target, and I don't need the portability to ship the bundle without node_modules. If you're in a similar position then you can make use of ESBuild's external
property. The external
property should prevent ESBuild from trying to bundle Prettier, and just require it directly from node_modules:
My build script is like
esbuild.buildSync({
entryPoints: [path.join(__dirname, './build-platform/index.ts')],
bundle: true,
platform: 'node',
target: 'node16',
entryNames: 'build',
external: ['esbuild', 'prettier'], // Exclude prettier here
sourcemap: 'inline',
outdir: path.join(__dirname, '../.artifacts'),
});
I can't tell you exactly why it isn't working when it's bundled, it seems the code that is generated by ESBuild is incorrect. My situation is similar to your image.
var import_meta = {};
var require2 = (0, import_module.createRequire)(import_meta.url);
Obviously that empty object is not going going to have a url
property.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With