mirror of https://github.com/status-im/metro.git
Remove old wrapping logic
Reviewed By: davidaurelio Differential Revision: D6439155 fbshipit-source-id: 3332b9c7952c90411d0c595f184f92aeffd4ddd2
This commit is contained in:
parent
8c43848a1e
commit
5c06a80fd7
|
@ -105,63 +105,4 @@ describe('Bundler', function() {
|
|||
});
|
||||
expect(b._opts.platforms).toEqual(['android', 'vr']);
|
||||
});
|
||||
|
||||
it('.generateAssetObjAndCode', async () => {
|
||||
const mockAsset = {
|
||||
__packager_asset: true,
|
||||
fileSystemLocation: '/root/img',
|
||||
scales: [1, 2, 3],
|
||||
files: [
|
||||
'/root/img/img.png',
|
||||
'/root/img/img@2x.png',
|
||||
'/root/img/img@3x.png',
|
||||
],
|
||||
hash: 'i am a hash',
|
||||
height: 100,
|
||||
httpServerLocation: '/assets/img',
|
||||
name: 'img',
|
||||
type: 'png',
|
||||
width: 50,
|
||||
};
|
||||
|
||||
assetServer.getAssetData.mockImplementation(() =>
|
||||
Promise.resolve(mockAsset),
|
||||
);
|
||||
|
||||
jest.mock(
|
||||
'mockPlugin1',
|
||||
() => {
|
||||
return asset => {
|
||||
asset.extraReverseHash = asset.hash
|
||||
.split('')
|
||||
.reverse()
|
||||
.join('');
|
||||
return asset;
|
||||
};
|
||||
},
|
||||
{virtual: true},
|
||||
);
|
||||
|
||||
jest.mock(
|
||||
'asyncMockPlugin2',
|
||||
() => {
|
||||
return asset => {
|
||||
expect(asset.extraReverseHash).toBeDefined();
|
||||
return new Promise(resolve => {
|
||||
asset.extraPixelCount = asset.width * asset.height;
|
||||
resolve(asset);
|
||||
});
|
||||
};
|
||||
},
|
||||
{virtual: true},
|
||||
);
|
||||
|
||||
expect(
|
||||
await bundler.generateAssetObjAndCode(
|
||||
{},
|
||||
['mockPlugin1', 'asyncMockPlugin2'],
|
||||
'ios',
|
||||
),
|
||||
).toMatchSnapshot();
|
||||
});
|
||||
});
|
||||
|
|
|
@ -1,38 +0,0 @@
|
|||
// Jest Snapshot v1, https://goo.gl/fbAQLP
|
||||
|
||||
exports[`Bundler .generateAssetObjAndCode 1`] = `
|
||||
Object {
|
||||
"asset": Object {
|
||||
"__packager_asset": true,
|
||||
"extraPixelCount": 5000,
|
||||
"extraReverseHash": "hsah a ma i",
|
||||
"fileSystemLocation": "/root/img",
|
||||
"files": Array [
|
||||
"/root/img/img.png",
|
||||
"/root/img/img@2x.png",
|
||||
"/root/img/img@3x.png",
|
||||
],
|
||||
"hash": "i am a hash",
|
||||
"height": 100,
|
||||
"httpServerLocation": "/assets/img",
|
||||
"name": "img",
|
||||
"scales": Array [
|
||||
1,
|
||||
2,
|
||||
3,
|
||||
],
|
||||
"type": "png",
|
||||
"width": 50,
|
||||
},
|
||||
"code": "module.exports=require(\\"/AssetRegistry.js\\").registerAsset({\\"__packager_asset\\":true,\\"scales\\":[1,2,3],\\"hash\\":\\"i am a hash\\",\\"height\\":100,\\"httpServerLocation\\":\\"/assets/img\\",\\"name\\":\\"img\\",\\"type\\":\\"png\\",\\"width\\":50,\\"extraReverseHash\\":\\"hsah a ma i\\",\\"extraPixelCount\\":5000});",
|
||||
"meta": Object {
|
||||
"dependencies": Array [
|
||||
"/AssetRegistry.js",
|
||||
],
|
||||
"dependencyOffsets": Array [
|
||||
23,
|
||||
],
|
||||
"preloaded": null,
|
||||
},
|
||||
}
|
||||
`;
|
|
@ -22,8 +22,6 @@ const path = require('path');
|
|||
const defaults = require('../defaults');
|
||||
const createModuleIdFactory = require('../lib/createModuleIdFactory');
|
||||
|
||||
const {generateAssetTransformResult} = require('./util');
|
||||
|
||||
const {sep: pathSeparator} = require('path');
|
||||
|
||||
const VERSION = require('../../package.json').version;
|
||||
|
@ -242,51 +240,6 @@ class Bundler {
|
|||
);
|
||||
}
|
||||
|
||||
async generateAssetObjAndCode(
|
||||
path: string,
|
||||
assetPlugins: Array<string>,
|
||||
platform: ?string = null,
|
||||
) {
|
||||
const assetData = await this._assetServer.getAssetData(path, platform);
|
||||
const asset = await this._applyAssetPlugins(assetPlugins, assetData);
|
||||
|
||||
const {
|
||||
code,
|
||||
dependencies,
|
||||
dependencyOffsets,
|
||||
} = generateAssetTransformResult(this._opts.assetRegistryPath, asset);
|
||||
|
||||
return {
|
||||
asset,
|
||||
code,
|
||||
meta: {dependencies, dependencyOffsets, preloaded: null},
|
||||
};
|
||||
}
|
||||
|
||||
_applyAssetPlugins(
|
||||
assetPlugins: Array<string>,
|
||||
asset: ExtendedAssetDescriptor,
|
||||
) {
|
||||
if (!assetPlugins.length) {
|
||||
return asset;
|
||||
}
|
||||
|
||||
const [currentAssetPlugin, ...remainingAssetPlugins] = assetPlugins;
|
||||
/* $FlowFixMe: dynamic requires prevent static typing :'( */
|
||||
const assetPluginFunction = require(currentAssetPlugin);
|
||||
const result = assetPluginFunction(asset);
|
||||
|
||||
// If the plugin was an async function, wait for it to fulfill before
|
||||
// applying the remaining plugins
|
||||
if (typeof result.then === 'function') {
|
||||
return result.then(resultAsset =>
|
||||
this._applyAssetPlugins(remainingAssetPlugins, resultAsset),
|
||||
);
|
||||
} else {
|
||||
return this._applyAssetPlugins(remainingAssetPlugins, result);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the transform options related to a specific entry file, by calling
|
||||
* the config parameter getTransformOptions().
|
||||
|
|
|
@ -160,23 +160,6 @@ function generateRemoteAssetCodeFileAst(
|
|||
);
|
||||
}
|
||||
|
||||
function generateAssetTransformResult(
|
||||
assetRegistryPath: string,
|
||||
assetDescriptor: ExtendedAssetDescriptor,
|
||||
): {|
|
||||
code: string,
|
||||
dependencies: Array<string>,
|
||||
dependencyOffsets: Array<number>,
|
||||
|} {
|
||||
const {code} = babelGenerate(
|
||||
generateAssetCodeFileAst(assetRegistryPath, assetDescriptor),
|
||||
{comments: false, compact: true},
|
||||
);
|
||||
const dependencies = [assetRegistryPath];
|
||||
const dependencyOffsets = [code.indexOf(assetRegistryPath) - 1];
|
||||
return {code, dependencies, dependencyOffsets};
|
||||
}
|
||||
|
||||
// Test extension against all types supported by image-size module.
|
||||
// If it's not one of these, we won't treat it as an image.
|
||||
function isAssetTypeAnImage(type: string): boolean {
|
||||
|
@ -272,7 +255,6 @@ class ArrayMap<K, V> extends Map<K, Array<V>> {
|
|||
module.exports = {
|
||||
createRamBundleGroups,
|
||||
generateAssetCodeFileAst,
|
||||
generateAssetTransformResult,
|
||||
generateRemoteAssetCodeFileAst,
|
||||
isAssetTypeAnImage,
|
||||
};
|
||||
|
|
|
@ -505,38 +505,6 @@ class DeltaTransformer extends EventEmitter {
|
|||
return addParamsToDefineCall(code, ...params);
|
||||
}
|
||||
|
||||
/**
|
||||
* Temporary function to wrap an asset. This logic will go away once we
|
||||
* generate the needed JS code for assets in the transformer.
|
||||
*/
|
||||
async _wrapAsset({
|
||||
code,
|
||||
dependencyPairs,
|
||||
name,
|
||||
path,
|
||||
}: {
|
||||
code: string,
|
||||
dependencyPairs: Map<string, string>,
|
||||
name: string,
|
||||
path: string,
|
||||
}): Promise<string> {
|
||||
const asset = await this._bundler.generateAssetObjAndCode(
|
||||
path,
|
||||
this._bundleOptions.assetPlugins,
|
||||
this._bundleOptions.platform,
|
||||
);
|
||||
|
||||
return await this._resolver.wrapModule({
|
||||
path,
|
||||
getModuleId: this._getModuleId,
|
||||
dependencyPairs,
|
||||
dependencyOffsets: asset.meta.dependencyOffsets,
|
||||
name,
|
||||
code: asset.code,
|
||||
dev: this._bundleOptions.dev,
|
||||
});
|
||||
}
|
||||
|
||||
_getModuleType(module: Module): DeltaEntryType {
|
||||
if (module.isAsset()) {
|
||||
return 'asset';
|
||||
|
|
|
@ -19,7 +19,6 @@ jest.mock('path');
|
|||
const DependencyGraph = jest.fn();
|
||||
jest.setMock('../../node-haste/DependencyGraph', DependencyGraph);
|
||||
let Module;
|
||||
let Polyfill;
|
||||
|
||||
describe('Resolver', function() {
|
||||
let Resolver, path;
|
||||
|
@ -28,21 +27,16 @@ describe('Resolver', function() {
|
|||
Resolver = require('../');
|
||||
path = require('path');
|
||||
DependencyGraph.mockClear();
|
||||
|
||||
Module = jest.fn(function() {
|
||||
this.getName = jest.fn();
|
||||
this.getDependencies = jest.fn();
|
||||
this.isPolyfill = jest.fn().mockReturnValue(false);
|
||||
this.isJSON = jest.fn().mockReturnValue(false);
|
||||
});
|
||||
Polyfill = jest.fn(function() {
|
||||
var polyfill = new Module();
|
||||
polyfill.isPolyfill.mockReturnValue(true);
|
||||
return polyfill;
|
||||
});
|
||||
|
||||
DependencyGraph.load = jest
|
||||
.fn()
|
||||
.mockImplementation(opts => Promise.resolve(new DependencyGraph(opts)));
|
||||
|
||||
DependencyGraph.prototype.createPolyfill = jest.fn();
|
||||
DependencyGraph.prototype.getDependencies = jest.fn();
|
||||
|
||||
|
@ -52,237 +46,53 @@ describe('Resolver', function() {
|
|||
DependencyGraph.prototype.load = jest.fn(() => Promise.resolve());
|
||||
});
|
||||
|
||||
class ResolutionResponseMock {
|
||||
constructor({dependencies, mainModuleId}) {
|
||||
this.dependencies = dependencies;
|
||||
this.mainModuleId = mainModuleId;
|
||||
this.getModuleId = createGetModuleId();
|
||||
}
|
||||
|
||||
prependDependency(dependency) {
|
||||
this.dependencies.unshift(dependency);
|
||||
}
|
||||
|
||||
finalize() {
|
||||
return Promise.resolve(this);
|
||||
}
|
||||
|
||||
getResolvedDependencyPairs() {
|
||||
return [];
|
||||
}
|
||||
}
|
||||
|
||||
function createModule(id, dependencies) {
|
||||
var module = new Module({});
|
||||
module.path = id;
|
||||
module.getName.mockImplementation(() => Promise.resolve(id));
|
||||
module.getDependencies.mockImplementation(() =>
|
||||
Promise.resolve(dependencies),
|
||||
);
|
||||
|
||||
return module;
|
||||
}
|
||||
|
||||
function createJsonModule(id) {
|
||||
const module = createModule(id, []);
|
||||
module.isJSON.mockReturnValue(true);
|
||||
return module;
|
||||
}
|
||||
describe('minification:', () => {
|
||||
const code = 'arbitrary(code)';
|
||||
const id = 'arbitrary.js';
|
||||
let depResolver, minifyCode, module, sourceMap;
|
||||
|
||||
function createPolyfill(id, dependencies) {
|
||||
var polyfill = new Polyfill({});
|
||||
polyfill.getName = jest.fn(() => Promise.resolve(id));
|
||||
polyfill.getDependencies = jest.fn(() => Promise.resolve(dependencies));
|
||||
return polyfill;
|
||||
}
|
||||
|
||||
describe('wrapModule', function() {
|
||||
let depResolver;
|
||||
beforeEach(() => {
|
||||
minifyCode = jest.fn((filename, code, map) =>
|
||||
Promise.resolve({code, map}),
|
||||
);
|
||||
module = createModule(id);
|
||||
module.path = '/arbitrary/path.js';
|
||||
|
||||
sourceMap = [];
|
||||
return Resolver.load({
|
||||
projectRoot: '/root',
|
||||
minifyCode,
|
||||
postMinifyProcess: e => e,
|
||||
}).then(r => {
|
||||
depResolver = r;
|
||||
});
|
||||
});
|
||||
|
||||
it('should resolve modules', function() {
|
||||
expect.assertions(1);
|
||||
|
||||
var code = [
|
||||
// require
|
||||
'require("x")',
|
||||
'require("y");require(\'abc\');',
|
||||
"require( 'z' )",
|
||||
'require( "a")',
|
||||
'require("b" )',
|
||||
].join('\n');
|
||||
/*eslint-disable */
|
||||
|
||||
function* findDependencyOffsets() {
|
||||
const re = /(['"']).*?\1/g;
|
||||
let match;
|
||||
while ((match = re.exec(code))) {
|
||||
yield match.index;
|
||||
}
|
||||
}
|
||||
|
||||
const dependencyOffsets = Array.from(findDependencyOffsets());
|
||||
const module = createModule('test module', ['x', 'y']);
|
||||
const resolutionResponse = new ResolutionResponseMock({
|
||||
dependencies: [module],
|
||||
mainModuleId: 'test module',
|
||||
});
|
||||
|
||||
resolutionResponse.getResolvedDependencyPairs = module => {
|
||||
return [
|
||||
['x', createModule('changed')],
|
||||
['y', createModule('Y')],
|
||||
['abc', createModule('abc')],
|
||||
];
|
||||
it('should use minified code', () => {
|
||||
expect.assertions(2);
|
||||
const minifiedCode = 'minified(code)';
|
||||
const minifiedMap = {
|
||||
version: 3,
|
||||
file: ['minified'],
|
||||
sources: [],
|
||||
mappings: '',
|
||||
};
|
||||
|
||||
const moduleIds = new Map(
|
||||
resolutionResponse
|
||||
.getResolvedDependencyPairs()
|
||||
.map(([importId, module]) => [
|
||||
importId,
|
||||
padRight(
|
||||
resolutionResponse.getModuleId(module.path),
|
||||
importId.length + 2,
|
||||
),
|
||||
]),
|
||||
minifyCode.mockReturnValue(
|
||||
Promise.resolve({code: minifiedCode, map: minifiedMap}),
|
||||
);
|
||||
|
||||
const dependencyPairs = new Map();
|
||||
for (const [
|
||||
relativePath,
|
||||
dependencyModule,
|
||||
] of resolutionResponse.getResolvedDependencyPairs(module)) {
|
||||
dependencyPairs.set(relativePath, dependencyModule.path);
|
||||
}
|
||||
|
||||
const processedCode = depResolver.wrapModule({
|
||||
path: module.path,
|
||||
getModuleId: resolutionResponse.getModuleId,
|
||||
dependencyPairs,
|
||||
name: 'test module',
|
||||
code,
|
||||
dependencyOffsets,
|
||||
dev: false,
|
||||
});
|
||||
|
||||
expect(processedCode).toEqual(
|
||||
[
|
||||
'__d(/* test module */function(global, require, module, exports) {' +
|
||||
// require
|
||||
`require(${moduleIds.get('x')}) // ${moduleIds
|
||||
.get('x')
|
||||
.trim()} = x`,
|
||||
`require(${moduleIds.get('y')});require(${moduleIds.get(
|
||||
'abc',
|
||||
)}); // ${moduleIds.get('abc').trim()} = abc // ${moduleIds
|
||||
.get('y')
|
||||
.trim()} = y`,
|
||||
"require( 'z' )",
|
||||
'require( "a")',
|
||||
'require("b" )',
|
||||
`}, ${resolutionResponse.getModuleId(module.path)});`,
|
||||
].join('\n'),
|
||||
);
|
||||
});
|
||||
|
||||
it('should add module transport names as fourth argument to `__d`', () => {
|
||||
expect.assertions(1);
|
||||
|
||||
const module = createModule('test module');
|
||||
const code = 'arbitrary(code)';
|
||||
const resolutionResponse = new ResolutionResponseMock({
|
||||
dependencies: [module],
|
||||
mainModuleId: 'test module',
|
||||
});
|
||||
|
||||
const processedCode = depResolver.wrapModule({
|
||||
getModuleId: resolutionResponse.getModuleId,
|
||||
dependencyPairs: resolutionResponse.getResolvedDependencyPairs(module),
|
||||
code,
|
||||
path: module.path,
|
||||
name: 'test module',
|
||||
dev: true,
|
||||
});
|
||||
expect(processedCode).toEqual(
|
||||
[
|
||||
'__d(/* test module */function(global, require, module, exports) {' +
|
||||
code,
|
||||
`}, ${resolutionResponse.getModuleId(
|
||||
module.path,
|
||||
)}, null, "test module");`,
|
||||
].join('\n'),
|
||||
);
|
||||
});
|
||||
|
||||
describe('minification:', () => {
|
||||
const code = 'arbitrary(code)';
|
||||
const id = 'arbitrary.js';
|
||||
let depResolver, minifyCode, module, resolutionResponse, sourceMap;
|
||||
|
||||
beforeEach(() => {
|
||||
minifyCode = jest.fn((filename, code, map) =>
|
||||
Promise.resolve({code, map}),
|
||||
);
|
||||
module = createModule(id);
|
||||
module.path = '/arbitrary/path.js';
|
||||
resolutionResponse = new ResolutionResponseMock({
|
||||
dependencies: [module],
|
||||
mainModuleId: id,
|
||||
return depResolver
|
||||
.minifyModule(module.path, code, sourceMap)
|
||||
.then(({code, map}) => {
|
||||
expect(code).toEqual(minifiedCode);
|
||||
expect(map).toEqual([]);
|
||||
});
|
||||
sourceMap = [];
|
||||
return Resolver.load({
|
||||
projectRoot: '/root',
|
||||
minifyCode,
|
||||
postMinifyProcess: e => e,
|
||||
}).then(r => {
|
||||
depResolver = r;
|
||||
});
|
||||
});
|
||||
|
||||
it('should use minified code', () => {
|
||||
expect.assertions(2);
|
||||
const minifiedCode = 'minified(code)';
|
||||
const minifiedMap = {
|
||||
version: 3,
|
||||
file: ['minified'],
|
||||
sources: [],
|
||||
mappings: '',
|
||||
};
|
||||
minifyCode.mockReturnValue(
|
||||
Promise.resolve({code: minifiedCode, map: minifiedMap}),
|
||||
);
|
||||
return depResolver
|
||||
.minifyModule(module.path, code, sourceMap)
|
||||
.then(({code, map}) => {
|
||||
expect(code).toEqual(minifiedCode);
|
||||
expect(map).toEqual([]);
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
function createGetModuleId() {
|
||||
let nextId = 1;
|
||||
const knownIds = new Map();
|
||||
function createId(path) {
|
||||
const id = nextId;
|
||||
nextId += 1;
|
||||
knownIds.set(path, id);
|
||||
return id;
|
||||
}
|
||||
|
||||
return path => knownIds.get(path) || createId(path);
|
||||
}
|
||||
|
||||
function padRight(value, width) {
|
||||
const s = String(value);
|
||||
const diff = width - s.length;
|
||||
return diff > 0 ? s + Array(diff + 1).join(' ') : s;
|
||||
}
|
||||
});
|
||||
|
|
|
@ -116,66 +116,6 @@ class Resolver {
|
|||
);
|
||||
}
|
||||
|
||||
resolveRequires(
|
||||
getModuleId: (path: string) => number,
|
||||
code: string,
|
||||
dependencyPairs: Map<string, string>,
|
||||
dependencyOffsets: Array<number> = [],
|
||||
): string {
|
||||
const resolvedDeps = Object.create(null);
|
||||
|
||||
// here, we build a map of all require strings (relative and absolute)
|
||||
// to the canonical ID of the module they reference
|
||||
for (const [name, path] of dependencyPairs) {
|
||||
resolvedDeps[name] = getModuleId(path);
|
||||
}
|
||||
|
||||
// if we have a canonical ID for the module imported here,
|
||||
// we use it, so that require() is always called with the same
|
||||
// id for every module.
|
||||
// Example:
|
||||
// -- in a/b.js:
|
||||
// require('./c') => require(3);
|
||||
// -- in b/index.js:
|
||||
// require('../a/c') => require(3);
|
||||
return dependencyOffsets
|
||||
.reduceRight(
|
||||
([unhandled, handled], offset) => [
|
||||
unhandled.slice(0, offset),
|
||||
replaceDependencyID(unhandled.slice(offset) + handled, resolvedDeps),
|
||||
],
|
||||
[code, ''],
|
||||
)
|
||||
.join('');
|
||||
}
|
||||
|
||||
wrapModule({
|
||||
path,
|
||||
getModuleId,
|
||||
dependencyPairs,
|
||||
dependencyOffsets,
|
||||
name,
|
||||
code,
|
||||
dev = true,
|
||||
}: {
|
||||
path: string,
|
||||
getModuleId: (path: string) => number,
|
||||
dependencyPairs: Map<string, string>,
|
||||
dependencyOffsets: Array<number>,
|
||||
name: string,
|
||||
code: string,
|
||||
dev?: boolean,
|
||||
}): string {
|
||||
code = this.resolveRequires(
|
||||
getModuleId,
|
||||
code,
|
||||
dependencyPairs,
|
||||
dependencyOffsets,
|
||||
);
|
||||
|
||||
return defineModuleCode(getModuleId(path), code, name, dev);
|
||||
}
|
||||
|
||||
async minifyModule(
|
||||
path: string,
|
||||
code: string,
|
||||
|
@ -200,48 +140,4 @@ class Resolver {
|
|||
}
|
||||
}
|
||||
|
||||
function defineModuleCode(moduleName, code, verboseName = '', dev = true) {
|
||||
return [
|
||||
`__d(/* ${verboseName} */`,
|
||||
'function(global, require, module, exports) {', // module factory
|
||||
code,
|
||||
'\n}, ',
|
||||
`${JSON.stringify(moduleName)}`, // module id, null = id map. used in ModuleGraph
|
||||
dev ? `, null, ${JSON.stringify(verboseName)}` : '',
|
||||
');',
|
||||
].join('');
|
||||
}
|
||||
|
||||
function definePolyfillCode(code) {
|
||||
return [
|
||||
'(function(global) {',
|
||||
code,
|
||||
`\n})(typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : this);`,
|
||||
].join('');
|
||||
}
|
||||
|
||||
const reDepencencyString = /^(['"])([^'"']*)\1/;
|
||||
function replaceDependencyID(stringWithDependencyIDAtStart, resolvedDeps) {
|
||||
const match = reDepencencyString.exec(stringWithDependencyIDAtStart);
|
||||
const dependencyName = match && match[2];
|
||||
if (match != null && dependencyName in resolvedDeps) {
|
||||
const {length} = match[0];
|
||||
const id = String(resolvedDeps[dependencyName]);
|
||||
return (
|
||||
padRight(id, length) +
|
||||
stringWithDependencyIDAtStart
|
||||
.slice(length)
|
||||
.replace(/$/m, ` // ${id} = ${dependencyName}`)
|
||||
);
|
||||
} else {
|
||||
return stringWithDependencyIDAtStart;
|
||||
}
|
||||
}
|
||||
|
||||
function padRight(string, length) {
|
||||
return string.length < length
|
||||
? string + Array(length - string.length + 1).join(' ')
|
||||
: string;
|
||||
}
|
||||
|
||||
module.exports = Resolver;
|
||||
|
|
Loading…
Reference in New Issue