@@ -111,80 +111,66 @@ final class SwiftPMIntegrationTests: XCTestCase {
111111 enableBackgroundIndexing: true
112112 )
113113
114+ // First, create a new in-memory file and verify that we get some basic functionality for it
115+
114116 let newFileUrl = project. scratchDirectory
115117 . appending ( components: " Sources " , " MyLibrary " , " Other.swift " )
116118 let newFileUri = DocumentURI ( newFileUrl)
117119
118120 let newFileContents = """
119121 func baz(l: Lib) {
120122 l.2️⃣foo()
123+ #warning( " A manual warning " )
121124 }
122125 """
123- try await extractMarkers ( newFileContents) . textWithoutMarkers. writeWithRetry ( to: newFileUrl)
124-
125- // Check that we don't get cross-file code completion before we send a `DidChangeWatchedFilesNotification` to make
126- // sure we didn't include the file in the initial retrieval of build settings.
127- let ( oldFileUri, oldFilePositions) = try project. openDocument ( " Lib.swift " )
128126 let newFilePositions = project. testClient. openDocument ( newFileContents, uri: newFileUri)
129127
130- let completionsBeforeDidChangeNotification = try await project. testClient. send (
128+ try await extractMarkers ( newFileContents) . textWithoutMarkers. writeWithRetry ( to: newFileUrl)
129+ let completionsBeforeSave = try await project. testClient. send (
131130 CompletionRequest ( textDocument: TextDocumentIdentifier ( newFileUri) , position: newFilePositions [ " 2️⃣ " ] )
132131 )
133- XCTAssertEqual ( completionsBeforeDidChangeNotification. items, [ ] )
132+ XCTAssertEqual ( Set ( completionsBeforeSave. items. map ( \. label) ) , [ " foo() " , " self " ] )
133+
134+ // We shouldn't get diagnostics for the new file yet since we still consider the build settings inferred from a
135+ // sibling file fallback settings.
136+ let diagnosticsBeforeSave = try await project. testClient. send (
137+ DocumentDiagnosticsRequest ( textDocument: TextDocumentIdentifier ( newFileUri) )
138+ )
139+ XCTAssertEqual ( diagnosticsBeforeSave. fullReport? . items, [ ] )
140+
141+ let ( oldFileUri, oldFilePositions) = try project. openDocument ( " Lib.swift " )
142+ // Check that we don't get completions for `baz` (defined in the new file) in the old file yet because the new file
143+ // is not part of the package manifest yet.
144+ let oldFileCompletionsBeforeSave = try await project. testClient. send (
145+ CompletionRequest ( textDocument: TextDocumentIdentifier ( oldFileUri) , position: oldFilePositions [ " 1️⃣ " ] )
146+ )
147+ XCTAssert ( !oldFileCompletionsBeforeSave. items. contains ( where: { $0. label == " baz(l: Lib) " } ) )
148+
149+ // Now save the file to disk, which adds it to the package graph, which should enable more functionality.
134150
135- // Send a `DidChangeWatchedFilesNotification` and verify that we now get cross-file code completion.
151+ try await extractMarkers ( newFileContents ) . textWithoutMarkers . writeWithRetry ( to : newFileUrl )
136152 project. testClient. send (
137153 DidChangeWatchedFilesNotification ( changes: [
138154 FileEvent ( uri: newFileUri, type: . created)
139155 ] )
140156 )
141-
142157 // Ensure that the DidChangeWatchedFilesNotification is handled before we continue.
143158 try await project. testClient. send ( SynchronizeRequest ( index: true ) )
144159
145- let completions = try await project. testClient. send (
160+ // Check that we still get completions in the new file, now get diagnostics in the new file and also see functions
161+ // from the new file in the old file
162+ let completionsAfterSave = try await project. testClient. send (
146163 CompletionRequest ( textDocument: TextDocumentIdentifier ( newFileUri) , position: newFilePositions [ " 2️⃣ " ] )
147164 )
148-
149- XCTAssertEqual (
150- completions. items. clearingUnstableValues,
151- [
152- CompletionItem (
153- label: " foo() " ,
154- kind: . method,
155- detail: " Void " ,
156- deprecated: false ,
157- sortText: nil ,
158- filterText: " foo() " ,
159- insertText: " foo() " ,
160- insertTextFormat: . plain,
161- textEdit: . textEdit(
162- TextEdit ( range: Range ( newFilePositions [ " 2️⃣ " ] ) , newText: " foo() " )
163- )
164- ) ,
165- CompletionItem (
166- label: " self " ,
167- kind: . keyword,
168- detail: " Lib " ,
169- deprecated: false ,
170- sortText: nil ,
171- filterText: " self " ,
172- insertText: " self " ,
173- insertTextFormat: . plain,
174- textEdit: . textEdit(
175- TextEdit ( range: Range ( newFilePositions [ " 2️⃣ " ] ) , newText: " self " )
176- )
177- ) ,
178- ]
165+ XCTAssertEqual ( Set ( completionsAfterSave. items. map ( \. label) ) , [ " foo() " , " self " ] )
166+ let diagnosticsAfterSave = try await project. testClient. send (
167+ DocumentDiagnosticsRequest ( textDocument: TextDocumentIdentifier ( newFileUri) )
179168 )
180-
181- // Check that we get code completion for `baz` (defined in the new file) in the old file.
182- // I.e. check that the existing file's build settings have been updated to include the new file.
183-
184- let oldFileCompletions = try await project. testClient. send (
169+ XCTAssertEqual ( diagnosticsAfterSave. fullReport? . items. map ( \. message) , [ " A manual warning " ] )
170+ let oldFileCompletionsAfterSave = try await project. testClient. send (
185171 CompletionRequest ( textDocument: TextDocumentIdentifier ( oldFileUri) , position: oldFilePositions [ " 1️⃣ " ] )
186172 )
187- XCTAssert ( oldFileCompletions . items. contains ( where : { $0 . label == " baz(l: Lib) " } ) )
173+ assertContains ( oldFileCompletionsAfterSave . items. map ( \ . label) , " baz(l: Lib) " )
188174 }
189175
190176 func testNestedPackage( ) async throws {
0 commit comments