@@ -356,7 +356,7 @@ package actor SourceKitLSPServer {
356
356
357
357
// This should be created as soon as we receive an open call, even if the document
358
358
// isn't yet ready.
359
- guard let languageService = workspace. documentService. value [ doc] else {
359
+ guard let languageService = workspace. documentService ( for : doc) else {
360
360
return
361
361
}
362
362
@@ -376,7 +376,7 @@ package actor SourceKitLSPServer {
376
376
guard let workspace = await self . workspaceForDocument ( uri: request. textDocument. uri) else {
377
377
throw ResponseError . workspaceNotOpen ( request. textDocument. uri)
378
378
}
379
- guard let languageService = workspace. documentService. value [ doc] else {
379
+ guard let languageService = workspace. documentService ( for : doc) else {
380
380
throw ResponseError . unknown ( " No language service for ' \( request. textDocument. uri) ' found " )
381
381
}
382
382
return try await requestHandler ( request, workspace, languageService)
@@ -399,7 +399,7 @@ package actor SourceKitLSPServer {
399
399
guard let workspace = await self . workspaceForDocument ( uri: documentUri) else {
400
400
continue
401
401
}
402
- guard workspace. documentService. value [ documentUri] === languageService else {
402
+ guard workspace. documentService ( for : documentUri) === languageService else {
403
403
continue
404
404
}
405
405
guard let snapshot = try ? self . documentManager. latestSnapshot ( documentUri) else {
@@ -517,7 +517,7 @@ package actor SourceKitLSPServer {
517
517
_ language: Language ,
518
518
in workspace: Workspace
519
519
) async -> LanguageService ? {
520
- if let service = workspace. documentService. value [ uri] {
520
+ if let service = workspace. documentService ( for : uri) {
521
521
return service
522
522
}
523
523
@@ -535,17 +535,7 @@ package actor SourceKitLSPServer {
535
535
"""
536
536
)
537
537
538
- return workspace. documentService. withLock { documentService in
539
- if let concurrentlySetService = documentService [ uri] {
540
- // Since we await the construction of `service`, another call to this
541
- // function might have happened and raced us, setting
542
- // `workspace.documentServices[uri]`. If this is the case, return the
543
- // existing value and discard the service that we just retrieved.
544
- return concurrentlySetService
545
- }
546
- documentService [ uri] = service
547
- return service
548
- }
538
+ return workspace. documentService ( for: uri, newLanguageService: service)
549
539
}
550
540
}
551
541
@@ -732,6 +722,8 @@ extension SourceKitLSPServer: MessageHandler {
732
722
await request. reply { try await executeCommand ( request. params) }
733
723
case let request as RequestAndReply < FoldingRangeRequest > :
734
724
await self . handleRequest ( for: request, requestHandler: self . foldingRange)
725
+ case let request as RequestAndReply < GetReferenceDocumentRequest > :
726
+ await request. reply { try await getReferenceDocument ( request. params) }
735
727
case let request as RequestAndReply < HoverRequest > :
736
728
await self . handleRequest ( for: request, requestHandler: self . hover)
737
729
case let request as RequestAndReply < ImplementationRequest > :
@@ -803,7 +795,7 @@ extension SourceKitLSPServer: BuildSystemDelegate {
803
795
continue
804
796
}
805
797
806
- guard let service = await self . workspaceForDocument ( uri: uri) ? . documentService. value [ uri] else {
798
+ guard let service = await self . workspaceForDocument ( uri: uri) ? . documentService ( for : uri) else {
807
799
continue
808
800
}
809
801
@@ -827,7 +819,7 @@ extension SourceKitLSPServer: BuildSystemDelegate {
827
819
}
828
820
for uri in self . affectedOpenDocumentsForChangeSet ( changedFilesForWorkspace, self . documentManager) {
829
821
logger. log ( " Dependencies updated for opened file \( uri. forLogging) " )
830
- if let service = workspace. documentService. value [ uri] {
822
+ if let service = workspace. documentService ( for : uri) {
831
823
await service. documentDependenciesUpdated ( uri)
832
824
}
833
825
}
@@ -962,6 +954,8 @@ extension SourceKitLSPServer {
962
954
//
963
955
// The below is a workaround for the vscode-swift extension since it cannot set client capabilities.
964
956
// It passes "workspace/peekDocuments" through the `initializationOptions`.
957
+ //
958
+ // Similarly, for "workspace/getReferenceDocument".
965
959
var clientCapabilities = req. capabilities
966
960
if case . dictionary( let initializationOptions) = req. initializationOptions {
967
961
if let peekDocuments = initializationOptions [ " workspace/peekDocuments " ] {
@@ -973,6 +967,15 @@ extension SourceKitLSPServer {
973
967
}
974
968
}
975
969
970
+ if let getReferenceDocument = initializationOptions [ " workspace/getReferenceDocument " ] {
971
+ if case . dictionary( var experimentalCapabilities) = clientCapabilities. experimental {
972
+ experimentalCapabilities [ " workspace/getReferenceDocument " ] = getReferenceDocument
973
+ clientCapabilities. experimental = . dictionary( experimentalCapabilities)
974
+ } else {
975
+ clientCapabilities. experimental = . dictionary( [ " workspace/getReferenceDocument " : getReferenceDocument] )
976
+ }
977
+ }
978
+
976
979
// The client announces what CodeLenses it supports, and the LSP will only return
977
980
// ones found in the supportedCommands dictionary.
978
981
if let codeLens = initializationOptions [ " textDocument/codeLens " ] ,
@@ -1139,6 +1142,7 @@ extension SourceKitLSPServer {
1139
1142
" workspace/tests " : . dictionary( [ " version " : . int( 2 ) ] ) ,
1140
1143
" textDocument/tests " : . dictionary( [ " version " : . int( 2 ) ] ) ,
1141
1144
" workspace/triggerReindex " : . dictionary( [ " version " : . int( 1 ) ] ) ,
1145
+ " workspace/getReferenceDocument " : . dictionary( [ " version " : . int( 1 ) ] ) ,
1142
1146
] )
1143
1147
)
1144
1148
}
@@ -1338,7 +1342,7 @@ extension SourceKitLSPServer {
1338
1342
)
1339
1343
return
1340
1344
}
1341
- await workspace. documentService. value [ uri] ? . reopenDocument ( notification)
1345
+ await workspace. documentService ( for : uri) ? . reopenDocument ( notification)
1342
1346
}
1343
1347
1344
1348
func closeDocument( _ notification: DidCloseTextDocumentNotification , workspace: Workspace ) async {
@@ -1352,7 +1356,7 @@ extension SourceKitLSPServer {
1352
1356
1353
1357
await workspace. buildSystemManager. unregisterForChangeNotifications ( for: uri)
1354
1358
1355
- await workspace. documentService. value [ uri] ? . closeDocument ( notification)
1359
+ await workspace. documentService ( for : uri) ? . closeDocument ( notification)
1356
1360
}
1357
1361
1358
1362
func changeDocument( _ notification: DidChangeTextDocumentNotification ) async {
@@ -1378,7 +1382,7 @@ extension SourceKitLSPServer {
1378
1382
// Already logged failure
1379
1383
return
1380
1384
}
1381
- await workspace. documentService. value [ uri] ? . changeDocument (
1385
+ await workspace. documentService ( for : uri) ? . changeDocument (
1382
1386
notification,
1383
1387
preEditSnapshot: preEditSnapshot,
1384
1388
postEditSnapshot: postEditSnapshot,
@@ -1641,7 +1645,7 @@ extension SourceKitLSPServer {
1641
1645
guard let workspace = await workspaceForDocument ( uri: uri) else {
1642
1646
throw ResponseError . workspaceNotOpen ( uri)
1643
1647
}
1644
- guard let languageService = workspace. documentService. value [ uri] else {
1648
+ guard let languageService = workspace. documentService ( for : uri) else {
1645
1649
return nil
1646
1650
}
1647
1651
@@ -1652,6 +1656,21 @@ extension SourceKitLSPServer {
1652
1656
return try await languageService. executeCommand ( executeCommand)
1653
1657
}
1654
1658
1659
+ func getReferenceDocument( _ req: GetReferenceDocumentRequest ) async throws -> GetReferenceDocumentResponse {
1660
+ let referenceDocumentURL = try ReferenceDocumentURL ( from: req. uri)
1661
+ let sourceFileURI = referenceDocumentURL. sourceDocument ( )
1662
+
1663
+ guard let workspace = await workspaceForDocument ( uri: sourceFileURI) else {
1664
+ throw ResponseError . workspaceNotOpen ( sourceFileURI)
1665
+ }
1666
+
1667
+ guard let languageService = workspace. documentService ( for: sourceFileURI) else {
1668
+ throw ResponseError . unknown ( " No Language Service for URI: \( sourceFileURI) " )
1669
+ }
1670
+
1671
+ return try await languageService. getReferenceDocument ( req)
1672
+ }
1673
+
1655
1674
func codeAction(
1656
1675
_ req: CodeActionRequest ,
1657
1676
workspace: Workspace ,
0 commit comments