Skip to content

Commit 2302553

Browse files
phlooseEric Snow
authored andcommitted
Fix codelens action for opening a dropdown on parametrized tests in windows 10 (#8647)
Fixes #8627. When the path of an actual test file (given by vscode.Uri.fsPath) is later compared against the fullPath of a single item of tests.TestFiles the drive letter mismatches and aborts further actions despite the rest of the path is the same.
1 parent 6cadda5 commit 2302553

4 files changed

Lines changed: 203 additions & 5 deletions

File tree

news/2 Fixes/8627.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Fixes that the test selection drop-down did not open when a code lens for a parameterized test was clicked on windows.

src/client/testing/display/picker.ts

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ import * as path from 'path';
33
import { QuickPickItem, Uri } from 'vscode';
44
import { IApplicationShell, ICommandManager } from '../../common/application/types';
55
import * as constants from '../../common/constants';
6+
import { IFileSystem } from '../../common/platform/types';
67
import { IServiceContainer } from '../../ioc/types';
78
import { CommandSource } from '../common/constants';
89
import { FlattenedTestFunction, ITestCollectionStorageService, TestFile, TestFunction, Tests, TestStatus, TestsToRun } from '../common/types';
@@ -12,7 +13,7 @@ import { ITestDisplay } from '../types';
1213
export class TestDisplay implements ITestDisplay {
1314
private readonly testCollectionStorage: ITestCollectionStorageService;
1415
private readonly appShell: IApplicationShell;
15-
constructor(@inject(IServiceContainer) serviceRegistry: IServiceContainer,
16+
constructor(@inject(IServiceContainer) private readonly serviceRegistry: IServiceContainer,
1617
@inject(ICommandManager) private readonly commandManager: ICommandManager) {
1718
this.testCollectionStorage = serviceRegistry.get<ITestCollectionStorageService>(ITestCollectionStorageService);
1819
this.appShell = serviceRegistry.get<IApplicationShell>(IApplicationShell);
@@ -57,7 +58,8 @@ export class TestDisplay implements ITestDisplay {
5758
return;
5859
}
5960
const fileName = file.fsPath;
60-
const testFile = tests.testFiles.find(item => item.name === fileName || item.fullPath === fileName);
61+
const fs = this.serviceRegistry.get<IFileSystem>(IFileSystem);
62+
const testFile = tests.testFiles.find(item => item.name === fileName || fs.arePathsSame(item.fullPath, fileName));
6163
if (!testFile) {
6264
return;
6365
}
Lines changed: 116 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,116 @@
1+
// Copyright (c) Microsoft Corporation. All rights reserved.
2+
// Licensed under the MIT License.
3+
4+
'use strict';
5+
6+
import { anything, instance, mock, verify, when } from 'ts-mockito';
7+
import { Uri } from 'vscode';
8+
import { ApplicationShell } from '../../../client/common/application/applicationShell';
9+
import { CommandManager } from '../../../client/common/application/commandManager';
10+
import { IApplicationShell, ICommandManager } from '../../../client/common/application/types';
11+
import { FileSystem } from '../../../client/common/platform/fileSystem';
12+
import { PlatformService } from '../../../client/common/platform/platformService';
13+
import { IFileSystem } from '../../../client/common/platform/types';
14+
import { ServiceContainer } from '../../../client/ioc/container';
15+
import { IServiceContainer } from '../../../client/ioc/types';
16+
import { CommandSource } from '../../../client/testing/common/constants';
17+
import { TestCollectionStorageService } from '../../../client/testing/common/services/storageService';
18+
import { ITestCollectionStorageService, TestFunction, Tests } from '../../../client/testing/common/types';
19+
import { TestDisplay } from '../../../client/testing/display/picker';
20+
import { createEmptyResults } from '../results';
21+
22+
// tslint:disable:no-any
23+
24+
// tslint:disable-next-line: max-func-body-length
25+
suite('Testing - TestDisplay', () => {
26+
const wkspace = Uri.file(__dirname);
27+
let mockedCommandManager: ICommandManager;
28+
let mockedServiceContainer: IServiceContainer;
29+
let mockedTestCollectionStorage: ITestCollectionStorageService;
30+
let mockedAppShell: IApplicationShell;
31+
let testDisplay: TestDisplay;
32+
33+
function fullPathInTests(collectedTests: Tests, fullpath?: string): Tests {
34+
collectedTests.testFiles = [{
35+
fullPath: fullpath ? fullpath : 'path/to/testfile',
36+
...anything()
37+
}];
38+
return collectedTests;
39+
}
40+
41+
setup(() => {
42+
mockedCommandManager = mock(CommandManager);
43+
mockedServiceContainer = mock(ServiceContainer);
44+
mockedTestCollectionStorage = mock(TestCollectionStorageService);
45+
mockedAppShell = mock(ApplicationShell);
46+
when(mockedServiceContainer.get<ITestCollectionStorageService>(ITestCollectionStorageService))
47+
.thenReturn(instance(mockedTestCollectionStorage));
48+
when(mockedServiceContainer.get<IApplicationShell>(IApplicationShell))
49+
.thenReturn(instance(mockedAppShell));
50+
51+
testDisplay = new TestDisplay(instance(mockedServiceContainer), instance(mockedCommandManager));
52+
});
53+
54+
suite('displayFunctionTestPickerUI', () => {
55+
const paths: { [key: string]: any } = {
56+
match: {
57+
fullPath: '/path/to/testfile',
58+
fileName: '/path/to/testfile'
59+
},
60+
mismatch: {
61+
fullPath: '/path/to/testfile',
62+
fileName: '/testfile/to/path'
63+
}
64+
};
65+
let tests: Tests;
66+
67+
function codeLensTestFunctions(testfunctions?: TestFunction[]): TestFunction[] {
68+
if (!testfunctions) {
69+
return [{ ...anything() }];
70+
}
71+
const functions: TestFunction[] = [];
72+
testfunctions.forEach(fn => functions.push(fn));
73+
return functions;
74+
}
75+
76+
setup(() => {
77+
tests = createEmptyResults();
78+
when(mockedServiceContainer.get<IFileSystem>(IFileSystem)).thenReturn(new FileSystem(new PlatformService()));
79+
when(mockedTestCollectionStorage.getTests(wkspace)).thenReturn(tests);
80+
when(mockedAppShell.showQuickPick(anything(), anything())).thenResolve();
81+
});
82+
83+
test(`Test that a dropdown picker for parametrized tests is shown if compared paths are equal (OS independent) (#8627)`, () => {
84+
const { fullPath, fileName } = paths.match;
85+
fullPathInTests(tests, fullPath);
86+
87+
testDisplay.displayFunctionTestPickerUI(CommandSource.commandPalette, wkspace, 'rootDirectory', Uri.file(fileName), codeLensTestFunctions());
88+
89+
verify(mockedAppShell.showQuickPick(anything(), anything())).once();
90+
});
91+
92+
test(`Test that a dropdown picker for parametrized tests is NOT shown if compared paths are NOT equal (OS independent) (#8627)`, () => {
93+
const { fullPath, fileName } = paths.mismatch;
94+
fullPathInTests(tests, fullPath);
95+
96+
testDisplay.displayFunctionTestPickerUI(CommandSource.commandPalette, wkspace, 'rootDirectory', Uri.file(fileName), codeLensTestFunctions());
97+
98+
verify(mockedAppShell.showQuickPick(anything(), anything())).never();
99+
});
100+
101+
test(`Test that clicking a codelens on parametrized tests opens a dropdown picker on windows (#8627)`, function () {
102+
if (process.platform !== 'win32') {
103+
// tslint:disable-next-line: no-invalid-this
104+
this.skip();
105+
}
106+
// The error described in #8627 originated from the problem that the casing of the drive letter was different
107+
// in a test items fullPath property to the one of a file that contained the clicked parametrized test.
108+
const fileName = 'c:\\path\\to\\testfile';
109+
fullPathInTests(tests, 'C:\\path\\to\\testfile');
110+
111+
testDisplay.displayFunctionTestPickerUI(CommandSource.commandPalette, wkspace, 'rootDirectory', Uri.file(fileName), codeLensTestFunctions());
112+
113+
verify(mockedAppShell.showQuickPick(anything(), anything())).once();
114+
});
115+
});
116+
});

src/test/testing/display/picker.unit.test.ts

Lines changed: 82 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,14 +3,22 @@
33

44
'use strict';
55

6-
import { anything, instance, mock, verify } from 'ts-mockito';
6+
import { anything, instance, mock, verify, when } from 'ts-mockito';
77
import { Uri } from 'vscode';
8+
import { ApplicationShell } from '../../../client/common/application/applicationShell';
89
import { CommandManager } from '../../../client/common/application/commandManager';
10+
import { IApplicationShell, ICommandManager } from '../../../client/common/application/types';
911
import { Commands } from '../../../client/common/constants';
12+
import { FileSystem } from '../../../client/common/platform/fileSystem';
13+
import { IFileSystem } from '../../../client/common/platform/types';
1014
import { getNamesAndValues } from '../../../client/common/utils/enum';
15+
import { ServiceContainer } from '../../../client/ioc/container';
16+
import { IServiceContainer } from '../../../client/ioc/types';
1117
import { CommandSource } from '../../../client/testing/common/constants';
12-
import { TestsToRun } from '../../../client/testing/common/types';
13-
import { onItemSelected, Type } from '../../../client/testing/display/picker';
18+
import { TestCollectionStorageService } from '../../../client/testing/common/services/storageService';
19+
import { ITestCollectionStorageService, TestFunction, Tests, TestsToRun } from '../../../client/testing/common/types';
20+
import { onItemSelected, TestDisplay, Type } from '../../../client/testing/display/picker';
21+
import { createEmptyResults } from '../results';
1422

1523
// tslint:disable:no-any
1624

@@ -99,3 +107,74 @@ suite('Unit Tests - Picker (execution of commands)', () => {
99107
});
100108
});
101109
});
110+
111+
suite('Testing - TestDisplay', () => {
112+
const wkspace = Uri.file(__dirname);
113+
let mockedCommandManager: ICommandManager;
114+
let mockedServiceContainer: IServiceContainer;
115+
let mockedTestCollectionStorage: ITestCollectionStorageService;
116+
let mockedAppShell: IApplicationShell;
117+
let mockedFileSytem: IFileSystem;
118+
let testDisplay: TestDisplay;
119+
120+
function fullPathInTests(collectedTests: Tests, fullpath?: string): Tests {
121+
collectedTests.testFiles = [{
122+
fullPath: fullpath ? fullpath : 'path/to/testfile',
123+
...anything()
124+
}];
125+
return collectedTests;
126+
}
127+
128+
setup(() => {
129+
mockedCommandManager = mock(CommandManager);
130+
mockedServiceContainer = mock(ServiceContainer);
131+
mockedTestCollectionStorage = mock(TestCollectionStorageService);
132+
mockedAppShell = mock(ApplicationShell);
133+
when(mockedServiceContainer.get<ITestCollectionStorageService>(ITestCollectionStorageService))
134+
.thenReturn(instance(mockedTestCollectionStorage));
135+
when(mockedServiceContainer.get<IApplicationShell>(IApplicationShell))
136+
.thenReturn(instance(mockedAppShell));
137+
138+
testDisplay = new TestDisplay(instance(mockedServiceContainer), instance(mockedCommandManager));
139+
});
140+
141+
suite('displayFunctionTestPickerUI', () => {
142+
const fileName = Uri.file('path/to/testfile');
143+
let tests: Tests;
144+
145+
function codeLensTestFunctions(testfunctions?: TestFunction[]): TestFunction[] {
146+
if (!testfunctions) {
147+
return [{ ...anything() }];
148+
}
149+
const functions: TestFunction[] = [];
150+
testfunctions.forEach(fn => functions.push(fn));
151+
return functions;
152+
}
153+
154+
setup(() => {
155+
tests = createEmptyResults();
156+
mockedFileSytem = mock(FileSystem);
157+
when(mockedServiceContainer.get<IFileSystem>(IFileSystem)).thenReturn(instance(mockedFileSytem));
158+
when(mockedTestCollectionStorage.getTests(wkspace)).thenReturn(tests);
159+
when(mockedAppShell.showQuickPick(anything(), anything())).thenResolve();
160+
});
161+
162+
test(`Test that a dropdown picker for parametrized tests is shown if compared paths are equal (#8627)`, () => {
163+
fullPathInTests(tests);
164+
when(mockedFileSytem.arePathsSame(anything(), anything())).thenReturn(true);
165+
166+
testDisplay.displayFunctionTestPickerUI(CommandSource.commandPalette, wkspace, 'rootDirectory', fileName, codeLensTestFunctions());
167+
168+
verify(mockedAppShell.showQuickPick(anything(), anything())).once();
169+
});
170+
171+
test(`Test that a dropdown picker for parametrized tests is NOT shown if compared paths are NOT equal (#8627)`, () => {
172+
fullPathInTests(tests);
173+
when(mockedFileSytem.arePathsSame(anything(), anything())).thenReturn(false);
174+
175+
testDisplay.displayFunctionTestPickerUI(CommandSource.commandPalette, wkspace, 'rootDirectory', fileName, codeLensTestFunctions());
176+
177+
verify(mockedAppShell.showQuickPick(anything(), anything())).never();
178+
});
179+
});
180+
});

0 commit comments

Comments
 (0)