I'm trying find the best/working solution for transpiling my ECMA Script 6 code to ES5. I'd like to use a module loader and make use of inheritance. The closest I've got so far is by using Babel 6 with the es2015
preset, and transform-es2015-modules-systemjs
plugin. Here is my .babelrc
file:
{
"presets": ["es2015"],
"plugins": ["transform-es2015-modules-systemjs"]
}
And my files are structured like this:
- dist
(transpiled files in the same structure as the src folder)
- src
- classes
- Point.js
- ColorPoint.js
app.js
index.html
The contents of app.js
looks like this:
import ColorPoint from 'classes/ColorPoint.js';
let cp = new ColorPoint(25, 8, 'green');
console.log(cp.toString()); // '(25, 8) in green'
The definition of Point.js
looks like this:
export default class Point {
And the definition of ColorPoint.js
looks like this:
import Point from 'classes/Point.js';
export default class ColorPoint extends Point {
And just for completeness, the important part of index.html
looks like this:
<script src="node_modules/systemjs/dist/system.js"></script>
<script>
System.config({
baseURL: 'dist'
});
System.import('app.js');
</script>
I am transpiling the whole src folder to the dist folder using the command:
babel src -d dist
The problem is that Babel adds a single line to the top of the transpiled ColorPoint.js
file which breaks System.js at runtime. The error is:
Uncaught Error: Module http://localhost/es6-tutorial/dist/classes/ColorPoint.js interpreted as global module format, but called System.register.
But when I remove this line at the top of this file it works again:
function _typeof(obj) { return obj && typeof Symbol !== "undefined" && obj.constructor === Symbol ? "symbol" : typeof obj; }
I guess this might be a bug in the transpiler. I hoping to get some guidance from someone who's successfully implemented inheritance and module loading before. Or maybe point me to a current working example which I can look at.
Go to your package. json file where we'll create a npm build script using the babel command. The babel command takes two arguments: the path to your ES6 code and a path to where you want your ES5 code to go.
class keyword In the ES5 version, there are no classes; a function is used to make an object directly.
If you're using ES modules (which are ES6), you still need to transpile. Also, the thing you're calling 'ES6' may contain features that are naturally transpiled by Babel but aren't supported by Node/V8.
Wow, I am having the same problem! I was using traceur to transpile my code just fine and things have been running well for the past year, but traceur is not very active and there are more language features available in babel, so I decided to switch.
The process has been a bit tedious and now I am falling down on this very issue; a class that extends a base class is transpiled with a statement that preceeds the System.register call.
From the SystemJS docs on modules it states the precedence of module format identification:
Module format detection
When the module format is not set, automatic regular-expression-based detection is used. This module format detection is never completely accurate, but caters well for the majority use cases.
The module format detection happens in the following order:
System.register / System.registerDynamic If the source code starts with a number of comments, followed by System.register or System.registerDynamic as the first line of code.
ES modules The source is only detected as an ES module if it contains explicit module syntax - valid import or export statements.
AMD modules The presence of a valid AMD define statement in the code.
CommonJS modules The presence of require(...) or exports / module.exports assignments
Global This is the fallback module format after all the above fail.
So, the auto detection fails with inherited classes as the babel transpiler adds the mentioned line at the head of the file.
What needs to happen is add a config to tell systemjs that those compiled js files are in register format.
I have been playing around with meta && packages in system.config.js trying to find the magic incantation to identify all '**/*.js' files in my build folder as {format: 'register'} but cannot get the glob, or path, or something quite right.
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