1515import * as vscode from "vscode" ;
1616import { FolderContext } from "../FolderContext" ;
1717import { getErrorDescription } from "../utilities/utilities" ;
18- import { isPathInsidePath } from "../utilities/filesystem" ;
1918import { FolderOperation , WorkspaceContext } from "../WorkspaceContext" ;
2019import { TestRunProxy , TestRunner } from "./TestRunner" ;
2120import { LSPTestDiscovery } from "./LSPTestDiscovery" ;
@@ -136,45 +135,11 @@ export class TestExplorer {
136135 const disposable = workspaceContext . onDidChangeFolders ( ( { folder, operation } ) => {
137136 switch ( operation ) {
138137 case FolderOperation . add :
139- if ( folder ) {
140- void folder . swiftPackage . getTargets ( TargetType . test ) . then ( targets => {
141- if ( targets . length === 0 ) {
142- return ;
143- }
144-
145- folder . addTestExplorer ( ) ;
146- // discover tests in workspace but only if disableAutoResolve is not on.
147- // discover tests will kick off a resolve if required
148- if ( ! configuration . folder ( folder . workspaceFolder ) . disableAutoResolve ) {
149- void folder . testExplorer ?. discoverTestsInWorkspace (
150- tokenSource . token
151- ) ;
152- }
153- } ) ;
154- }
155- break ;
156138 case FolderOperation . packageUpdated :
157139 if ( folder ) {
158- void folder . swiftPackage . getTargets ( TargetType . test ) . then ( targets => {
159- const hasTestTargets = targets . length > 0 ;
160- if ( hasTestTargets && ! folder . hasTestExplorer ( ) ) {
161- folder . addTestExplorer ( ) ;
162- // discover tests in workspace but only if disableAutoResolve is not on.
163- // discover tests will kick off a resolve if required
164- if (
165- ! configuration . folder ( folder . workspaceFolder ) . disableAutoResolve
166- ) {
167- void folder . testExplorer ?. discoverTestsInWorkspace (
168- tokenSource . token
169- ) ;
170- }
171- } else if ( ! hasTestTargets && folder . hasTestExplorer ( ) ) {
172- folder . removeTestExplorer ( ) ;
173- } else if ( folder . hasTestExplorer ( ) ) {
174- folder . refreshTestExplorer ( ) ;
175- }
176- } ) ;
140+ void this . setupTestExplorerForFolder ( folder , tokenSource . token ) ;
177141 }
142+ break ;
178143 }
179144 } ) ;
180145 return {
@@ -185,6 +150,28 @@ export class TestExplorer {
185150 } ;
186151 }
187152
153+ /**
154+ * Configures a test explorer for the given folder.
155+ * If the folder has test targets, and there is no existing test explorer,
156+ * it will create a test explorer and discover tests.
157+ * If the folder has no test targets, it will remove any existing test explorer.
158+ * If the folder has test targets and an existing test explorer, it will refresh the tests.
159+ */
160+ private static async setupTestExplorerForFolder (
161+ folder : FolderContext ,
162+ token : vscode . CancellationToken
163+ ) {
164+ const targets = await folder . swiftPackage . getTargets ( TargetType . test ) ;
165+ const hasTestTargets = targets . length > 0 ;
166+ if ( hasTestTargets && ! folder . hasTestExplorer ( ) ) {
167+ await folder . addTestExplorer ( ) . discoverTestsInWorkspace ( token ) ;
168+ } else if ( hasTestTargets && folder . hasTestExplorer ( ) ) {
169+ await folder . refreshTestExplorer ( ) ;
170+ } else if ( ! hasTestTargets && folder . hasTestExplorer ( ) ) {
171+ folder . removeTestExplorer ( ) ;
172+ }
173+ }
174+
188175 /**
189176 * Sets the `swift.tests` context variable which is used by commands
190177 * to determine if the test item belongs to the Swift extension.
@@ -196,45 +183,29 @@ export class TestExplorer {
196183 } ) ;
197184 }
198185
199- /**
200- * Called whenever we have new document symbols
201- */
202- static onDocumentSymbols (
186+ async getDocumentTests (
203187 folder : FolderContext ,
204- document : vscode . TextDocument ,
205- symbols : vscode . DocumentSymbol [ ] | null | undefined
206- ) {
207- const uri = document ?. uri ;
208- const testExplorer = folder ?. testExplorer ;
209- if ( testExplorer && symbols && uri && uri . scheme === "file" ) {
210- if ( isPathInsidePath ( uri . fsPath , folder . folder . fsPath ) ) {
211- void folder . swiftPackage . getTarget ( uri . fsPath ) . then ( target => {
212- if ( target && target . type === "test" ) {
213- testExplorer . lspTestDiscovery
214- . getDocumentTests ( folder . swiftPackage , uri )
215- . then ( tests => {
216- TestDiscovery . updateTestsForTarget (
217- testExplorer . controller ,
218- { id : target . c99name , label : target . name } ,
219- tests ,
220- uri
221- ) ;
222- testExplorer . onTestItemsDidChangeEmitter . fire (
223- testExplorer . controller
224- ) ;
225- } )
226- // Fallback to parsing document symbols for XCTests only
227- . catch ( ( ) => {
228- const tests = parseTestsFromDocumentSymbols (
229- target . name ,
230- symbols ,
231- uri
232- ) ;
233- testExplorer . updateTests ( testExplorer . controller , tests , uri ) ;
234- } ) ;
235- }
236- } ) ;
237- }
188+ uri : vscode . Uri ,
189+ symbols : vscode . DocumentSymbol [ ]
190+ ) : Promise < void > {
191+ const target = await folder . swiftPackage . getTarget ( uri . fsPath ) ;
192+ if ( ! target || target . type !== "test" ) {
193+ return ;
194+ }
195+
196+ try {
197+ const tests = await this . lspTestDiscovery . getDocumentTests ( folder . swiftPackage , uri ) ;
198+ TestDiscovery . updateTestsForTarget (
199+ this . controller ,
200+ { id : target . c99name , label : target . name } ,
201+ tests ,
202+ uri
203+ ) ;
204+ this . onTestItemsDidChangeEmitter . fire ( this . controller ) ;
205+ } catch {
206+ // Fallback to parsing document symbols for XCTests only
207+ const tests = parseTestsFromDocumentSymbols ( target . name , symbols , uri ) ;
208+ this . updateTests ( this . controller , tests , uri ) ;
238209 }
239210 }
240211
0 commit comments