esbuild
esbuild copied to clipboard
🐞 `import.meta.url` transpile.
When i use esbuild to transpile import.meat.url in cjs format, I always don't get the correct result.
Reproduce
const result = require('esbuild')
.transformSync('import.meta.url', { format: 'cjs' });
console.log(result.code);
// const import_meta = {};
// import_meta.url;
Expected
const import_meta = {
+ url: 'file:' + __filename
};
import_meta.url;
@evanw is there a solution planned for this? This prevents us from bumping versions of several dependencies, including some critical ones :(
You can inject it yourself:
https://hyrious.me/esbuild-repl/?version=0.15.5&mode=transform&input=import.meta.url&options=--format%3Dcjs+--define%3Aimport.meta.url%3D%27_importMetaUrl%27+--banner%3D%22const+_importMetaUrl%3Drequire%28%27url%27%29.pathToFileURL%28__filename%29%22
Is it still not resolved?
Why this need?
We use this to dynamically determine path for import outside of javascript.
esbuild options:
...
platform: "browser",
format: "esm",
bundle: true,
treeShaking: true,
splitting: true,
sourcemap: true,
...
Consider this example:
function inject_style(text: string) {
let newText = text;
const pathSearch = new RegExp(/(\\[START_RESOLVE_PATH\\])(?<RelativePath>.*)(\\[END_RESOLVE_PATH\\])/g);
const foundResources = text.matchAll(pathSearch);
for (const iterator of foundResources) {
const relPath = iterator["groups"].RelativePath;
const replaceRegexp = new RegExp(`(\\\\[START_RESOLVE_PATH\\\\])($\{relPath})(\\\\[END_RESOLVE_PATH\\\\])`);
const resolvedPath = import.meta.resolve(relPath);
newText = newText.replace(replaceRegexp, resolvedPath);
}
const style = window.document.createElement("style");
const node = window.document.createTextNode(newText);
style.appendChild(node);
window.document.head.appendChild(style);
}
in a custom plugin:
[custom esbuild plugin setup]....
onResolve({ filter: /^__style_helper__$/ }, () => {
return { path: "styleImporter.js", namespace: "style-helper" };
});
//if you pass he function as a string it will be correct, however if you pass the "function".toString() it will be "import_meta"
onLoad({ filter: /.*/, namespace: "style-helper" }, () => ({
contents: `export ${inject_style.toString().replace("import_meta","import.meta")}`,
}));