最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - ESM export * except from module - Stack Overflow

programmeradmin8浏览0评论

Given I have two imports with lots of named exports (too many to write them all out) and I want to reexport these except a few of them. In my case this is because a few exports collide.

As an example of what I want to archive lets assume we have two files:

foo.js:

export const a = 1;
export const b = 2;

bar.js:

export const b = 1;
export const c = 3;

If I want to aggregate and reexport them all using CommonJS I could do something like this:

/* use rest destructuring to put everything except "b" into variable "foo" */
const { b, ...foo } = require("./foo"); 
const bar = require("./bar");

module.exports = {
    ...foo,
    ...bar
};

As I'm using typescript the closest I've gotten is using export = { ... } in a similar way:

import * as foo from "./foo";
import * as bar from "./bar";

const { b, ...foo2 } = foo;

export = {
    ...foo2,
    ...bar,
};

However it is my understanding this will create a file with CommonJS module.exports instead of a proper ESM module (and probably require esModuleInterop). And it is a typescript construct and not available when writing vanilla JS.

Is there a way to archive this using ESM import / export instead?

Given I have two imports with lots of named exports (too many to write them all out) and I want to reexport these except a few of them. In my case this is because a few exports collide.

As an example of what I want to archive lets assume we have two files:

foo.js:

export const a = 1;
export const b = 2;

bar.js:

export const b = 1;
export const c = 3;

If I want to aggregate and reexport them all using CommonJS I could do something like this:

/* use rest destructuring to put everything except "b" into variable "foo" */
const { b, ...foo } = require("./foo"); 
const bar = require("./bar");

module.exports = {
    ...foo,
    ...bar
};

As I'm using typescript the closest I've gotten is using export = { ... } in a similar way:

import * as foo from "./foo";
import * as bar from "./bar";

const { b, ...foo2 } = foo;

export = {
    ...foo2,
    ...bar,
};

However it is my understanding this will create a file with CommonJS module.exports instead of a proper ESM module (and probably require esModuleInterop). And it is a typescript construct and not available when writing vanilla JS.

Is there a way to archive this using ESM import / export instead?

Share Improve this question edited Jun 3, 2022 at 9:05 ext asked Jun 3, 2022 at 8:58 extext 2,9334 gold badges37 silver badges49 bronze badges
Add a ment  | 

1 Answer 1

Reset to default 3

Is there a way to archive this using ESM import / export instead?

No, not in pure standard ESM, not without doing what you're trying to avoid: Listing the named exports. There's no "rest" concept in ESM import/export.

I think you know this, but you could export an object with properties for a, b, and c, but that's a very different thing from re-exporting named exports. It wouldn't be a live binding, and the syntax for importing its parts is different from importing named exports (unless build-time tools like TypeScript or bundlers, etc. are involved).

Just FWIW, here's what that looks like (it's very similar to your TypeScript version near the end), but I don't think it's what you want:

reexport.js:

import * as foo from "./foo.js";
import * as bar from "./bar.js";

const { b, ...restOfFoo } = foo;
export default {
    ...restOfFoo,
    ...bar,
};

Then using it is:

// Import the object (which is the default export)
import stuff from "./reexport.js";

// Destructure into local vars (optional, but...)
const { a, b, c } = stuff;

// Use it...
console.log(a, b, c);

That's all standard ESM.

发布评论

评论列表(0)

  1. 暂无评论