Browse Source

resolve merge conflict

contingency-plan
Rich-Harris 10 years ago
parent
commit
a3b935b5d1
  1. 71
      src/Bundle.js
  2. 4
      src/finalisers/amd.js
  3. 26
      src/finalisers/cjs.js
  4. 4
      src/finalisers/es6.js
  5. 4
      src/finalisers/umd.js
  6. 2
      src/utils/object.js
  7. 8
      test/samples/export-default-expression/_config.js
  8. 1
      test/samples/export-default-expression/main.js
  9. 12
      test/test.js

71
src/Bundle.js

@ -1,5 +1,10 @@
<<<<<<< HEAD
import { dirname, resolve } from 'path';
import { readFile, Promise } from 'sander';
=======
import { basename, extname, resolve } from 'path';
import { readFile } from 'sander';
>>>>>>> 281d5ca00ac28f62b06bb265987ba59cae7b2eff
import MagicString from 'magic-string';
import { keys, has } from './utils/object';
import { sequence } from './utils/promise';
@ -10,6 +15,10 @@ import replaceIdentifiers from './utils/replaceIdentifiers';
import makeLegalIdentifier from './utils/makeLegalIdentifier';
import { defaultResolver } from './utils/resolvePath';
function badExports ( option, keys ) {
throw new Error( `'${option}' was specified for options.exports, but entry module has following exports: ${keys.join(', ')}` );
}
export default class Bundle {
constructor ( options ) {
this.entryPath = resolve( options.entry ).replace( /\.js$/, '' ) + '.js';
@ -21,6 +30,7 @@ export default class Bundle {
this.modulePromises = {};
this.statements = [];
this.externalModules = [];
this.defaultExportName = null;
}
fetchModule ( importee, importer ) {
@ -74,11 +84,29 @@ export default class Bundle {
// Exclude imports
if ( /^Import/.test( node.type ) ) return;
if ( node.type === 'ExportNamedDeclaration' ) {
// Exclude specifier exports
if ( node.specifiers.length ) return;
// Exclude default exports that proxy a name
// e.g. `export default foo`
if ( node.type === 'ExportDefaultDeclaration' && /Declaration$/.test( node.declaration.type ) ) return;
// Exclude specifier exports
// e.g. `export { foo }`
if ( node.type === 'ExportNamedDeclaration' && node.specifiers.length ) return;
// Include everything else...
if ( node.type === 'ExportDefaultDeclaration' ) {
// TODO generic 'get deconflicted name' mechanism
let defaultExportName = makeLegalIdentifier( basename( this.entryPath ).slice( 0, -extname( this.entryPath ).length ) );
while ( this.entryModule.ast._scope.contains( defaultExportName ) ) {
defaultExportName = `_${defaultExportName}`;
}
// Remove the `export` from everything else
this.defaultExportName = defaultExportName;
node._source.overwrite( node.start, node.declaration.start, `var ${defaultExportName} = ` );
}
if ( node.type === 'ExportNamedDeclaration' ) {
// Remove the `export`
node._source.remove( node.start, node.declaration.start );
}
@ -138,6 +166,9 @@ export default class Bundle {
generate ( options = {} ) {
let magicString = new MagicString.Bundle({ separator: '' });
// Determine export mode - 'default', 'named', 'none'
let exportMode = this.getExportMode( options.exports );
// Apply new names and add to the output bundle
this.statements.forEach( statement => {
let replacements = {};
@ -164,7 +195,7 @@ export default class Bundle {
throw new Error( `You must specify an output type - valid options are ${keys( finalisers ).join( ', ' )}` );
}
magicString = finalise( this, magicString, options );
magicString = finalise( this, magicString, exportMode, options );
return {
code: magicString.toString(),
@ -175,4 +206,32 @@ export default class Bundle {
})
};
}
}
getExportMode ( exportMode ) {
const exportKeys = keys( this.entryModule.exports );
if ( exportMode === 'default' ) {
if ( exportKeys.length !== 1 || exportKeys[0] !== 'default' ) {
badExports( 'default', exportKeys );
}
} else if ( exportMode === 'none' && exportKeys.length ) {
badExports( 'none', exportKeys );
}
if ( !exportMode || exportMode === 'auto' ) {
if ( exportKeys.length === 0 ) {
exportMode = 'none';
} else if ( exportKeys.length === 1 && exportKeys[0] === 'default' ) {
exportMode = 'default';
} else {
exportMode = 'named';
}
}
if ( !/(?:default|named|none)/.test( exportMode ) ) {
throw new Error( `options.exports must be 'default', 'named', 'none', 'auto', or left unspecified (defaults to 'auto')` );
}
return exportMode;
}
}

4
src/finalisers/amd.js

@ -1,3 +1,3 @@
export default function amd ( bundle, magicString, options ) {
export default function amd ( bundle, magicString, exportMode, options ) {
throw new Error( 'TODO' );
}
}

26
src/finalisers/cjs.js

@ -1,6 +1,6 @@
import { keys } from '../utils/object';
export default function cjs ( bundle, magicString ) {
export default function cjs ( bundle, magicString, exportMode ) {
let intro = `'use strict';\n\n`;
// TODO handle ambiguous default imports
@ -24,19 +24,23 @@ export default function cjs ( bundle, magicString ) {
magicString.prepend( intro );
// TODO handle default exports
const exportBlock = keys( bundle.entryModule.exports )
.map( key => {
const specifier = bundle.entryModule.exports[ key ];
const name = bundle.entryModule.getCanonicalName( specifier.localName );
return `exports.${key} = ${name};`;
})
.join( '\n' );
let exportBlock;
if ( exportMode === 'default' && bundle.entryModule.exports.default ) {
exportBlock = `module.exports = ${bundle.defaultExportName};`;
} else if ( exportMode === 'named' ) {
exportBlock = keys( bundle.entryModule.exports )
.map( key => {
const specifier = bundle.entryModule.exports[ key ];
const name = bundle.entryModule.getCanonicalName( specifier.localName );
return `exports.${key} = ${name};`;
})
.join( '\n' );
}
if ( exportBlock ) {
magicString.append( '\n\n' + exportBlock );
}
return magicString;
}
}

4
src/finalisers/es6.js

@ -1,3 +1,3 @@
export default function es6 ( bundle, magicString, options ) {
export default function es6 ( bundle, magicString, exportMode, options ) {
throw new Error( 'TODO' );
}
}

4
src/finalisers/umd.js

@ -1,4 +1,4 @@
export default function umd ( bundle, magicString, options ) {
export default function umd ( bundle, magicString, exportMode, options ) {
const indentStr = magicString.getIndentString();
const intro =
@ -21,4 +21,4 @@ export default function umd ( bundle, magicString, options ) {
.indent()
.append( '\n\n}));' )
.prepend( intro );
}
}

2
src/utils/object.js

@ -4,4 +4,4 @@ export const hasOwnProp = Object.prototype.hasOwnProperty;
export function has ( obj, prop ) {
return hasOwnProp.call( obj, prop );
}
}

8
test/samples/export-default-expression/_config.js

@ -0,0 +1,8 @@
var assert = require( 'assert' );
module.exports = {
description: 'exports a default value as module.exports',
exports: function ( exports ) {
assert.equal( exports, 42 );
}
};

1
test/samples/export-default-expression/main.js

@ -0,0 +1 @@
export default 42;

12
test/test.js

@ -40,12 +40,14 @@ describe( 'rollup', function () {
}));
try {
var fn = new Function( 'require', 'exports', 'assert', result.code );
var exports = {};
fn( require, exports, assert );
var fn = new Function( 'require', 'module', 'exports', 'assert', result.code );
var module = {
exports: {}
};
fn( require, module, module.exports, assert );
if ( config.exports ) {
config.exports( exports, assert );
config.exports( module.exports, assert );
}
} catch ( err ) {
console.log( result.code );
@ -58,4 +60,4 @@ describe( 'rollup', function () {
});
});
});
});
});

Loading…
Cancel
Save