Reviewed By: jeanlauliac

Differential Revision: D4628330

fbshipit-source-id: 94fad1294e22fa0073e15843f94241ae778112a0
This commit is contained in:
Christoph Pojer 2017-03-01 08:05:59 -08:00 коммит произвёл Facebook Github Bot
Родитель 04f42ab075
Коммит 4d00df41b4
23 изменённых файлов: 176 добавлений и 179 удалений

Просмотреть файл

@ -29,7 +29,7 @@ function escapeRegExp(pattern) {
} else if (typeof pattern === 'string') { } else if (typeof pattern === 'string') {
var escaped = pattern.replace(/[\-\[\]\{\}\(\)\*\+\?\.\\\^\$\|]/g, '\\$&'); var escaped = pattern.replace(/[\-\[\]\{\}\(\)\*\+\?\.\\\^\$\|]/g, '\\$&');
// convert the '/' into an escaped local file separator // convert the '/' into an escaped local file separator
return escaped.replace(/\//g,'\\' + path.sep); return escaped.replace(/\//g, '\\' + path.sep);
} else { } else {
throw new Error('Unexpected packager blacklist pattern: ' + pattern); throw new Error('Unexpected packager blacklist pattern: ' + pattern);
} }

Просмотреть файл

@ -12,7 +12,6 @@ jest.disableAutomock();
const Bundle = require('../Bundle'); const Bundle = require('../Bundle');
const ModuleTransport = require('../../lib/ModuleTransport'); const ModuleTransport = require('../../lib/ModuleTransport');
const SourceMapGenerator = require('source-map').SourceMapGenerator;
const crypto = require('crypto'); const crypto = require('crypto');
describe('Bundle', () => { describe('Bundle', () => {
@ -107,33 +106,37 @@ describe('Bundle', () => {
}); });
}); });
it('should insert modules in a deterministic order, independent from timing of the wrapping process', () => { it('inserts modules in a deterministic order, independent of timing of the wrapper process',
const moduleTransports = [ () => {
createModuleTransport({name: 'module1'}), const moduleTransports = [
createModuleTransport({name: 'module2'}), createModuleTransport({name: 'module1'}),
createModuleTransport({name: 'module3'}), createModuleTransport({name: 'module2'}),
]; createModuleTransport({name: 'module3'}),
];
const resolves = {}; const resolves = {};
const resolver = { const resolver = {
wrapModule({name}) { wrapModule({name}) {
return new Promise(resolve => resolves[name] = resolve); return new Promise(resolve => {
}, resolves[name] = resolve;
}; });
},
};
const promise = Promise.all( const promise = Promise.all(moduleTransports.map(
moduleTransports.map(m => bundle.addModule(resolver, null, {isPolyfill: () => false}, m))) m => bundle.addModule(resolver, null, {isPolyfill: () => false}, m)
.then(() => { )).then(() => {
expect(bundle.getModules()) expect(bundle.getModules())
.toEqual(moduleTransports); .toEqual(moduleTransports);
}); });
resolves.module2({code: ''}); resolves.module2({code: ''});
resolves.module3({code: ''}); resolves.module3({code: ''});
resolves.module1({code: ''}); resolves.module1({code: ''});
return promise; return promise;
}); },
);
}); });
describe('sourcemap bundle', () => { describe('sourcemap bundle', () => {
@ -268,7 +271,6 @@ describe('Bundle', () => {
describe('getEtag()', function() { describe('getEtag()', function() {
it('should return an etag', function() { it('should return an etag', function() {
var bundle = new Bundle({sourceMapUrl: 'test_url'});
bundle.finalize({}); bundle.finalize({});
var eTag = crypto.createHash('md5').update(bundle.getSource()).digest('hex'); var eTag = crypto.createHash('md5').update(bundle.getSource()).digest('hex');
expect(bundle.getEtag()).toEqual(eTag); expect(bundle.getEtag()).toEqual(eTag);

Просмотреть файл

@ -38,7 +38,10 @@ const VERSION = require('../../package.json').version;
import type AssetServer from '../AssetServer'; import type AssetServer from '../AssetServer';
import type Module, {HasteImpl} from '../node-haste/Module'; import type Module, {HasteImpl} from '../node-haste/Module';
import type ResolutionResponse from '../node-haste/DependencyGraph/ResolutionResponse'; import type ResolutionResponse from '../node-haste/DependencyGraph/ResolutionResponse';
import type {Options as JSTransformerOptions, TransformOptions} from '../JSTransformer/worker/worker'; import type {
Options as JSTransformerOptions,
TransformOptions,
} from '../JSTransformer/worker/worker';
import type {Reporter} from '../lib/reporting'; import type {Reporter} from '../lib/reporting';
import type GlobalTransformCache from '../lib/GlobalTransformCache'; import type GlobalTransformCache from '../lib/GlobalTransformCache';

Просмотреть файл

@ -8,13 +8,14 @@
* *
* @flow * @flow
*/ */
/** /**
* Copyright 2011 Mozilla Foundation and contributors * Copyright 2011 Mozilla Foundation and contributors
* Licensed under the New BSD license. See LICENSE or: * Licensed under the New BSD license. See LICENSE or:
* http://opensource.org/licenses/BSD-3-Clause * http://opensource.org/licenses/BSD-3-Clause
* *
* Based on the Base 64 VLQ implementation in Closure Compiler: * Based on the Base 64 VLQ implementation in Closure Compiler:
* https://code.google.com/p/closure-compiler/source/browse/trunk/src/com/google/debugging/sourcemap/Base64VLQ.java * https://git.io/vymuA
* *
* Copyright 2011 The Closure Compiler Authors. All rights reserved. * Copyright 2011 The Closure Compiler Authors. All rights reserved.
* Redistribution and use in source and binary forms, with or without * Redistribution and use in source and binary forms, with or without
@ -107,7 +108,8 @@ function toVLQSigned(value) {
* V8 OPTIMIZATION! * V8 OPTIMIZATION!
*/ */
function encode(value: number, buffer: Buffer, position: number): number { function encode(value: number, buffer: Buffer, position: number): number {
let digit, vlq = toVLQSigned(value); let vlq = toVLQSigned(value);
let digit;
do { do {
digit = vlq & VLQ_BASE_MASK; digit = vlq & VLQ_BASE_MASK;
vlq >>>= VLQ_BASE_SHIFT; vlq >>>= VLQ_BASE_SHIFT;

Просмотреть файл

@ -8,6 +8,8 @@
*/ */
'use strict'; 'use strict';
/* eslint-disable max-len */
jest.disableAutomock(); jest.disableAutomock();
const inline = require('../inline'); const inline = require('../inline');
const {transform, transformFromAst} = require('babel-core'); const {transform, transformFromAst} = require('babel-core');
@ -205,7 +207,9 @@ describe('inline constants', () => {
var b = a.ReactNative.Platform.select({}); var b = a.ReactNative.Platform.select({});
}`; }`;
const {ast} = inline('arbitrary.js', {code}, {platform: 'ios'}); const {ast} = inline('arbitrary.js', {code}, {platform: 'ios'});
expect(toString(ast)).toEqual(normalize(code.replace(/ReactNative\.Platform\.select[^;]+/, '1'))); expect(toString(ast)).toEqual(
normalize(code.replace(/ReactNative\.Platform\.select[^;]+/, '1')),
);
}); });
it('replaces React.Platform.select in the code if React is a top level import', () => { it('replaces React.Platform.select in the code if React is a top level import', () => {
@ -237,7 +241,9 @@ describe('inline constants', () => {
var b = a.ReactNative.Platform.select; var b = a.ReactNative.Platform.select;
}`; }`;
const {ast} = inline('arbitrary.js', {code}, {platform: 'android'}); const {ast} = inline('arbitrary.js', {code}, {platform: 'android'});
expect(toString(ast)).toEqual(normalize(code.replace(/ReactNative.Platform\.select[^;]+/, '2'))); expect(toString(ast)).toEqual(
normalize(code.replace(/ReactNative.Platform\.select[^;]+/, '2')),
);
}); });
it('replaces require("react-native").Platform.select in the code', () => { it('replaces require("react-native").Platform.select in the code', () => {
@ -269,18 +275,6 @@ describe('inline constants', () => {
normalize(code.replace(/process\.env\.NODE_ENV/, '"production"'))); normalize(code.replace(/process\.env\.NODE_ENV/, '"production"')));
}); });
it('replaces process.env.NODE_ENV in the code', () => {
const code = `function a() {
if (process.env.NODE_ENV === 'production') {
return require('Prod');
}
return require('Dev');
}`;
const {ast} = inline('arbitrary.js', {code}, {dev: true});
expect(toString(ast)).toEqual(
normalize(code.replace(/process\.env\.NODE_ENV/, '"development"')));
});
it('accepts an AST as input', function() { it('accepts an AST as input', function() {
const code = 'function ifDev(a,b){return __DEV__?a:b;}'; const code = 'function ifDev(a,b){return __DEV__?a:b;}';
const {ast} = inline('arbitrary.hs', {ast: toAst(code)}, {dev: false}); const {ast} = inline('arbitrary.hs', {ast: toAst(code)}, {dev: false});

Просмотреть файл

@ -33,7 +33,12 @@ function extractDependencies(code: string) {
const node = path.node; const node = path.node;
const callee = node.callee; const callee = node.callee;
const arg = node.arguments[0]; const arg = node.arguments[0];
if (callee.type !== 'Identifier' || callee.name !== 'require' || !arg || arg.type !== 'StringLiteral') { if (
callee.type !== 'Identifier' ||
callee.name !== 'require' ||
!arg ||
arg.type !== 'StringLiteral'
) {
return; return;
} }
dependencyOffsets.push(arg.start); dependencyOffsets.push(arg.start);

Просмотреть файл

@ -208,50 +208,52 @@ describe('Graph:', () => {
}); });
}); });
it('calls back with an array of modules in depth-first traversal order, regardless of the order of resolution', done => { it('resolves modules in depth-first traversal order, regardless of the order of resolution',
load.stub.reset(); done => {
resolve.stub.reset(); load.stub.reset();
resolve.stub.reset();
const ids = [ const ids = [
'a', 'a',
'b', 'b',
'c', 'd', 'c', 'd',
'e', 'e',
'f', 'g', 'f', 'g',
'h', 'h',
]; ];
ids.forEach(id => { ids.forEach(id => {
const path = idToPath(id); const path = idToPath(id);
resolve.stub.withArgs(id).yields(null, path); resolve.stub.withArgs(id).yields(null, path);
load.stub.withArgs(path).yields(null, createFile(id), []); load.stub.withArgs(path).yields(null, createFile(id), []);
}); });
load.stub.withArgs(idToPath('a')).yields(null, createFile('a'), ['b', 'e', 'h']); load.stub.withArgs(idToPath('a')).yields(null, createFile('a'), ['b', 'e', 'h']);
load.stub.withArgs(idToPath('b')).yields(null, createFile('b'), ['c', 'd']); load.stub.withArgs(idToPath('b')).yields(null, createFile('b'), ['c', 'd']);
load.stub.withArgs(idToPath('e')).yields(null, createFile('e'), ['f', 'g']); load.stub.withArgs(idToPath('e')).yields(null, createFile('e'), ['f', 'g']);
// load certain ids later // load certain ids later
['b', 'e', 'h'].forEach(id => resolve.stub.withArgs(id).resetBehavior()); ['b', 'e', 'h'].forEach(id => resolve.stub.withArgs(id).resetBehavior());
resolve.stub.withArgs('h').func = (a, b, c, d, callback) => { resolve.stub.withArgs('h').func = (a, b, c, d, callback) => {
callback(null, idToPath('h')); callback(null, idToPath('h'));
['e', 'b'].forEach( ['e', 'b'].forEach(
id => resolve.stub.withArgs(id).yield(null, idToPath(id))); id => resolve.stub.withArgs(id).yield(null, idToPath(id)));
}; };
graph(['a'], anyPlatform, noOpts, (error, result) => { graph(['a'], anyPlatform, noOpts, (error, result) => {
expect(error).toEqual(null); expect(error).toEqual(null);
expect(result.modules).toEqual([ expect(result.modules).toEqual([
createModule('a', ['b', 'e', 'h']), createModule('a', ['b', 'e', 'h']),
createModule('b', ['c', 'd']), createModule('b', ['c', 'd']),
createModule('c'), createModule('c'),
createModule('d'), createModule('d'),
createModule('e', ['f', 'g']), createModule('e', ['f', 'g']),
createModule('f'), createModule('f'),
createModule('g'), createModule('g'),
createModule('h'), createModule('h'),
]); ]);
done(); done();
}); });
}); },
);
it('calls back with the resolved modules of the entry points', done => { it('calls back with the resolved modules of the entry points', done => {
load.stub.reset(); load.stub.reset();
@ -274,7 +276,7 @@ describe('Graph:', () => {
}); });
}); });
it('calls back with the resolved modules of the entry points if one entry point is a dependency of another', done => { it('resolves modules for all entry points correctly if one is a dependency of another', done => {
load.stub.reset(); load.stub.reset();
resolve.stub.reset(); resolve.stub.reset();

Просмотреть файл

@ -25,7 +25,9 @@ module.exports = class HasteFS {
} }
closest(path: string, fileName: string): ?string { closest(path: string, fileName: string): ?string {
let {dir, root} = parse(path); const parsedPath = parse(path);
const root = parsedPath.root;
let dir = parsedPath.dir;
do { do {
const candidate = join(dir, fileName); const candidate = join(dir, fileName);
if (this.files.has(candidate)) { if (this.files.has(candidate)) {
@ -63,7 +65,9 @@ module.exports = class HasteFS {
function buildDirectorySet(files) { function buildDirectorySet(files) {
const directories = new Set(); const directories = new Set();
files.forEach(path => { files.forEach(path => {
let {dir, root} = parse(path); const parsedPath = parse(path);
const root = parsedPath.root;
let dir = parsedPath.dir;
while (dir !== '.' && dir !== root && !directories.has(dir)) { while (dir !== '.' && dir !== root && !directories.has(dir)) {
directories.add(dir); directories.add(dir);
dir = dirname(dir); dir = dirname(dir);

Просмотреть файл

@ -63,27 +63,29 @@ describe('dependency collection from ASTs:', () => {
.toEqual(any(String)); .toEqual(any(String));
}); });
it('replaces all required module ID strings with array lookups and keeps the ID as second argument', () => { it('replaces all required module ID strings with array lookups, keeps the ID as second argument',
const ast = astFromCode(` () => {
const a = require('b/lib/a'); const ast = astFromCode(`
const b = require(123); const a = require('b/lib/a');
exports.do = () => require("do"); const b = require(123);
if (!something) { exports.do = () => require("do");
require("setup/something"); if (!something) {
} require("setup/something");
`); }
`);
const {dependencyMapName} = collectDependencies(ast); const {dependencyMapName} = collectDependencies(ast);
expect(codeFromAst(ast)).toEqual(comparableCode(` expect(codeFromAst(ast)).toEqual(comparableCode(`
const a = require(${dependencyMapName}[0], 'b/lib/a'); const a = require(${dependencyMapName}[0], 'b/lib/a');
const b = require(123); const b = require(123);
exports.do = () => require(${dependencyMapName}[1], "do"); exports.do = () => require(${dependencyMapName}[1], "do");
if (!something) { if (!something) {
require(${dependencyMapName}[2], "setup/something"); require(${dependencyMapName}[2], "setup/something");
} }
`)); `));
}); },
);
}); });
describe('Dependency collection from optimized ASTs:', () => { describe('Dependency collection from optimized ASTs:', () => {

Просмотреть файл

@ -94,4 +94,5 @@ function findLast(code, needle) {
return {line: line + 1, column}; return {line: line + 1, column};
} }
} }
return null;
} }

Просмотреть файл

@ -19,8 +19,6 @@ const {parse} = require('babylon');
const generate = require('babel-generator').default; const generate = require('babel-generator').default;
const {traverse} = require('babel-core'); const {traverse} = require('babel-core');
const {any, objectContaining} = jasmine;
describe('transforming JS modules:', () => { describe('transforming JS modules:', () => {
const filename = 'arbitrary'; const filename = 'arbitrary';
@ -47,7 +45,7 @@ describe('transforming JS modules:', () => {
it('passes through file name and code', done => { it('passes through file name and code', done => {
transformModule(sourceCode, options(), (error, result) => { transformModule(sourceCode, options(), (error, result) => {
expect(result).toEqual(objectContaining({ expect(result).toEqual(expect.objectContaining({
code: sourceCode, code: sourceCode,
file: filename, file: filename,
})); }));
@ -59,36 +57,39 @@ describe('transforming JS modules:', () => {
const hasteID = 'TheModule'; const hasteID = 'TheModule';
const codeWithHasteID = `/** @providesModule ${hasteID} */`; const codeWithHasteID = `/** @providesModule ${hasteID} */`;
transformModule(codeWithHasteID, options(), (error, result) => { transformModule(codeWithHasteID, options(), (error, result) => {
expect(result).toEqual(objectContaining({hasteID})); expect(result).toEqual(expect.objectContaining({hasteID}));
done(); done();
}); });
}); });
it('sets `type` to `"module"` by default', done => { it('sets `type` to `"module"` by default', done => {
transformModule(sourceCode, options(), (error, result) => { transformModule(sourceCode, options(), (error, result) => {
expect(result).toEqual(objectContaining({type: 'module'})); expect(result).toEqual(expect.objectContaining({type: 'module'}));
done(); done();
}); });
}); });
it('sets `type` to `"script"` if the input is a polyfill', done => { it('sets `type` to `"script"` if the input is a polyfill', done => {
transformModule(sourceCode, {...options(), polyfill: true}, (error, result) => { transformModule(sourceCode, {...options(), polyfill: true}, (error, result) => {
expect(result).toEqual(objectContaining({type: 'script'})); expect(result).toEqual(expect.objectContaining({type: 'script'}));
done(); done();
}); });
}); });
it('calls the passed-in transform function with code, file name, and options for all passed in variants', done => { it('calls the passed-in transform function with code, file name, and options ' +
const variants = {dev: {dev: true}, prod: {dev: false}}; 'for all passed in variants',
done => {
const variants = {dev: {dev: true}, prod: {dev: false}};
transformModule(sourceCode, options(variants), () => { transformModule(sourceCode, options(variants), () => {
expect(transformer.transform) expect(transformer.transform)
.toBeCalledWith(sourceCode, filename, variants.dev); .toBeCalledWith(sourceCode, filename, variants.dev);
expect(transformer.transform) expect(transformer.transform)
.toBeCalledWith(sourceCode, filename, variants.prod); .toBeCalledWith(sourceCode, filename, variants.prod);
done(); done();
}); });
}); },
);
it('calls back with any error yielded by the transform function', done => { it('calls back with any error yielded by the transform function', done => {
const error = new Error(); const error = new Error();
@ -114,7 +115,7 @@ describe('transforming JS modules:', () => {
}); });
}); });
it('wraps the code produced by the transform function into an immediately invoked function expression for polyfills', done => { it('wraps the code produced by the transform function into an IIFE for polyfills', done => {
transformModule(sourceCode, {...options(), polyfill: true}, (error, result) => { transformModule(sourceCode, {...options(), polyfill: true}, (error, result) => {
expect(error).toEqual(null); expect(error).toEqual(null);
@ -131,20 +132,21 @@ describe('transforming JS modules:', () => {
const column = code.indexOf('code'); const column = code.indexOf('code');
const consumer = new SourceMapConsumer(map); const consumer = new SourceMapConsumer(map);
expect(consumer.originalPositionFor({line: 1, column})) expect(consumer.originalPositionFor({line: 1, column}))
.toEqual(objectContaining({line: 1, column: sourceCode.indexOf('code')})); .toEqual(expect.objectContaining({line: 1, column: sourceCode.indexOf('code')}));
done(); done();
}); });
}); });
it('extracts dependencies (require calls)', done => { it('extracts dependencies (require calls)', done => {
const dep1 = 'foo', dep2 = 'bar'; const dep1 = 'foo';
const dep2 = 'bar';
const code = `require('${dep1}'),require('${dep2}')`; const code = `require('${dep1}'),require('${dep2}')`;
const {body} = parse(code).program; const {body} = parse(code).program;
transformer.transform.stub.returns(transformResult(body)); transformer.transform.stub.returns(transformResult(body));
transformModule(code, options(), (error, result) => { transformModule(code, options(), (error, result) => {
expect(result.transformed.default) expect(result.transformed.default)
.toEqual(objectContaining({dependencies: [dep1, dep2]})); .toEqual(expect.objectContaining({dependencies: [dep1, dep2]}));
done(); done();
}); });
}); });
@ -190,7 +192,7 @@ describe('transforming JS modules:', () => {
it('does not create source maps for JSON files', done => { it('does not create source maps for JSON files', done => {
transformModule('{}', {...options(), filename: 'some.json'}, (error, result) => { transformModule('{}', {...options(), filename: 'some.json'}, (error, result) => {
expect(result.transformed.default) expect(result.transformed.default)
.toEqual(objectContaining({map: null})); .toEqual(expect.objectContaining({map: null}));
done(); done();
}); });
}); });

Просмотреть файл

@ -44,7 +44,8 @@ function transformModule(
callback: Callback<TransformedFile>, callback: Callback<TransformedFile>,
): void { ): void {
if (options.filename.endsWith('.json')) { if (options.filename.endsWith('.json')) {
return transformJSON(code, options, callback); transformJSON(code, options, callback);
return;
} }
const {filename, transformer, variants = defaultVariants} = options; const {filename, transformer, variants = defaultVariants} = options;
@ -86,6 +87,7 @@ function transformModule(
type: options.polyfill ? 'script' : 'module', type: options.polyfill ? 'script' : 'module',
}); });
}); });
return;
} }
function transformJSON(json, options, callback) { function transformJSON(json, options, callback) {

Просмотреть файл

@ -237,40 +237,6 @@ describe('Resolver', function() {
}); });
}); });
it('should get dependencies with polyfills', function() {
var module = createModule('index');
var deps = [module];
var depResolver = new Resolver({
projectRoot: '/root',
});
DependencyGraph.prototype.getDependencies.mockImplementation(function() {
return Promise.resolve(new ResolutionResponseMock({
dependencies: deps,
mainModuleId: 'index',
}));
});
const polyfill = {};
DependencyGraph.prototype.createPolyfill.mockReturnValueOnce(polyfill);
return depResolver
.getDependencies(
'/root/index.js',
{dev: true},
undefined,
undefined,
createGetModuleId()
).then(function(result) {
expect(result.mainModuleId).toEqual('index');
expect(DependencyGraph.mock.instances[0].getDependencies)
.toBeCalledWith({entryPath: '/root/index.js', recursive: true});
expect(result.dependencies[0]).toBe(polyfill);
expect(result.dependencies[result.dependencies.length - 1])
.toBe(module);
});
});
it('should pass in more polyfills', function() { it('should pass in more polyfills', function() {
var module = createModule('index'); var module = createModule('index');
var deps = [module]; var deps = [module];
@ -296,7 +262,9 @@ describe('Resolver', function() {
createGetModuleId() createGetModuleId()
).then(result => { ).then(result => {
expect(result.mainModuleId).toEqual('index'); expect(result.mainModuleId).toEqual('index');
expect(DependencyGraph.prototype.createPolyfill.mock.calls[result.dependencies.length - 2]).toEqual([ const calls =
DependencyGraph.prototype.createPolyfill.mock.calls[result.dependencies.length - 2];
expect(calls).toEqual([
{file: 'some module', {file: 'some module',
id: 'some module', id: 'some module',
dependencies: [ dependencies: [
@ -444,7 +412,8 @@ describe('Resolver', function() {
expect(processedCode).toEqual([ expect(processedCode).toEqual([
'(function(global) {', '(function(global) {',
'global.fetch = () => 1;', 'global.fetch = () => 1;',
"\n})(typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : this);", '\n})' +
"(typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : this);",
].join('')); ].join(''));
}); });
}); });

Просмотреть файл

@ -76,7 +76,8 @@ class Resolver {
}, },
platforms: new Set(opts.platforms), platforms: new Set(opts.platforms),
preferNativePlatform: true, preferNativePlatform: true,
providesModuleNodeModules: opts.providesModuleNodeModules || defaults.providesModuleNodeModules, providesModuleNodeModules:
opts.providesModuleNodeModules || defaults.providesModuleNodeModules,
reporter: opts.reporter, reporter: opts.reporter,
resetCache: opts.resetCache, resetCache: opts.resetCache,
roots: opts.projectRoots, roots: opts.projectRoots,
@ -261,7 +262,7 @@ function defineModuleCode(moduleName, code, verboseName = '', dev = true) {
].join(''); ].join('');
} }
function definePolyfillCode(code,) { function definePolyfillCode(code) {
return [ return [
'(function(global) {', '(function(global) {',
code, code,

Просмотреть файл

@ -27,6 +27,7 @@ if (Number.MIN_SAFE_INTEGER === undefined) {
}); });
} }
if (!Number.isNaN) { if (!Number.isNaN) {
// eslint-disable-next-line max-len
// https://github.com/dherman/tc39-codex-wiki/blob/master/data/es6/number/index.md#polyfill-for-numberisnan // https://github.com/dherman/tc39-codex-wiki/blob/master/data/es6/number/index.md#polyfill-for-numberisnan
const globalIsNaN = global.isNaN; const globalIsNaN = global.isNaN;
Object.defineProperty(Number, 'isNaN', { Object.defineProperty(Number, 'isNaN', {

Просмотреть файл

@ -52,6 +52,7 @@ const ErrorUtils = {
} finally { } finally {
_inGuard--; _inGuard--;
} }
return null;
}, },
applyWithGuardIfNeeded(fun, context, args) { applyWithGuardIfNeeded(fun, context, args) {
if (ErrorUtils.inGuard()) { if (ErrorUtils.inGuard()) {
@ -59,6 +60,7 @@ const ErrorUtils = {
} else { } else {
ErrorUtils.applyWithGuard(fun, context, args); ErrorUtils.applyWithGuard(fun, context, args);
} }
return null;
}, },
inGuard() { inGuard() {
return _inGuard; return _inGuard;

Просмотреть файл

@ -43,7 +43,8 @@ const {
} = require('../Logger'); } = require('../Logger');
function debounceAndBatch(fn, delay) { function debounceAndBatch(fn, delay) {
let timeout, args = []; let args = [];
let timeout;
return value => { return value => {
args.push(value); args.push(value);
clearTimeout(timeout); clearTimeout(timeout);
@ -957,7 +958,8 @@ class Server {
'entryModuleOnly', 'entryModuleOnly',
false, false,
), ),
generateSourceMaps: minify || !dev || this._getBoolOptionFromQuery(urlObj.query, 'babelSourcemap', false), generateSourceMaps:
minify || !dev || this._getBoolOptionFromQuery(urlObj.query, 'babelSourcemap', false),
assetPlugins, assetPlugins,
}; };
} }

Просмотреть файл

@ -17,11 +17,11 @@ import type {MixedSourceMap} from './SourceMap';
function relativizeSourceMapInternal(sourceMap: any, sourcesRoot: string) { function relativizeSourceMapInternal(sourceMap: any, sourcesRoot: string) {
if (sourceMap.sections) { if (sourceMap.sections) {
for (var i = 0; i < sourceMap.sections.length; i++) { for (let i = 0; i < sourceMap.sections.length; i++) {
relativizeSourceMapInternal(sourceMap.sections[i].map, sourcesRoot); relativizeSourceMapInternal(sourceMap.sections[i].map, sourcesRoot);
} }
} else { } else {
for (var i = 0; i < sourceMap.sources.length; i++) { for (let i = 0; i < sourceMap.sources.length; i++) {
sourceMap.sources[i] = path.relative(sourcesRoot, sourceMap.sources[i]); sourceMap.sources[i] = path.relative(sourcesRoot, sourceMap.sources[i]);
} }
} }

Просмотреть файл

@ -87,6 +87,7 @@ class HasteMap extends EventEmitter {
return this._processHasteModule(absPath, invalidated); return this._processHasteModule(absPath, invalidated);
} }
} }
return null;
}); });
} }

Просмотреть файл

@ -37,7 +37,7 @@ fs.realpath.mockImplementation((filepath, callback) => {
if (node && typeof node === 'object' && node.SYMLINK != null) { if (node && typeof node === 'object' && node.SYMLINK != null) {
return callback(null, node.SYMLINK); return callback(null, node.SYMLINK);
} }
callback(null, filepath); return callback(null, filepath);
}); });
fs.readdirSync.mockImplementation(filepath => Object.keys(getToNode(filepath))); fs.readdirSync.mockImplementation(filepath => Object.keys(getToNode(filepath)));
@ -58,7 +58,7 @@ fs.readdir.mockImplementation((filepath, callback) => {
return callback(new Error(filepath + ' is not a directory.')); return callback(new Error(filepath + ' is not a directory.'));
} }
callback(null, Object.keys(node)); return callback(null, Object.keys(node));
}); });
fs.readFile.mockImplementation(function(filepath, encoding, callback) { fs.readFile.mockImplementation(function(filepath, encoding, callback) {
@ -76,9 +76,9 @@ fs.readFile.mockImplementation(function(filepath, encoding, callback) {
callback(new Error('Error readFile a dir: ' + filepath)); callback(new Error('Error readFile a dir: ' + filepath));
} }
if (node == null) { if (node == null) {
callback(Error('No such file: ' + filepath)); return callback(Error('No such file: ' + filepath));
} else { } else {
callback(null, node); return callback(null, node);
} }
} catch (e) { } catch (e) {
return callback(e); return callback(e);

Просмотреть файл

@ -748,7 +748,7 @@ describe('DependencyGraph', function() {
}); });
}); });
it('should work with packages', function() { it('should work with packages with a trailing slash', function() {
var root = '/root'; var root = '/root';
setMockFileSystem({ setMockFileSystem({
'root': { 'root': {

Просмотреть файл

@ -130,7 +130,9 @@ class DependencyGraph extends EventEmitter {
moduleOptions: this._opts.moduleOptions, moduleOptions: this._opts.moduleOptions,
reporter: this._opts.reporter, reporter: this._opts.reporter,
getClosestPackage: filePath => { getClosestPackage: filePath => {
let {dir, root} = path.parse(filePath); const parsedPath = path.parse(filePath);
const root = parsedPath.root;
let dir = parsedPath.dir;
do { do {
const candidate = path.join(dir, 'package.json'); const candidate = path.join(dir, 'package.json');
if (this._hasteFS.exists(candidate)) { if (this._hasteFS.exists(candidate)) {

Просмотреть файл

@ -35,7 +35,7 @@ const getBabelRC = (function() {
return babelRC; return babelRC;
} }
babelRC = { plugins: [] }; // empty babelrc babelRC = {plugins: []}; // empty babelrc
// Let's look for the .babelrc in the first project root. // Let's look for the .babelrc in the first project root.
// In the future let's look into adding a command line option to specify // In the future let's look into adding a command line option to specify
@ -54,7 +54,7 @@ const getBabelRC = (function() {
); );
// Require the babel-preset's listed in the default babel config // Require the babel-preset's listed in the default babel config
babelRC.presets = babelRC.presets.map((preset) => require('babel-preset-' + preset)); babelRC.presets = babelRC.presets.map(preset => require('babel-preset-' + preset));
babelRC.plugins = resolvePlugins(babelRC.plugins); babelRC.plugins = resolvePlugins(babelRC.plugins);
} else { } else {
// if we find a .babelrc file we tell babel to use it // if we find a .babelrc file we tell babel to use it