Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

IIFE transformed modules are incompatible es module babel plugins #15

Open
gabemeola opened this issue Oct 24, 2019 · 4 comments
Open

Comments

@gabemeola
Copy link
Contributor

gabemeola commented Oct 24, 2019

IIFE transformed modules are incompatible with babel plugins which transform es modules.

Sort of a mouthful but I'll try to explain what's happening below.

Consider this CJS module

this.name = 'true';

Running this through transform-commonjs wraps it in a IIFE to preserve the this module context.

var module = {
  exports: {}
};
var exports = module.exports;
(function () {
  this.name = 'true';
}).call(module.exports);
export default module.exports;

If we use another ESM babel transform (such as transform-modules-systemjs) it causes nested duplication of code

System.register([], function (_export2, _context) {
  "use strict";

  return {
    setters: [],
    execute: function () {
      System.register([], function (_export, _context) {
        "use strict";

        var module, exports;
        return {
          setters: [],
          execute: function () {
            module = {
              exports: {}
            };
            exports = module.exports;
            (function () {
              this.name = 'true';
            }).call(module.exports);

            _export("default", module.exports);
          }
        };
      });
    }
  };
});

BABEL REPL


The issue seems to be coming from this line in the ThisExpression branch:

cursor.scope.path.replaceWith(program);

I'm not too familiar with babel's helper functions. What's your thoughts on this? Is there another method which will prevent duplication of the program?

@tbranyen
Copy link
Owner

Is the nested duplication breaking anything, or does it just look inefficient?

@gabemeola
Copy link
Contributor Author

For SystemJS in this case, it breaks dependency loading since the System.register call is duplicated.

@shrinktofit
Copy link

I use multi-pass to solve this problem. babel.transformFile + babel.transformAst.

@gabemeola
Copy link
Contributor Author

Replacing top level this exports with the exports keyword worked for me.
https://github.com/tbranyen/babel-plugin-transform-commonjs/pull/16/files#diff-13b5b151431c7e7a17f273559ed212d5R316

Although this implementation may not cover all use cases and doesn't handle early returns

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants