Skip to content

Transitive export * statements not re-exported in cjs with preserveModules #7115

@logaretm

Description

@logaretm

Summary

When using preserveModules: true with CJS output format, Rolldown does not generate re-export code for transitive export * statements.

The intermediate module correctly re-exports from an external dependency, but the top-level module that re-exports from the intermediate module produces an empty exports object.

In our use-case, we have layers of libraries building on top of each other, so there is transitive export statements in each level.

Reproduction:

https://repl.rolldown.rs/#eNptUD1PxDAM/StWlgAq7Z4bmdnYKENpXAhKk8pJj0pV/jtueukBuiWx/Z4/3lvFINQqjNO41DFssRPqmlei57Rp4OXTBCCcCAO6GGBnBKQzEhNbh8vkKcIDDORHkHWzY/LEM1CoSDOmSpC3VvtvV/feDebj18obyL7cjHnwChoH4/Apw5Aue0qbPLXuOIKZ3Wzzf3Tcra0DPnuao9rOKxJltdX9HDOQSQCDp7HbeP3XhQCgDXFBmxBLJZvBIp+9ni0GBZvIjKX84hKRXGcVvMoSP1rzLt9al+75YMGOHBYWI66FXf8/Y/8MEoknnJlku4ghivQD3FKcmQ==

You can also check this stackblitz and run node with require('./dist') and notice that the module doesn't export zod's own exports.

https://stackblitz.com/edit/abveex9m-czrtm8oq?file=dist%2Fserver.js,dist%2Findex.js,server.ts,index.ts

File structure:

  • index.ts: export * from './server';
  • server.ts: export * from 'external-lib';
  • external-lib: External dependency

Config

{
  format: 'cjs',
  preserveModules: true,
  external: ['external-lib']
}

Expected

index.js should contain re-export code similar to, or re-use the exports from the ./server.

const require_server = require('./server.js');

Object.keys(require_server).forEach(function (k) {
  if (k !== 'default' && !Object.prototype.hasOwnProperty.call(exports, k)) {
    Object.defineProperty(exports, k, {
      enumerable: true,
      get: function () { return require_server[k]; }
    });
  }
});

Actual Behavior

index.js produces an empty exports object:

const require_server = require('./server.js');

var index_exports = {};

Meanwhile, server.js correctly generates the re-export code for external-lib.


Workaround

I'm explicitly re-exporting the transitive export * statements in each entry again.

Metadata

Metadata

Labels

No labels
No labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions