@@ -18,6 +18,7 @@ import com.intellij.util.messages.MessageBusConnection
1818import io.mockk.every
1919import io.mockk.just
2020import io.mockk.mockk
21+ import io.mockk.mockkObject
2122import io.mockk.mockkStatic
2223import io.mockk.runs
2324import io.mockk.slot
@@ -34,6 +35,7 @@ import org.junit.Before
3435import org.junit.Test
3536import software.aws.toolkits.jetbrains.services.amazonq.lsp.AmazonQLanguageServer
3637import software.aws.toolkits.jetbrains.services.amazonq.lsp.AmazonQLspService
38+ import software.aws.toolkits.jetbrains.services.amazonq.lsp.util.FileUriUtil
3739import java.net.URI
3840import java.nio.file.Path
3941import java.util.concurrent.Callable
@@ -99,14 +101,7 @@ class TextDocumentServiceHandlerTest {
99101 every { text } returns " test content"
100102 }
101103
102- val path = mockk<Path > {
103- every { toUri() } returns uri
104- }
105-
106- val file = mockk<VirtualFile > {
107- every { this @mockk.path } returns uri.path
108- every { toNioPath() } returns path
109- }
104+ val file = createMockVirtualFile(uri)
110105
111106 // Mock FileDocumentManager
112107 val fileDocumentManager = mockk<FileDocumentManager > {
@@ -125,7 +120,7 @@ class TextDocumentServiceHandlerTest {
125120 verify { mockTextDocumentService.didSave(capture(paramsSlot)) }
126121
127122 with (paramsSlot.captured) {
128- assertEquals(uri.toString(), textDocument.uri)
123+ assertEquals(normalizeFileUri( uri.toString() ), textDocument.uri)
129124 assertEquals(" test content" , text)
130125 }
131126 }
@@ -136,17 +131,8 @@ class TextDocumentServiceHandlerTest {
136131 // Create test file
137132 val uri = URI .create(" file:///test/path/file.txt" )
138133 val content = " test content"
139- val inputStream = content.byteInputStream()
140134
141- val path = mockk<Path > {
142- every { toUri() } returns uri
143- }
144-
145- val file = mockk<VirtualFile > {
146- every { this @mockk.path } returns uri.path
147- every { toNioPath() } returns path
148- every { this @mockk.inputStream } returns inputStream
149- }
135+ val file = createMockVirtualFile(uri, content)
150136
151137 // Call the handler method
152138 sut.fileOpened(mockk(), file)
@@ -156,28 +142,22 @@ class TextDocumentServiceHandlerTest {
156142 verify { mockTextDocumentService.didOpen(capture(paramsSlot)) }
157143
158144 with (paramsSlot.captured.textDocument) {
159- assertEquals(uri.toString(), this .uri)
145+ assertEquals(normalizeFileUri( uri.toString() ), this .uri)
160146 assertEquals(content, text)
161147 }
162148 }
163149
164150 @Test
165151 fun `didClose runs on fileClosed` () = runTest {
166152 val uri = URI .create(" file:///test/path/file.txt" )
167- val path = mockk<Path > {
168- every { toUri() } returns uri
169- }
170- val file = mockk<VirtualFile > {
171- every { this @mockk.path } returns uri.path
172- every { toNioPath() } returns path
173- }
153+ val file = createMockVirtualFile(uri)
174154
175155 sut.fileClosed(mockk(), file)
176156
177157 val paramsSlot = slot<DidCloseTextDocumentParams >()
178158 verify { mockTextDocumentService.didClose(capture(paramsSlot)) }
179159
180- assertEquals(uri.toString(), paramsSlot.captured.textDocument.uri)
160+ assertEquals(normalizeFileUri( uri.toString() ), paramsSlot.captured.textDocument.uri)
181161 }
182162
183163 @Test
@@ -188,14 +168,7 @@ class TextDocumentServiceHandlerTest {
188168 every { modificationStamp } returns 123L
189169 }
190170
191- val path = mockk<Path > {
192- every { toUri() } returns uri
193- }
194-
195- val file = mockk<VirtualFile > {
196- every { this @mockk.path } returns uri.path
197- every { toNioPath() } returns path
198- }
171+ val file = createMockVirtualFile(uri)
199172
200173 val changeEvent = mockk<VFileContentChangeEvent > {
201174 every { this @mockk.file } returns file
@@ -218,7 +191,7 @@ class TextDocumentServiceHandlerTest {
218191 verify { mockTextDocumentService.didChange(capture(paramsSlot)) }
219192
220193 with (paramsSlot.captured) {
221- assertEquals(uri.toString(), textDocument.uri)
194+ assertEquals(normalizeFileUri( uri.toString() ), textDocument.uri)
222195 assertEquals(123 , textDocument.version)
223196 assertEquals(" changed content" , contentChanges[0 ].text)
224197 }
@@ -227,23 +200,22 @@ class TextDocumentServiceHandlerTest {
227200 @Test
228201 fun `didSave does not run when URI is empty` () = runTest {
229202 val document = mockk<Document >()
230- val path = mockk<Path > {
231- every { toUri() } returns URI .create(" " )
232- }
233- val file = mockk<VirtualFile > {
234- every { toNioPath() } returns path
235- }
203+ val file = createMockVirtualFile(URI .create(" " ))
236204
237- val fileDocumentManager = mockk<FileDocumentManager > {
238- every { getFile(document) } returns file
239- }
205+ mockkObject(FileUriUtil ) {
206+ every { FileUriUtil .toUriString(file) } returns null
240207
241- mockkStatic(FileDocumentManager ::class ) {
242- every { FileDocumentManager .getInstance() } returns fileDocumentManager
208+ val fileDocumentManager = mockk<FileDocumentManager > {
209+ every { getFile(document) } returns file
210+ }
243211
244- sut.beforeDocumentSaving(document)
212+ mockkStatic(FileDocumentManager ::class ) {
213+ every { FileDocumentManager .getInstance() } returns fileDocumentManager
245214
246- verify(exactly = 0 ) { mockTextDocumentService.didSave(any()) }
215+ sut.beforeDocumentSaving(document)
216+
217+ verify(exactly = 0 ) { mockTextDocumentService.didSave(any()) }
218+ }
247219 }
248220 }
249221
@@ -298,4 +270,33 @@ class TextDocumentServiceHandlerTest {
298270 verify(exactly = 0 ) { mockTextDocumentService.didChange(any()) }
299271 }
300272 }
273+
274+ private fun createMockVirtualFile (uri : URI , content : String = ""): VirtualFile {
275+ val path = mockk<Path > {
276+ every { toUri() } returns uri
277+ }
278+ val inputStream = content.byteInputStream()
279+ return mockk<VirtualFile > {
280+ every { url } returns uri.path
281+ every { toNioPath() } returns path
282+ every { isDirectory } returns false
283+ every { fileSystem } returns mockk {
284+ every { protocol } returns " file"
285+ }
286+ every { this @mockk.inputStream } returns inputStream
287+ }
288+ }
289+
290+ private fun normalizeFileUri (uri : String ): String {
291+ if (! System .getProperty(" os.name" ).lowercase().contains(" windows" )) {
292+ return uri
293+ }
294+
295+ if (! uri.startsWith(" file:///" )) {
296+ return uri
297+ }
298+
299+ val path = uri.substringAfter(" file:///" )
300+ return " file:///C:/$path "
301+ }
301302}
0 commit comments