├── .gitignore ├── .babelrc ├── .npmignore ├── test ├── fixtures │ ├── return_export_var │ │ ├── actual.js │ │ └── expected.js │ └── basic │ │ ├── actual.js │ │ └── expected.js └── index.js ├── .editorconfig ├── package.json ├── LICENSE ├── README.md └── src └── index.js /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | /dist 3 | *.log 4 | .directory 5 | -------------------------------------------------------------------------------- /.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": ["es2015"], 3 | "plugins": ["transform-runtime"], 4 | } 5 | -------------------------------------------------------------------------------- /.npmignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | /src 3 | /test 4 | *.log 5 | .directory 6 | .editorconfig 7 | .babelrc 8 | -------------------------------------------------------------------------------- /test/fixtures/return_export_var/actual.js: -------------------------------------------------------------------------------- 1 | import a from '/path/to/a'; 2 | import '/path/to/b'; 3 | import c from '/path/to/c'; 4 | import '/path/to/d'; 5 | import e from '/path/to/e'; 6 | doSomething(); 7 | export default x + y; 8 | doSomethingElse(); 9 | -------------------------------------------------------------------------------- /.editorconfig: -------------------------------------------------------------------------------- 1 | root = true 2 | 3 | [*] 4 | charset = utf-8 5 | trim_trailing_whitespace = true 6 | indent_style = tab 7 | indent_size = 4 8 | insert_final_newline = true 9 | 10 | [*.{json,babelrc,eslintrc}] 11 | indent_style = space 12 | indent_size = 2 13 | -------------------------------------------------------------------------------- /test/fixtures/basic/actual.js: -------------------------------------------------------------------------------- 1 | import a from '/path/to/a'; 2 | import '/path/to/b'; 3 | import c from '/path/to/c'; 4 | import '/path/to/d'; 5 | import {e, f as g, h, i as j} from '/path/to/e'; 6 | import {k} from '/path/to/k'; 7 | doSomething(); 8 | export default x + y; 9 | -------------------------------------------------------------------------------- /test/fixtures/return_export_var/expected.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | 3 | define(['/path/to/a', '/path/to/c', '/path/to/e', '/path/to/b', '/path/to/d'], function (a, c, e) { 4 | doSomething(); 5 | var _export_default = x + y; 6 | doSomethingElse(); 7 | return _export_default; 8 | }); 9 | -------------------------------------------------------------------------------- /test/fixtures/basic/expected.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | 3 | define(['/path/to/a', '/path/to/c', '/path/to/e', '/path/to/k', '/path/to/b', '/path/to/d'], function (a, c, _pathToE, _pathToK) { 4 | var e = _pathToE.e; 5 | var g = _pathToE.f; 6 | var h = _pathToE.h; 7 | var j = _pathToE.i; 8 | var k = _pathToK.k; 9 | doSomething(); 10 | return x + y; 11 | }); 12 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "babel-plugin-transform-es2015-modules-simple-amd", 3 | "version": "0.3.0", 4 | "description": "Simplified imports and exports", 5 | "repository": "finom/babel-plugin-transform-es2015-modules-simple-amd", 6 | "license": "MIT", 7 | "main": "dist/index.js", 8 | "dependencies": { 9 | "babel-runtime": "^6.3.19", 10 | "better-log": "^1.3.1", 11 | "babel-template": "^6.3.13" 12 | }, 13 | "devDependencies": { 14 | "babel-cli": "^6.3.17", 15 | "babel-core": "^6.3.21", 16 | "babel-plugin-transform-runtime": "^6.3.13", 17 | "babel-preset-es2015": "^6.5.0", 18 | "babel-register": "^6.3.13", 19 | "chalk": "^1.1.0", 20 | "clear": "0.0.1", 21 | "diff": "^1.4.0", 22 | "watch": "^0.16.0" 23 | }, 24 | "scripts": { 25 | "release": "babel src --out-dir dist", 26 | "test": "node test", 27 | "watch": "node test --watch", 28 | "prepublish": "npm test && npm run release" 29 | }, 30 | "keywords": [ 31 | "babel-plugin", 32 | "amd" 33 | ] 34 | } 35 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2016 Andrey Gubanov 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /test/index.js: -------------------------------------------------------------------------------- 1 | var assert = require('assert'); 2 | var babel = require('babel-core'); 3 | var chalk = require('chalk'); 4 | var clear = require('clear'); 5 | var diff = require('diff'); 6 | var fs = require('fs'); 7 | var path = require('path'); 8 | 9 | require('babel-register'); 10 | 11 | var pluginPath = require.resolve('../src'); 12 | 13 | function runTests() { 14 | var testsPath = __dirname + '/fixtures/'; 15 | 16 | fs.readdirSync(testsPath).map(function(item) { 17 | return { 18 | path: path.join(testsPath, item), 19 | name: item, 20 | }; 21 | }).filter(function(item) { 22 | return fs.statSync(item.path).isDirectory(); 23 | }).forEach(runTest); 24 | } 25 | 26 | function runTest(dir) { 27 | var output = babel.transformFileSync(dir.path + '/actual.js', { 28 | plugins: [pluginPath] 29 | }); 30 | 31 | var expected = fs.readFileSync(dir.path + '/expected.js', 'utf-8'); 32 | 33 | function normalizeLines(str) { 34 | return str.trimRight().replace(/\r\n/g, '\n'); 35 | } 36 | 37 | process.stdout.write(chalk.bgWhite.black(dir.name)); 38 | process.stdout.write('\n\n'); 39 | 40 | diff.diffLines(normalizeLines(output.code), normalizeLines(expected)) 41 | .forEach(function (part) { 42 | var value = part.value; 43 | if (part.added) { 44 | value = chalk.green(part.value); 45 | } else if (part.removed) { 46 | value = chalk.red(part.value); 47 | } 48 | 49 | 50 | process.stdout.write(value); 51 | }); 52 | 53 | process.stdout.write('\n\n\n'); 54 | } 55 | 56 | if (process.argv.indexOf('--watch') >= 0) { 57 | require('watch').watchTree(__dirname + '/..', function () { 58 | delete require.cache[pluginPath]; 59 | clear(); 60 | console.log('Press Ctrl+C to stop watching...'); 61 | console.log('================================'); 62 | try { 63 | runTests(); 64 | } catch (e) { 65 | console.error(chalk.magenta(e.stack)); 66 | } 67 | }); 68 | } else { 69 | runTests(); 70 | } 71 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # babel-plugin-transform-es2015-modules-simple-amd [![npm version](https://badge.fury.io/js/babel-plugin-transform-es2015-modules-simple-amd.svg)](https://badge.fury.io/js/babel-plugin-transform-es2015-modules-simple-amd) 2 | 3 | Limited transformer for ECMAScript 2015 modules (AMD) 4 | 5 | Converts this code: 6 | ```js 7 | import x from '/path/to/x'; 8 | import y from '/path/to/y'; 9 | doSomething(); 10 | export default x + y; 11 | ``` 12 | 13 | Into this one: 14 | ```js 15 | define(['/path/to/x', '/path/to/y'], function (x, y) { 16 | doSomething(); 17 | return x + y; 18 | }); 19 | ``` 20 | 21 | Instead of this one (generated with ``babel-plugin-transform-es2015-modules-amd``): 22 | ```js 23 | define(['exports', '/path/to/x', '/path/to/y'], function (exports, _x, _y) { 24 | Object.defineProperty(exports, "__esModule", { 25 | value: true 26 | }); 27 | 28 | var _x2 = _interopRequireDefault(_x); 29 | 30 | var _y2 = _interopRequireDefault(_y); 31 | 32 | function _interopRequireDefault(obj) { 33 | return obj && obj.__esModule ? obj : { 34 | 'default': obj 35 | }; 36 | } 37 | 38 | doSomething(); 39 | exports.default = _x2.default + _y2.default; 40 | }); 41 | ``` 42 | 43 | Supported features: 44 | - ``import SPECIFIER from 'PATH'`` 45 | - ``import 'PATH'`` 46 | - ``import {SPECIFIER1, SPECIFIER2 as SPECIFIER3} from 'PATH'`` 47 | - ``export default NODE`` 48 | 49 | Other features aren't supported. 50 | 51 | **Warning**. If no ``import`` or ``export`` are presented in JavaScript file, the plugin does nothing (means it doesn't wrap code with ``define``). 52 | 53 | ## Installation 54 | 55 | ```sh 56 | $ npm install --save-dev babel-plugin-transform-es2015-modules-simple-amd 57 | ``` 58 | 59 | ## Usage 60 | 61 | ### Via `.babelrc` (Recommended) 62 | 63 | **.babelrc** 64 | 65 | ```json 66 | { 67 | "plugins": ["transform-es2015-modules-simple-amd"] 68 | } 69 | ``` 70 | 71 | ### Via Node API 72 | 73 | ```javascript 74 | require('babel').transform('code', { 75 | plugins: ['transform-es2015-modules-simple-amd'] 76 | }); 77 | ``` 78 | 79 | [The same thing for CommonJS](https://github.com/finom/babel-plugin-transform-es2015-modules-simple-commonjs). 80 | 81 | Thanks to [RReverser](https://github.com/RReverser/babel-plugin-hello-world). 82 | -------------------------------------------------------------------------------- /src/index.js: -------------------------------------------------------------------------------- 1 | import 'better-log/install'; 2 | import template from "babel-template"; 3 | 4 | let buildModule = template(` 5 | define([IMPORT_PATHS], function(IMPORT_VARS) { 6 | NAMED_IMPORTS; 7 | BODY; 8 | }); 9 | `); 10 | 11 | module.exports = function({ types: t }) { 12 | return { 13 | visitor: { 14 | Program: { 15 | exit(path, file) { 16 | let body = path.get("body"), 17 | sources = [], 18 | anonymousSources = [], 19 | vars = [], 20 | namedImports = [], 21 | isModular = false, 22 | middleDefaultExportID = false; 23 | 24 | for (let i = 0; i < body.length; i++) { 25 | let path = body[i], 26 | isLast = i == body.length - 1; 27 | 28 | if (path.isExportDefaultDeclaration()) { 29 | let declaration = path.get("declaration"); 30 | 31 | if(isLast) { 32 | path.replaceWith(t.returnStatement(declaration.node)); 33 | } else { 34 | middleDefaultExportID = path.scope.generateUidIdentifier("export_default"); 35 | path.replaceWith(t.variableDeclaration('var', [t.variableDeclarator(middleDefaultExportID, declaration.node)])); 36 | } 37 | 38 | isModular = true; 39 | } 40 | 41 | if (path.isImportDeclaration()) { 42 | let specifiers = path.node.specifiers; 43 | 44 | if(specifiers.length == 0) { 45 | anonymousSources.push(path.node.source); 46 | } else if(specifiers.length == 1 && specifiers[0].type == 'ImportDefaultSpecifier') { 47 | sources.push(path.node.source); 48 | vars.push(specifiers[0]); 49 | } else { 50 | let importedID = path.scope.generateUidIdentifier(path.node.source.value); 51 | sources.push(path.node.source); 52 | vars.push(importedID); 53 | 54 | specifiers.forEach(({imported, local}) => { 55 | namedImports.push(t.variableDeclaration("var", [ 56 | t.variableDeclarator(t.identifier(local.name), t.identifier(importedID.name + '.' + imported.name)) 57 | ])); 58 | }); 59 | } 60 | 61 | path.remove(); 62 | 63 | isModular = true; 64 | } 65 | 66 | if(isLast && middleDefaultExportID) { 67 | path.insertAfter(t.returnStatement(middleDefaultExportID)); 68 | } 69 | } 70 | 71 | if(isModular) { 72 | path.node.body = [ 73 | buildModule({ 74 | IMPORT_PATHS: sources.concat(anonymousSources), 75 | IMPORT_VARS: vars, 76 | BODY: path.node.body, 77 | NAMED_IMPORTS: namedImports 78 | }) 79 | ]; 80 | } 81 | } 82 | } 83 | } 84 | }; 85 | }; 86 | --------------------------------------------------------------------------------