Skip to content

Commit

Permalink
react-native: make automated fs-based tests platform-independent
Browse files Browse the repository at this point in the history
Summary:
@public

These tests are using a mock memory FS to start with, so there is no reason at all they should depend on the host OS or filesystem details. This changeset fixes that so that we fully mock the `fs` and `path` modules dependending on the mock platform (not the host platform). I also added an example of how we can test both platforms (regardless of the host platform) in `findPackageClassName`. Follow up changeset will be to do the same for all the other affected tests.

Related to #20260.

Reviewed By: mjesun

Differential Revision: D9771024

fbshipit-source-id: b368b43e8e54292d33b6183eec9a9ea69f2e6e76
  • Loading branch information
Jean Lauliac authored and facebook-github-bot committed Sep 17, 2018
1 parent 470a958 commit e327f88
Show file tree
Hide file tree
Showing 16 changed files with 101 additions and 35 deletions.
34 changes: 26 additions & 8 deletions local-cli/__mocks__/fs.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,18 +9,21 @@

'use strict';

const fs = new (require('metro-memory-fs'))({cwd: process.cwd});
const path = require('path');
const MemoryFS = require('metro-memory-fs');
let fs;

function setMockFilesystem(object) {
fs.reset();
const root = process.platform === 'win32' ? 'c:\\' : '/';
function setMockFilesystem(object, platform) {
reset(platform);
const root = platform === 'win32' ? 'c:\\' : '/';
mockDir(root, {...object});
return root;
}

function mockDir(dirPath, desc) {
for (const entName in desc) {
const ent = desc[entName];
const entPath = require('path').join(dirPath, entName);
const entPath = path.join(dirPath, entName);
if (typeof ent === 'string' || ent instanceof Buffer) {
fs.writeFileSync(entPath, ent);
continue;
Expand All @@ -37,7 +40,22 @@ function mockDir(dirPath, desc) {
}
}

fs.__setMockFilesystem = setMockFilesystem;
fs.mock = {clear: () => fs.reset()};
function reset(platform) {
if (path.mock == null) {
throw new Error(
'to use this "fs" module mock, you must also mock the "path" module',
);
}
path.mock.reset(platform);
const cwd = () => (platform === 'win32' ? 'c:\\' : '/');
fs = new MemoryFS({platform, cwd});
Object.assign(mockFs, fs);
}

const mockFs = {};
mockFs.__setMockFilesystem = setMockFilesystem;
mockFs.mock = {clear: reset};

reset('posix');

module.exports = fs;
module.exports = mockFs;
20 changes: 20 additions & 0 deletions local-cli/__mocks__/path.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
/**
* Copyright (c) Facebook, Inc. and its affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*
* @format
*/

'use strict';

const mockPath = {};

function reset(platform) {
Object.assign(mockPath, jest.requireActual('path')[platform]);
}

mockPath.mock = {reset};

module.exports = mockPath;
11 changes: 9 additions & 2 deletions local-cli/core/__fixtures__/android.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,14 @@
/** @format */
/**
* Copyright (c) Facebook, Inc. and its affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*
* @format
*/

const fs = require.requireActual('fs');
const path = require('path');
const path = require.requireActual('path');

const manifest = fs.readFileSync(
path.join(__dirname, './files/AndroidManifest.xml'),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

'use strict';

jest.mock('path');
jest.mock('fs');

const fs = require('fs');
Expand Down
1 change: 1 addition & 0 deletions local-cli/core/__tests__/android/findManifest.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

'use strict';

jest.mock('path');
jest.mock('fs');

const findManifest = require('../../android/findManifest');
Expand Down
59 changes: 34 additions & 25 deletions local-cli/core/__tests__/android/findPackageClassName.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,40 +10,49 @@

'use strict';

jest.mock('path');
jest.mock('fs');

const mocks = require('../../__fixtures__/android');
const findPackageClassName = require('../../android/findPackageClassName');
const fs = require('fs');
const mocks = require('../../__fixtures__/android');

describe('android::findPackageClassName', () => {
beforeAll(() => {
fs.__setMockFilesystem({
empty: {},
flatJava: {
android: mocks.valid,
},
flatKotlin: {
android: mocks.validKotlin,
},
['posix', 'win32'].forEach(platform => {
let root;
describe(`android::findPackageClassName (${platform})`, () => {
beforeAll(() => {
root = fs.__setMockFilesystem(
{
empty: {},
flatJava: {
android: mocks.valid,
},
flatKotlin: {
android: mocks.validKotlin,
},
},
platform,
);
});
});

it('returns manifest content if file exists in the folder', () => {
expect(typeof findPackageClassName('/flatJava')).toBe('string');
});
it('returns manifest content if file exists in the folder', () => {
expect(typeof findPackageClassName(root + 'flatJava')).toBe('string');
});

it('returns the name of the java class implementing ReactPackage', () => {
expect(findPackageClassName('/flatJava')).toBe('SomeExampleJavaPackage');
});
it('returns the name of the java class implementing ReactPackage', () => {
expect(findPackageClassName(root + 'flatJava')).toBe(
'SomeExampleJavaPackage',
);
});

it('returns the name of the kotlin class implementing ReactPackage', () => {
expect(findPackageClassName('/flatKotlin')).toBe(
'SomeExampleKotlinPackage',
);
});
it('returns the name of the kotlin class implementing ReactPackage', () => {
expect(findPackageClassName(root + 'flatKotlin')).toBe(
'SomeExampleKotlinPackage',
);
});

it('returns `null` if there are no matches', () => {
expect(findPackageClassName('/empty')).toBeNull();
it('returns `null` if there are no matches', () => {
expect(findPackageClassName(root + 'empty')).toBeNull();
});
});
});
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

'use strict';

jest.mock('path');
jest.mock('fs');

const getDependencyConfig = require('../../android').dependencyConfig;
Expand Down
1 change: 1 addition & 0 deletions local-cli/core/__tests__/android/getProjectConfig.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

'use strict';

jest.mock('path');
jest.mock('fs');

const getProjectConfig = require('../../android').projectConfig;
Expand Down
1 change: 1 addition & 0 deletions local-cli/core/__tests__/android/readManifest.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

'use strict';

jest.mock('path');
jest.mock('fs');

const findManifest = require('../../android/findManifest');
Expand Down
1 change: 1 addition & 0 deletions local-cli/core/__tests__/findAssets.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

'use strict';

jest.mock('path');
jest.mock('fs');

const findAssets = require('../findAssets');
Expand Down
1 change: 1 addition & 0 deletions local-cli/core/__tests__/ios/findPodfilePath.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

'use strict';

jest.mock('path');
jest.mock('fs');

const findPodfilePath = require('../../ios/findPodfilePath');
Expand Down
1 change: 1 addition & 0 deletions local-cli/core/__tests__/ios/findPodspecName.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

'use strict';

jest.mock('path');
jest.mock('fs');

const findPodspecName = require('../../ios/findPodspecName');
Expand Down
1 change: 1 addition & 0 deletions local-cli/core/__tests__/ios/findProject.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

'use strict';

jest.mock('path');
jest.mock('fs');

const findProject = require('../../ios/findProject');
Expand Down
1 change: 1 addition & 0 deletions local-cli/core/__tests__/ios/getProjectConfig.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

'use strict';

jest.mock('path');
jest.mock('fs');

const getProjectConfig = require('../../ios').projectConfig;
Expand Down
1 change: 1 addition & 0 deletions local-cli/link/__tests__/ios/writePlist.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

'use strict';

jest.mock('path');
jest.mock('fs');

let plistPath = null;
Expand Down
1 change: 1 addition & 0 deletions local-cli/util/__tests__/findSymlinkedModules-test.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
* @emails oncall+javascript_foundation
*/

jest.mock('path');
jest.mock('fs');

const fs = require('fs');
Expand Down

0 comments on commit e327f88

Please sign in to comment.