mirror of https://github.com/status-im/metro.git
Convert entryPoint paths to absolute in the Server
Reviewed By: davidaurelio Differential Revision: D7196392 fbshipit-source-id: a1927d66fd67e35382a5ac418896dc5a902a5a5c
This commit is contained in:
parent
ab25e7c475
commit
40cce3b120
|
@ -11,6 +11,8 @@
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
const os = require('os');
|
const os = require('os');
|
||||||
|
const path = require('path');
|
||||||
|
const process = require('process');
|
||||||
|
|
||||||
const {EventEmitter} = require('events');
|
const {EventEmitter} = require('events');
|
||||||
|
|
||||||
|
@ -33,6 +35,7 @@ export type LogEntry = {
|
||||||
action_name?: string,
|
action_name?: string,
|
||||||
action_phase?: string,
|
action_phase?: string,
|
||||||
duration_ms?: number,
|
duration_ms?: number,
|
||||||
|
entry_point?: string,
|
||||||
log_entry_label: string,
|
log_entry_label: string,
|
||||||
log_session?: string,
|
log_session?: string,
|
||||||
start_timestamp?: [number, number],
|
start_timestamp?: [number, number],
|
||||||
|
@ -46,7 +49,13 @@ function on(event: string, handler: (logEntry: LogEntry) => void): void {
|
||||||
}
|
}
|
||||||
|
|
||||||
function createEntry(data: LogEntry | string): LogEntry {
|
function createEntry(data: LogEntry | string): LogEntry {
|
||||||
const logEntry = typeof data === 'string' ? {log_entry_label: data} : data;
|
const logEntry: LogEntry =
|
||||||
|
typeof data === 'string' ? {log_entry_label: data} : data;
|
||||||
|
|
||||||
|
const entryPoint = logEntry.entry_point;
|
||||||
|
if (entryPoint) {
|
||||||
|
logEntry.entry_point = path.relative(process.cwd(), entryPoint);
|
||||||
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
...logEntry,
|
...logEntry,
|
||||||
|
|
|
@ -73,13 +73,9 @@ class DeltaCalculator extends EventEmitter {
|
||||||
this._options = options;
|
this._options = options;
|
||||||
this._dependencyGraph = dependencyGraph;
|
this._dependencyGraph = dependencyGraph;
|
||||||
|
|
||||||
const entryPoints = this._options.entryPoints.map(entryPoint =>
|
|
||||||
this._dependencyGraph.getAbsolutePath(entryPoint),
|
|
||||||
);
|
|
||||||
|
|
||||||
this._graph = {
|
this._graph = {
|
||||||
dependencies: new Map(),
|
dependencies: new Map(),
|
||||||
entryPoints,
|
entryPoints: this._options.entryPoints,
|
||||||
};
|
};
|
||||||
|
|
||||||
this._dependencyGraph
|
this._dependencyGraph
|
||||||
|
|
|
@ -356,19 +356,12 @@ class DeltaTransformer extends EventEmitter {
|
||||||
}
|
}
|
||||||
|
|
||||||
async _getAppend(dependencyEdges: DependencyEdges): Promise<DeltaEntries> {
|
async _getAppend(dependencyEdges: DependencyEdges): Promise<DeltaEntries> {
|
||||||
// Get the absolute path of the entry file, in order to be able to get the
|
|
||||||
// actual correspondant module (and its moduleId) to be able to add the
|
|
||||||
// correct require(); call at the very end of the bundle.
|
|
||||||
const entryPointModulePath = this._dependencyGraph.getAbsolutePath(
|
|
||||||
this._bundleOptions.entryFile,
|
|
||||||
);
|
|
||||||
|
|
||||||
// First, get the modules correspondant to all the module names defined in
|
// First, get the modules correspondant to all the module names defined in
|
||||||
// the `runBeforeMainModule` config variable. Then, append the entry point
|
// the `runBeforeMainModule` config variable. Then, append the entry point
|
||||||
// module so the last thing that gets required is the entry point.
|
// module so the last thing that gets required is the entry point.
|
||||||
const append = new Map(
|
const append = new Map(
|
||||||
this._bundleOptions.runBeforeMainModule
|
this._bundleOptions.runBeforeMainModule
|
||||||
.concat(entryPointModulePath)
|
.concat(this._bundleOptions.entryFile)
|
||||||
.filter(path => dependencyEdges.has(path))
|
.filter(path => dependencyEdges.has(path))
|
||||||
.map(this._getModuleId)
|
.map(this._getModuleId)
|
||||||
.map(moduleId => {
|
.map(moduleId => {
|
||||||
|
|
|
@ -9,6 +9,8 @@
|
||||||
*/
|
*/
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
|
jest.mock('../../lib/getAbsolutePath');
|
||||||
|
|
||||||
const HmrServer = require('..');
|
const HmrServer = require('..');
|
||||||
|
|
||||||
const {EventEmitter} = require('events');
|
const {EventEmitter} = require('events');
|
||||||
|
@ -41,6 +43,9 @@ describe('HmrServer', () => {
|
||||||
update: jest.fn(),
|
update: jest.fn(),
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
|
getProjectRoots() {
|
||||||
|
return ['/root'];
|
||||||
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
hmrServer = new HmrServer(serverMock);
|
hmrServer = new HmrServer(serverMock);
|
||||||
|
@ -57,7 +62,7 @@ describe('HmrServer', () => {
|
||||||
expect.objectContaining({
|
expect.objectContaining({
|
||||||
deltaBundleId: null,
|
deltaBundleId: null,
|
||||||
dev: true,
|
dev: true,
|
||||||
entryFile: 'EntryPoint.js',
|
entryFile: '/root/EntryPoint.js',
|
||||||
minify: false,
|
minify: false,
|
||||||
platform: 'ios',
|
platform: 'ios',
|
||||||
}),
|
}),
|
||||||
|
|
|
@ -12,6 +12,7 @@
|
||||||
|
|
||||||
const addParamsToDefineCall = require('../lib/addParamsToDefineCall');
|
const addParamsToDefineCall = require('../lib/addParamsToDefineCall');
|
||||||
const formatBundlingError = require('../lib/formatBundlingError');
|
const formatBundlingError = require('../lib/formatBundlingError');
|
||||||
|
const getAbsolutePath = require('../lib/getAbsolutePath');
|
||||||
const getBundlingOptionsForHmr = require('./getBundlingOptionsForHmr');
|
const getBundlingOptionsForHmr = require('./getBundlingOptionsForHmr');
|
||||||
const nullthrows = require('fbjs/lib/nullthrows');
|
const nullthrows = require('fbjs/lib/nullthrows');
|
||||||
const parseCustomTransformOptions = require('../lib/parseCustomTransformOptions');
|
const parseCustomTransformOptions = require('../lib/parseCustomTransformOptions');
|
||||||
|
@ -66,7 +67,11 @@ class HmrServer<TClient: Client> {
|
||||||
const deltaBundler = this._packagerServer.getDeltaBundler();
|
const deltaBundler = this._packagerServer.getDeltaBundler();
|
||||||
const deltaTransformer = await deltaBundler.getDeltaTransformer(
|
const deltaTransformer = await deltaBundler.getDeltaTransformer(
|
||||||
clientUrl,
|
clientUrl,
|
||||||
getBundlingOptionsForHmr(bundleEntry, platform, customTransformOptions),
|
getBundlingOptionsForHmr(
|
||||||
|
getAbsolutePath(bundleEntry, this._packagerServer.getProjectRoots()),
|
||||||
|
platform,
|
||||||
|
customTransformOptions,
|
||||||
|
),
|
||||||
);
|
);
|
||||||
|
|
||||||
// Trigger an initial build to start up the DeltaTransformer.
|
// Trigger an initial build to start up the DeltaTransformer.
|
||||||
|
|
|
@ -21,6 +21,7 @@ jest
|
||||||
.mock('../../Assets')
|
.mock('../../Assets')
|
||||||
.mock('../../node-haste/DependencyGraph')
|
.mock('../../node-haste/DependencyGraph')
|
||||||
.mock('metro-core/src/Logger')
|
.mock('metro-core/src/Logger')
|
||||||
|
.mock('../../lib/getAbsolutePath')
|
||||||
.mock('../../lib/GlobalTransformCache')
|
.mock('../../lib/GlobalTransformCache')
|
||||||
.mock('../../DeltaBundler/Serializers/Serializers');
|
.mock('../../DeltaBundler/Serializers/Serializers');
|
||||||
|
|
||||||
|
@ -47,7 +48,7 @@ describe('processRequest', () => {
|
||||||
let server;
|
let server;
|
||||||
|
|
||||||
const options = {
|
const options = {
|
||||||
projectRoots: ['root'],
|
projectRoots: ['/root'],
|
||||||
blacklistRE: null,
|
blacklistRE: null,
|
||||||
cacheVersion: null,
|
cacheVersion: null,
|
||||||
polyfillModuleNames: null,
|
polyfillModuleNames: null,
|
||||||
|
@ -183,7 +184,7 @@ describe('processRequest', () => {
|
||||||
bundleType: 'bundle',
|
bundleType: 'bundle',
|
||||||
customTransformOptions: {},
|
customTransformOptions: {},
|
||||||
dev: true,
|
dev: true,
|
||||||
entryFile: 'index.ios.js',
|
entryFile: '/root/index.ios.js',
|
||||||
entryModuleOnly: false,
|
entryModuleOnly: false,
|
||||||
excludeSource: false,
|
excludeSource: false,
|
||||||
hot: true,
|
hot: true,
|
||||||
|
@ -214,7 +215,7 @@ describe('processRequest', () => {
|
||||||
bundleType: 'bundle',
|
bundleType: 'bundle',
|
||||||
customTransformOptions: {},
|
customTransformOptions: {},
|
||||||
dev: true,
|
dev: true,
|
||||||
entryFile: 'index.js',
|
entryFile: '/root/index.js',
|
||||||
entryModuleOnly: false,
|
entryModuleOnly: false,
|
||||||
excludeSource: false,
|
excludeSource: false,
|
||||||
hot: true,
|
hot: true,
|
||||||
|
@ -245,7 +246,7 @@ describe('processRequest', () => {
|
||||||
bundleType: 'bundle',
|
bundleType: 'bundle',
|
||||||
customTransformOptions: {},
|
customTransformOptions: {},
|
||||||
dev: true,
|
dev: true,
|
||||||
entryFile: 'index.js',
|
entryFile: '/root/index.js',
|
||||||
entryModuleOnly: false,
|
entryModuleOnly: false,
|
||||||
excludeSource: false,
|
excludeSource: false,
|
||||||
hot: true,
|
hot: true,
|
||||||
|
@ -391,7 +392,7 @@ describe('processRequest', () => {
|
||||||
|
|
||||||
server.processRequest(req, res);
|
server.processRequest(req, res);
|
||||||
res.end.mockImplementation(value => {
|
res.end.mockImplementation(value => {
|
||||||
expect(getAsset).toBeCalledWith('imgs/a.png', ['root'], 'ios');
|
expect(getAsset).toBeCalledWith('imgs/a.png', ['/root'], 'ios');
|
||||||
expect(value).toBe('i am image');
|
expect(value).toBe('i am image');
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
|
@ -409,7 +410,7 @@ describe('processRequest', () => {
|
||||||
|
|
||||||
server.processRequest(req, res);
|
server.processRequest(req, res);
|
||||||
res.end.mockImplementation(value => {
|
res.end.mockImplementation(value => {
|
||||||
expect(getAsset).toBeCalledWith('imgs/a.png', ['root'], 'ios');
|
expect(getAsset).toBeCalledWith('imgs/a.png', ['/root'], 'ios');
|
||||||
expect(value).toBe(mockData.slice(0, 4));
|
expect(value).toBe(mockData.slice(0, 4));
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
|
@ -427,7 +428,7 @@ describe('processRequest', () => {
|
||||||
res.end.mockImplementation(value => {
|
res.end.mockImplementation(value => {
|
||||||
expect(getAsset).toBeCalledWith(
|
expect(getAsset).toBeCalledWith(
|
||||||
'imgs/\u{4E3B}\u{9875}/logo.png',
|
'imgs/\u{4E3B}\u{9875}/logo.png',
|
||||||
['root'],
|
['/root'],
|
||||||
undefined,
|
undefined,
|
||||||
);
|
);
|
||||||
expect(value).toBe('i am image');
|
expect(value).toBe('i am image');
|
||||||
|
@ -450,7 +451,7 @@ describe('processRequest', () => {
|
||||||
assetPlugins: [],
|
assetPlugins: [],
|
||||||
customTransformOptions: {},
|
customTransformOptions: {},
|
||||||
dev: true,
|
dev: true,
|
||||||
entryFile: 'foo file',
|
entryFile: '/root/foo file',
|
||||||
entryModuleOnly: false,
|
entryModuleOnly: false,
|
||||||
excludeSource: false,
|
excludeSource: false,
|
||||||
hot: false,
|
hot: false,
|
||||||
|
|
|
@ -1,3 +1,3 @@
|
||||||
// Jest Snapshot v1, https://goo.gl/fbAQLP
|
// Jest Snapshot v1, https://goo.gl/fbAQLP
|
||||||
|
|
||||||
exports[`processRequest Generate delta bundle endpoint should send the correct deltaBundlerId to the bundler 1`] = `"{\\"sourceMapUrl\\":null,\\"bundleType\\":\\"delta\\",\\"customTransformOptions\\":{},\\"entryFile\\":\\"index.js\\",\\"deltaBundleId\\":null,\\"dev\\":true,\\"minify\\":false,\\"excludeSource\\":null,\\"hot\\":true,\\"runBeforeMainModule\\":[\\"InitializeCore\\"],\\"runModule\\":true,\\"inlineSourceMap\\":false,\\"isolateModuleIDs\\":false,\\"platform\\":\\"ios\\",\\"resolutionResponse\\":null,\\"entryModuleOnly\\":false,\\"assetPlugins\\":[],\\"onProgress\\":null,\\"unbundle\\":false}"`;
|
exports[`processRequest Generate delta bundle endpoint should send the correct deltaBundlerId to the bundler 1`] = `"{\\"sourceMapUrl\\":null,\\"bundleType\\":\\"delta\\",\\"customTransformOptions\\":{},\\"entryFile\\":\\"/root/index.js\\",\\"deltaBundleId\\":null,\\"dev\\":true,\\"minify\\":false,\\"excludeSource\\":null,\\"hot\\":true,\\"runBeforeMainModule\\":[\\"InitializeCore\\"],\\"runModule\\":true,\\"inlineSourceMap\\":false,\\"isolateModuleIDs\\":false,\\"platform\\":\\"ios\\",\\"resolutionResponse\\":null,\\"entryModuleOnly\\":false,\\"assetPlugins\\":[],\\"onProgress\\":null,\\"unbundle\\":false}"`;
|
||||||
|
|
|
@ -17,6 +17,7 @@ const Serializers = require('../DeltaBundler/Serializers/Serializers');
|
||||||
const debug = require('debug')('Metro:Server');
|
const debug = require('debug')('Metro:Server');
|
||||||
const defaults = require('../defaults');
|
const defaults = require('../defaults');
|
||||||
const formatBundlingError = require('../lib/formatBundlingError');
|
const formatBundlingError = require('../lib/formatBundlingError');
|
||||||
|
const getAbsolutePath = require('../lib/getAbsolutePath');
|
||||||
const getMaxWorkers = require('../lib/getMaxWorkers');
|
const getMaxWorkers = require('../lib/getMaxWorkers');
|
||||||
const getOrderedDependencyPaths = require('../lib/getOrderedDependencyPaths');
|
const getOrderedDependencyPaths = require('../lib/getOrderedDependencyPaths');
|
||||||
const mime = require('mime-types');
|
const mime = require('mime-types');
|
||||||
|
@ -234,6 +235,7 @@ class Server {
|
||||||
runBeforeMainModule: this._opts.getModulesRunBeforeMainModule(
|
runBeforeMainModule: this._opts.getModulesRunBeforeMainModule(
|
||||||
options.entryFile,
|
options.entryFile,
|
||||||
),
|
),
|
||||||
|
entryFile: getAbsolutePath(options.entryFile, this._opts.projectRoots),
|
||||||
};
|
};
|
||||||
|
|
||||||
const fullBundle = await Serializers.fullBundle(
|
const fullBundle = await Serializers.fullBundle(
|
||||||
|
@ -255,7 +257,10 @@ class Server {
|
||||||
async getRamBundleInfo(options: BundleOptions): Promise<RamBundleInfo> {
|
async getRamBundleInfo(options: BundleOptions): Promise<RamBundleInfo> {
|
||||||
return await Serializers.getRamBundleInfo(
|
return await Serializers.getRamBundleInfo(
|
||||||
this._deltaBundler,
|
this._deltaBundler,
|
||||||
options,
|
{
|
||||||
|
...options,
|
||||||
|
entryFile: getAbsolutePath(options.entryFile, this._opts.projectRoots),
|
||||||
|
},
|
||||||
this._opts.getTransformOptions,
|
this._opts.getTransformOptions,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -263,7 +268,10 @@ class Server {
|
||||||
async getAssets(options: BundleOptions): Promise<$ReadOnlyArray<AssetData>> {
|
async getAssets(options: BundleOptions): Promise<$ReadOnlyArray<AssetData>> {
|
||||||
return await Serializers.getAssets(
|
return await Serializers.getAssets(
|
||||||
this._deltaBundler,
|
this._deltaBundler,
|
||||||
options,
|
{
|
||||||
|
...options,
|
||||||
|
entryFile: getAbsolutePath(options.entryFile, this._opts.projectRoots),
|
||||||
|
},
|
||||||
this._opts.projectRoots,
|
this._opts.projectRoots,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -277,6 +285,7 @@ class Server {
|
||||||
const bundleOptions = {
|
const bundleOptions = {
|
||||||
...Server.DEFAULT_BUNDLE_OPTIONS,
|
...Server.DEFAULT_BUNDLE_OPTIONS,
|
||||||
...options,
|
...options,
|
||||||
|
entryFile: getAbsolutePath(options.entryFile, this._opts.projectRoots),
|
||||||
bundleType: 'delta',
|
bundleType: 'delta',
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -813,6 +822,11 @@ class Server {
|
||||||
})
|
})
|
||||||
.join('.') + '.js';
|
.join('.') + '.js';
|
||||||
|
|
||||||
|
const absoluteEntryFile = getAbsolutePath(
|
||||||
|
entryFile,
|
||||||
|
this._opts.projectRoots,
|
||||||
|
);
|
||||||
|
|
||||||
// try to get the platform from the url
|
// try to get the platform from the url
|
||||||
const platform =
|
const platform =
|
||||||
urlQuery.platform ||
|
urlQuery.platform ||
|
||||||
|
@ -847,7 +861,7 @@ class Server {
|
||||||
}),
|
}),
|
||||||
bundleType: isMap ? 'map' : deltaBundleId ? 'delta' : 'bundle',
|
bundleType: isMap ? 'map' : deltaBundleId ? 'delta' : 'bundle',
|
||||||
customTransformOptions,
|
customTransformOptions,
|
||||||
entryFile,
|
entryFile: absoluteEntryFile,
|
||||||
deltaBundleId,
|
deltaBundleId,
|
||||||
dev,
|
dev,
|
||||||
minify,
|
minify,
|
||||||
|
@ -891,6 +905,10 @@ class Server {
|
||||||
return this._reporter;
|
return this._reporter;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
getProjectRoots(): $ReadOnlyArray<string> {
|
||||||
|
return this._opts.projectRoots;
|
||||||
|
}
|
||||||
|
|
||||||
static DEFAULT_BUNDLE_OPTIONS = {
|
static DEFAULT_BUNDLE_OPTIONS = {
|
||||||
assetPlugins: [],
|
assetPlugins: [],
|
||||||
customTransformOptions: Object.create(null),
|
customTransformOptions: Object.create(null),
|
||||||
|
|
|
@ -0,0 +1,16 @@
|
||||||
|
/**
|
||||||
|
* Copyright (c) 2015-present, Facebook, Inc.
|
||||||
|
*
|
||||||
|
* This source code is licensed under the MIT license found in the
|
||||||
|
* LICENSE file in the root directory of this source tree.
|
||||||
|
*
|
||||||
|
* @flow
|
||||||
|
* @format
|
||||||
|
*/
|
||||||
|
|
||||||
|
'use strict';
|
||||||
|
|
||||||
|
const path = require('path');
|
||||||
|
|
||||||
|
module.exports = (file: string, roots: $ReadOnlyArray<string>): string =>
|
||||||
|
path.resolve(roots[0], file);
|
|
@ -0,0 +1,57 @@
|
||||||
|
/**
|
||||||
|
* Copyright (c) 2013-present, Facebook, Inc.
|
||||||
|
*
|
||||||
|
* This source code is licensed under the MIT license found in the
|
||||||
|
* LICENSE file in the root directory of this source tree.
|
||||||
|
*
|
||||||
|
* @emails oncall+javascript_foundation
|
||||||
|
* @format
|
||||||
|
*/
|
||||||
|
|
||||||
|
'use strict';
|
||||||
|
|
||||||
|
jest.mock('fs', () => new (require('metro-memory-fs'))());
|
||||||
|
|
||||||
|
const fs = require('fs');
|
||||||
|
const getAbsolutePath = require('../getAbsolutePath');
|
||||||
|
const mkdirp = require('mkdirp');
|
||||||
|
|
||||||
|
beforeEach(() => {
|
||||||
|
fs.reset();
|
||||||
|
|
||||||
|
mkdirp.sync('/root/a');
|
||||||
|
mkdirp.sync('/root/b');
|
||||||
|
mkdirp.sync('/root/a/d');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work for a simple case with a single project root', () => {
|
||||||
|
fs.writeFileSync('/root/a/entryPoint.js', '');
|
||||||
|
|
||||||
|
expect(getAbsolutePath('entryPoint.js', ['/root/a'])).toEqual(
|
||||||
|
'/root/a/entryPoint.js',
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should resolve from the first defined project root', () => {
|
||||||
|
fs.writeFileSync('/root/a/entryPoint.js', '');
|
||||||
|
fs.writeFileSync('/root/b/entryPoint.js', '');
|
||||||
|
|
||||||
|
expect(getAbsolutePath('entryPoint.js', ['/root/a', '/root/c'])).toEqual(
|
||||||
|
'/root/a/entryPoint.js',
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should resolve from sub-folders', () => {
|
||||||
|
fs.writeFileSync('/root/a/d/entryPoint.js', '');
|
||||||
|
fs.writeFileSync('/root/b/entryPoint.js', '');
|
||||||
|
|
||||||
|
expect(getAbsolutePath('d/entryPoint.js', ['/root/a', '/root/d'])).toEqual(
|
||||||
|
'/root/a/d/entryPoint.js',
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should throw an error if not found', () => {
|
||||||
|
expect(() =>
|
||||||
|
getAbsolutePath('entryPoint.js', ['/root/a', '/root/d']),
|
||||||
|
).toThrow();
|
||||||
|
});
|
|
@ -0,0 +1,51 @@
|
||||||
|
/**
|
||||||
|
* Copyright (c) 2015-present, Facebook, Inc.
|
||||||
|
*
|
||||||
|
* This source code is licensed under the MIT license found in the
|
||||||
|
* LICENSE file in the root directory of this source tree.
|
||||||
|
*
|
||||||
|
* @flow
|
||||||
|
* @format
|
||||||
|
*/
|
||||||
|
|
||||||
|
'use strict';
|
||||||
|
|
||||||
|
const fs = require('fs');
|
||||||
|
const isAbsolutePath = require('absolute-path');
|
||||||
|
const path = require('path');
|
||||||
|
|
||||||
|
function getAbsolutePath(
|
||||||
|
filePath: string,
|
||||||
|
projectRoots: $ReadOnlyArray<string>,
|
||||||
|
): string {
|
||||||
|
if (isAbsolutePath(filePath)) {
|
||||||
|
return path.resolve(filePath);
|
||||||
|
}
|
||||||
|
|
||||||
|
for (let i = 0; i < projectRoots.length; i++) {
|
||||||
|
const potentialAbsPath = path.resolve(projectRoots[i], filePath);
|
||||||
|
if (fs.existsSync(potentialAbsPath)) {
|
||||||
|
return potentialAbsPath;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
throw new NotFoundError(filePath, projectRoots);
|
||||||
|
}
|
||||||
|
|
||||||
|
class NotFoundError extends Error {
|
||||||
|
status: number;
|
||||||
|
type: string;
|
||||||
|
|
||||||
|
constructor(relativePath: string, projectRoots: $ReadOnlyArray<string>) {
|
||||||
|
super(
|
||||||
|
`File not found: ${relativePath} in any of the project roots (${projectRoots.join(
|
||||||
|
', ',
|
||||||
|
)})`,
|
||||||
|
);
|
||||||
|
|
||||||
|
this.type = 'NotFoundError';
|
||||||
|
this.status = 404;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
module.exports = getAbsolutePath;
|
|
@ -19,11 +19,9 @@ const ModuleCache = require('./ModuleCache');
|
||||||
const ResolutionRequest = require('./DependencyGraph/ResolutionRequest');
|
const ResolutionRequest = require('./DependencyGraph/ResolutionRequest');
|
||||||
|
|
||||||
const fs = require('fs');
|
const fs = require('fs');
|
||||||
const isAbsolutePath = require('absolute-path');
|
|
||||||
const parsePlatformFilePath = require('./lib/parsePlatformFilePath');
|
const parsePlatformFilePath = require('./lib/parsePlatformFilePath');
|
||||||
const path = require('path');
|
const path = require('path');
|
||||||
const toLocalPath = require('../node-haste/lib/toLocalPath');
|
const toLocalPath = require('../node-haste/lib/toLocalPath');
|
||||||
const util = require('util');
|
|
||||||
|
|
||||||
const {ModuleResolver} = require('./DependencyGraph/ModuleResolution');
|
const {ModuleResolver} = require('./DependencyGraph/ModuleResolution');
|
||||||
const {EventEmitter} = require('events');
|
const {EventEmitter} = require('events');
|
||||||
|
@ -288,52 +286,9 @@ class DependencyGraph extends EventEmitter {
|
||||||
return toLocalPath(this._opts.projectRoots, filePath);
|
return toLocalPath(this._opts.projectRoots, filePath);
|
||||||
}
|
}
|
||||||
|
|
||||||
getAbsolutePath(filePath: string) {
|
|
||||||
if (isAbsolutePath(filePath)) {
|
|
||||||
return path.resolve(filePath);
|
|
||||||
}
|
|
||||||
|
|
||||||
for (let i = 0; i < this._opts.projectRoots.length; i++) {
|
|
||||||
const root = this._opts.projectRoots[i];
|
|
||||||
const potentialAbsPath = path.join(root, filePath);
|
|
||||||
if (this._hasteFS.exists(potentialAbsPath)) {
|
|
||||||
return path.resolve(potentialAbsPath);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// If we failed to find a file, maybe this is just a Haste name so try that
|
|
||||||
// TODO: We should prefer Haste name resolution first ideally since it is faster
|
|
||||||
// TODO: Ideally, we should not do any `path.parse().name` here and just use the
|
|
||||||
// name, but in `metro/src/Server/index.js` we append `'.js'` to all names
|
|
||||||
// so until that changes, we have to do this.
|
|
||||||
const potentialPath = this._moduleMap.getModule(
|
|
||||||
path.parse(filePath).name,
|
|
||||||
null,
|
|
||||||
);
|
|
||||||
if (potentialPath) {
|
|
||||||
return potentialPath;
|
|
||||||
}
|
|
||||||
|
|
||||||
throw new NotFoundError(
|
|
||||||
'Cannot find entry file %s in any of the roots: %j',
|
|
||||||
filePath,
|
|
||||||
this._opts.projectRoots,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
createPolyfill(options: {file: string}) {
|
createPolyfill(options: {file: string}) {
|
||||||
return this._moduleCache.createPolyfill(options);
|
return this._moduleCache.createPolyfill(options);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function NotFoundError(...args) {
|
|
||||||
Error.call(this);
|
|
||||||
Error.captureStackTrace(this, this.constructor);
|
|
||||||
var msg = util.format.apply(util, args);
|
|
||||||
this.message = msg;
|
|
||||||
this.type = this.name = 'NotFoundError';
|
|
||||||
this.status = 404;
|
|
||||||
}
|
|
||||||
util.inherits(NotFoundError, Error);
|
|
||||||
|
|
||||||
module.exports = DependencyGraph;
|
module.exports = DependencyGraph;
|
||||||
|
|
Loading…
Reference in New Issue