-
-
Notifications
You must be signed in to change notification settings - Fork 6.5k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(vcs): Support Sapling in jest-changed-files (#13941)
- Loading branch information
Showing
7 changed files
with
398 additions
and
40 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -7,16 +7,25 @@ | |
|
||
import {tmpdir} from 'os'; | ||
import * as path from 'path'; | ||
import * as fs from 'graceful-fs'; | ||
import semver = require('semver'); | ||
import slash = require('slash'); | ||
import {findRepos, getChangedFilesForRoots} from 'jest-changed-files'; | ||
import {cleanup, run, testIfHg, writeFiles} from '../Utils'; | ||
import { | ||
cleanup, | ||
run, | ||
testIfHg, | ||
testIfSl, | ||
testIfSlAndHg, | ||
writeFiles, | ||
} from '../Utils'; | ||
import runJest from '../runJest'; | ||
|
||
const DIR = path.resolve(tmpdir(), 'jest-changed-files-test-dir'); | ||
|
||
const GIT = 'git -c user.name=jest_test -c [email protected]'; | ||
const HG = 'hg --config ui.username=jest_test'; | ||
const SL = 'sl --config ui.username=jest_test'; | ||
|
||
const gitVersionSupportsInitialBranch = (() => { | ||
const {stdout} = run(`${GIT} --version`); | ||
|
@@ -129,42 +138,56 @@ test('gets git SCM roots and dedupes them', async () => { | |
); | ||
}); | ||
|
||
testIfHg('gets mixed git and hg SCM roots and dedupes them', async () => { | ||
writeFiles(DIR, { | ||
'first-repo/file1.txt': 'file1', | ||
'first-repo/nested-dir/file2.txt': 'file2', | ||
'first-repo/nested-dir/second-nested-dir/file3.txt': 'file3', | ||
'second-repo/file1.txt': 'file1', | ||
'second-repo/nested-dir/file2.txt': 'file2', | ||
'second-repo/nested-dir/second-nested-dir/file3.txt': 'file3', | ||
}); | ||
|
||
gitInit(path.resolve(DIR, 'first-repo')); | ||
run(`${HG} init`, path.resolve(DIR, 'second-repo')); | ||
|
||
const roots = [ | ||
'', | ||
'first-repo/nested-dir', | ||
'first-repo/nested-dir/second-nested-dir', | ||
'second-repo/nested-dir', | ||
'second-repo/nested-dir/second-nested-dir', | ||
].map(filename => path.resolve(DIR, filename)); | ||
|
||
const repos = await findRepos(roots); | ||
const hgRepos = Array.from(repos.hg); | ||
const gitRepos = Array.from(repos.git); | ||
|
||
// NOTE: This test can break if you have a .git or .hg repo initialized | ||
// inside your os tmp directory. | ||
expect(gitRepos).toHaveLength(1); | ||
expect(hgRepos).toHaveLength(1); | ||
expect(slash(gitRepos[0])).toMatch( | ||
/\/jest-changed-files-test-dir\/first-repo\/?$/, | ||
); | ||
expect(slash(hgRepos[0])).toMatch( | ||
/\/jest-changed-files-test-dir\/second-repo\/?$/, | ||
); | ||
}); | ||
testIfSlAndHg( | ||
'gets mixed git, hg, and sl SCM roots and dedupes them', | ||
async () => { | ||
writeFiles(DIR, { | ||
'first-repo/file1.txt': 'file1', | ||
'first-repo/nested-dir/file2.txt': 'file2', | ||
'first-repo/nested-dir/second-nested-dir/file3.txt': 'file3', | ||
'second-repo/file1.txt': 'file1', | ||
'second-repo/nested-dir/file2.txt': 'file2', | ||
'second-repo/nested-dir/second-nested-dir/file3.txt': 'file3', | ||
'third-repo/file1.txt': 'file1', | ||
'third-repo/nested-dir/file2.txt': 'file2', | ||
'third-repo/nested-dir/second-nested-dir/file3.txt': 'file3', | ||
}); | ||
|
||
gitInit(path.resolve(DIR, 'first-repo')); | ||
run(`${HG} init`, path.resolve(DIR, 'second-repo')); | ||
run(`${SL} init --git`, path.resolve(DIR, 'third-repo')); | ||
|
||
const roots = [ | ||
'', | ||
'first-repo/nested-dir', | ||
'first-repo/nested-dir/second-nested-dir', | ||
'second-repo/nested-dir', | ||
'second-repo/nested-dir/second-nested-dir', | ||
'third-repo/nested-dir', | ||
'third-repo/nested-dir/second-nested-dir', | ||
].map(filename => path.resolve(DIR, filename)); | ||
|
||
const repos = await findRepos(roots); | ||
const hgRepos = Array.from(repos.hg); | ||
const gitRepos = Array.from(repos.git); | ||
const slRepos = Array.from(repos.sl); | ||
|
||
// NOTE: This test can break if you have a .git or .hg repo initialized | ||
// inside your os tmp directory. | ||
expect(gitRepos).toHaveLength(1); | ||
expect(hgRepos).toHaveLength(1); | ||
expect(slRepos).toHaveLength(1); | ||
expect(slash(gitRepos[0])).toMatch( | ||
/\/jest-changed-files-test-dir\/first-repo\/?$/, | ||
); | ||
expect(slash(hgRepos[0])).toMatch( | ||
/\/jest-changed-files-test-dir\/second-repo\/?$/, | ||
); | ||
expect(slash(slRepos[0])).toMatch( | ||
/\/jest-changed-files-test-dir\/third-repo\/?$/, | ||
); | ||
}, | ||
); | ||
|
||
test('gets changed files for git', async () => { | ||
writeFiles(DIR, { | ||
|
@@ -496,3 +519,183 @@ testIfHg('handles a bad revision for "changedSince", for hg', async () => { | |
expect(stderr).toContain('Test suite failed to run'); | ||
expect(stderr).toContain("abort: unknown revision 'blablabla'"); | ||
}); | ||
|
||
testIfSl('gets sl SCM roots and dedupes them', async () => { | ||
fs.mkdirSync(path.resolve(DIR, 'first-repo'), {recursive: true}); | ||
writeFiles(DIR, { | ||
'first-repo/file1.txt': 'file1', | ||
'first-repo/nested-dir/file2.txt': 'file2', | ||
'first-repo/nested-dir/second-nested-dir/file3.txt': 'file3', | ||
'second-repo/file1.txt': 'file1', | ||
'second-repo/nested-dir/file2.txt': 'file2', | ||
'second-repo/nested-dir/second-nested-dir/file3.txt': 'file3', | ||
}); | ||
|
||
run(`${SL} init --git`, path.resolve(DIR, 'first-repo')); | ||
run(`${SL} init --git`, path.resolve(DIR, 'second-repo')); | ||
|
||
const roots = [ | ||
'', | ||
'first-repo/nested-dir', | ||
'first-repo/nested-dir/second-nested-dir', | ||
'second-repo/nested-dir', | ||
'second-repo/nested-dir/second-nested-dir', | ||
].map(filename => path.resolve(DIR, filename)); | ||
|
||
const repos = await findRepos(roots); | ||
expect(repos.git.size).toBe(0); | ||
expect(repos.hg.size).toBe(0); | ||
|
||
const slRepos = Array.from(repos.sl); | ||
|
||
// it's not possible to match the exact path because it will resolve | ||
// differently on different platforms. | ||
// NOTE: This test can break if you have a .sl repo initialized inside your | ||
// os tmp directory. | ||
expect(slRepos).toHaveLength(2); | ||
expect(slash(slRepos[0])).toMatch( | ||
/\/jest-changed-files-test-dir\/first-repo\/?$/, | ||
); | ||
expect(slash(slRepos[1])).toMatch( | ||
/\/jest-changed-files-test-dir\/second-repo\/?$/, | ||
); | ||
}); | ||
|
||
testIfSl('gets changed files for sl', async () => { | ||
// file1.txt is used to make a multi-line commit message | ||
// with `sl commit -l file1.txt`. | ||
// This is done to ensure that `changedFiles` only returns files | ||
// and not parts of commit messages. | ||
writeFiles(DIR, { | ||
'file1.txt': 'file1\n\nextra-line', | ||
'nested-dir/file2.txt': 'file2', | ||
'nested-dir/second-nested-dir/file3.txt': 'file3', | ||
}); | ||
|
||
run(`${SL} init --git`, DIR); | ||
|
||
const roots = ['', 'nested-dir', 'nested-dir/second-nested-dir'].map( | ||
filename => path.resolve(DIR, filename), | ||
); | ||
|
||
let {changedFiles: files} = await getChangedFilesForRoots(roots, {}); | ||
expect( | ||
Array.from(files) | ||
.map(filePath => path.basename(filePath)) | ||
.sort(), | ||
).toEqual(['file1.txt', 'file2.txt', 'file3.txt']); | ||
|
||
run(`${SL} add .`, DIR); | ||
run(`${SL} commit -l file1.txt`, DIR); | ||
|
||
({changedFiles: files} = await getChangedFilesForRoots(roots, {})); | ||
expect(Array.from(files)).toEqual([]); | ||
|
||
({changedFiles: files} = await getChangedFilesForRoots(roots, { | ||
lastCommit: true, | ||
})); | ||
expect( | ||
Array.from(files) | ||
.map(filePath => path.basename(filePath)) | ||
.sort(), | ||
).toEqual(['file1.txt', 'file2.txt', 'file3.txt']); | ||
|
||
writeFiles(DIR, { | ||
'file1.txt': 'modified file1', | ||
}); | ||
|
||
({changedFiles: files} = await getChangedFilesForRoots(roots, {})); | ||
expect( | ||
Array.from(files) | ||
.map(filePath => path.basename(filePath)) | ||
.sort(), | ||
).toEqual(['file1.txt']); | ||
|
||
run(`${SL} commit -m "test2"`, DIR); | ||
|
||
writeFiles(DIR, { | ||
'file4.txt': 'file4', | ||
}); | ||
|
||
({changedFiles: files} = await getChangedFilesForRoots(roots, { | ||
withAncestor: true, | ||
})); | ||
// Returns files from current uncommitted state + the last commit | ||
expect( | ||
Array.from(files) | ||
.map(filePath => path.basename(filePath)) | ||
.sort(), | ||
).toEqual(['file1.txt', 'file4.txt']); | ||
|
||
run(`${SL} add file4.txt`, DIR); | ||
run(`${SL} commit -m "test3"`, DIR); | ||
|
||
({changedFiles: files} = await getChangedFilesForRoots(roots, { | ||
changedSince: '.~2', | ||
})); | ||
// Returns files from the last 2 commits | ||
expect( | ||
Array.from(files) | ||
.map(filePath => path.basename(filePath)) | ||
.sort(), | ||
).toEqual(['file1.txt', 'file4.txt']); | ||
|
||
run(`${SL} bookmark main_branch`, DIR); | ||
// Back up and develop on a different branch | ||
run(`${SL}`, DIR); | ||
run(`${SL} go prev(2)`, DIR); | ||
|
||
writeFiles(DIR, { | ||
'file5.txt': 'file5', | ||
}); | ||
run(`${SL} add file5.txt`, DIR); | ||
run(`${SL} commit -m "test4"`, DIR); | ||
|
||
({changedFiles: files} = await getChangedFilesForRoots(roots, { | ||
changedSince: 'main_branch', | ||
})); | ||
// Returns files from this branch but not ones that only exist on main | ||
expect( | ||
Array.from(files) | ||
.map(filePath => path.basename(filePath)) | ||
.sort(), | ||
).toEqual(['file5.txt']); | ||
}); | ||
|
||
testIfSl('monitors only root paths for sl', async () => { | ||
writeFiles(DIR, { | ||
'file1.txt': 'file1', | ||
'nested-dir/file2.txt': 'file2', | ||
'nested-dir/second-nested-dir/file3.txt': 'file3', | ||
}); | ||
|
||
run(`${SL} init --git`, DIR); | ||
|
||
const roots = [path.resolve(DIR, 'nested-dir')]; | ||
|
||
const {changedFiles: files} = await getChangedFilesForRoots(roots, {}); | ||
expect( | ||
Array.from(files) | ||
.map(filePath => path.basename(filePath)) | ||
.sort(), | ||
).toEqual(['file2.txt', 'file3.txt']); | ||
}); | ||
|
||
testIfSl('handles a bad revision for "changedSince", for sl', async () => { | ||
writeFiles(DIR, { | ||
'.watchmanconfig': '', | ||
'__tests__/file1.test.js': "require('../file1'); test('file1', () => {});", | ||
'file1.js': 'module.exports = {}', | ||
'package.json': '{}', | ||
}); | ||
|
||
run(`${SL} init --git`, DIR); | ||
run(`${SL} add .`, DIR); | ||
run(`${SL} commit -m "first"`, DIR); | ||
|
||
const {exitCode, stderr} = runJest(DIR, ['--changedSince=blablabla']); | ||
|
||
expect(exitCode).toBe(1); | ||
expect(stderr).toContain('Test suite failed to run'); | ||
expect(stderr).toContain("abort: unknown revision 'blablabla'"); | ||
}); |
Oops, something went wrong.