'use strict'; const rollup = require('rollup').rollup; const babel = require('rollup-plugin-babel'); const commonjs = require('rollup-plugin-commonjs'); const alias = require('rollup-plugin-alias'); const uglify = require('rollup-plugin-uglify'); const replace = require('rollup-plugin-replace'); const chalk = require('chalk'); const escapeStringRegexp = require('escape-string-regexp'); const join = require('path').join; const resolve = require('path').resolve; const fs = require('fs'); const rimraf = require('rimraf'); const argv = require('minimist')(process.argv.slice(2)); const Modules = require('./modules'); const Bundles = require('./bundles'); const propertyMangleWhitelist = require('./mangle').propertyMangleWhitelist; const sizes = require('./plugins/sizes-plugin'); const Stats = require('./stats'); const syncReactNative = require('./sync').syncReactNative; const Packaging = require('./packaging'); const Header = require('./header'); const UMD_DEV = Bundles.bundleTypes.UMD_DEV; const UMD_PROD = Bundles.bundleTypes.UMD_PROD; const NODE_DEV = Bundles.bundleTypes.NODE_DEV; const NODE_PROD = Bundles.bundleTypes.NODE_PROD; const FB_DEV = Bundles.bundleTypes.FB_DEV; const FB_PROD = Bundles.bundleTypes.FB_PROD; const RN_DEV = Bundles.bundleTypes.RN_DEV; const RN_PROD = Bundles.bundleTypes.RN_PROD; const reactVersion = require('../../package.json').version; const requestedBundleTypes = (argv.type || '') .split(',') .map(type => type.toUpperCase()); const requestedBundleNames = (argv._[0] || '') .split(',') .map(type => type.toLowerCase()); const syncFbsource = argv['sync-fbsource']; // used for when we property mangle with uglify/gcc const mangleRegex = new RegExp( `^(?${propertyMangleWhitelist .map(prop => `!${escapeStringRegexp(prop)}`) .join('|')}$).*$`, 'g' ); function getHeaderSanityCheck(bundleType, hasteName) { switch (bundleType) { case FB_DEV: case FB_PROD: case RN_DEV: case RN_PROD: let hasteFinalName = hasteName; switch (bundleType) { case FB_DEV: case RN_DEV: hasteFinalName += '-dev'; break; case FB_PROD: case RN_PROD: hasteFinalName += '-prod'; break; } return hasteFinalName; case UMD_DEV: case UMD_PROD: return reactVersion; default: return null; } } function getBanner(bundleType, hasteName, filename) { switch (bundleType) { // UMDs are not wrapped in conditions. case UMD_DEV: case UMD_PROD: return Header.getUMDHeader(filename, reactVersion); // CommonJS DEV bundle is guarded to help weak dead code elimination. case NODE_DEV: return `'use strict';\n\n\nif (process.env.NODE_ENV !== "production") {\n`; case NODE_PROD: return ''; // FB and RN DEV bundles are also guarded. // Additionally, all FB and RN bundles need Haste headers. case FB_DEV: case FB_PROD: case RN_DEV: case RN_PROD: const isDev = bundleType === FB_DEV || bundleType === RN_DEV; const hasteFinalName = hasteName + (isDev ? '-dev' : '-prod'); return ( Header.getProvidesHeader(hasteFinalName) + (isDev ? `\n\n'use strict';\n\n\nif (__DEV__) {\n` : '') ); default: throw new Error('Unknown type.'); } } function getFooter(bundleType) { // Only need a footer if getBanner() has an opening brace. switch (bundleType) { // Non-UMD DEV bundles need conditions to help weak dead code elimination. case NODE_DEV: case FB_DEV: case RN_DEV: return '\n}\n'; default: return ''; } } function updateBabelConfig(babelOpts, bundleType) { switch (bundleType) { case UMD_DEV: case UMD_PROD: case NODE_DEV: case NODE_PROD: return Object.assign({}, babelOpts, { plugins: babelOpts.plugins.concat([ // Use object-assign polyfill in open source resolve('./scripts/babel/transform-object-assign-require'), // Replace __DEV__ with process.env.NODE_ENV and minify invariant messages require('../error-codes/dev-expression-with-codes'), ]), }); default: return babelOpts; } } function handleRollupWarnings(warning) { if (warning.code === 'UNRESOLVED_IMPORT') { console.error(warning.message); process.exit(1); } console.warn(warning.message || warning); } function updateBundleConfig(config, filename, format, bundleType, hasteName) { return Object.assign({}, config, { banner: getBanner(bundleType, hasteName, filename), dest: Packaging.getPackageDestination(config, bundleType, filename), footer: getFooter(bundleType), format, interop: false, }); } function stripEnvVariables(production) { return { __DEV__: production ? 'false' : 'true', 'process.env.NODE_ENV': production ? "'production'" : "'development'", }; } function getFormat(bundleType) { switch (bundleType) { case UMD_DEV: case UMD_PROD: return `umd`; case NODE_DEV: case NODE_PROD: case FB_DEV: case FB_PROD: case RN_DEV: case RN_PROD: return `cjs`; } } function getFilename(name, hasteName, bundleType) { // we do this to replace / to -, for react-dom/server name = name.replace('/', '-'); switch (bundleType) { case UMD_DEV: return `${name}.development.js`; case UMD_PROD: return `${name}.production.min.js`; case NODE_DEV: return `${name}.development.js`; case NODE_PROD: return `${name}.production.min.js`; case FB_DEV: case RN_DEV: return `${hasteName}-dev.js`; case FB_PROD: case RN_PROD: return `${hasteName}-prod.js`; } } function uglifyConfig(configs) { var mangle = configs.mangle; var manglePropertiesOnProd = configs.manglePropertiesOnProd; var preserveVersionHeader = configs.preserveVersionHeader; var removeComments = configs.removeComments; var headerSanityCheck = configs.headerSanityCheck; return { warnings: false, compress: { screw_ie8: true, dead_code: true, unused: true, drop_debugger: true, // we have a string literal