[split mode] IJPL-253269 IJ-CR-219485 Wait until backend assigns an id to document before binding editors. Otherwise a race can cause creating a new model for the document

(cherry picked from commit d9e5922e0ba470f96b9f1dc32f4ba29bf5be7f83)

GitOrigin-RevId: 0277d9c5d406f5f327af636381270ef0eb633cec
This commit is contained in:
Nikita Katkov
2026-08-26 00:45:38 +00:00
committed by intellij-monorepo-bot
parent 25cd511391
commit 19e200a734
2 changed files with 12 additions and 6 deletions
@@ -36,13 +36,13 @@ fun Document.bindToBackend(
val builder = BackendDocumentBindBuilder().apply(builder)
val backendDocumentIdProvider = builder.backendDocumentIdProvider
val documentBound = if (backendDocumentIdProvider != null) {
bindToBackend(backendDocumentIdProvider, builder.onBindingDispose)
bindToBackend(backendDocumentIdProvider, builder.onBindingDispose, builder.bindEditors)
}
else {
true
}
if (documentBound && builder.bindEditors) {
if (documentBound && builder.bindEditors && backendDocumentIdProvider == null) {
// mark the document, so future editors will be bind
bindEditorsToBackend()
// bind current editors (since they might be created during backends' documents initialization)
@@ -90,11 +90,12 @@ private fun Document.bindCurrentEditors() {
private suspend fun Document.bindToBackend(
backendDocumentIdProvider: suspend (FrontendDocumentId) -> BackendDocumentId?,
onBindingDispose: (() -> Unit)?,
bindEditors: Boolean,
): Boolean {
val frontendDocument = this
val frontendDocumentId = FrontendDocumentId(UID.random())
val registry = FrontendDocumentIdRegistry.EP_NAME.extensionList.firstOrNull()
registry?.registerFrontendDocumentId(frontendDocumentId, frontendDocument, onBindingDispose)
registry?.registerFrontendDocumentId(frontendDocumentId, frontendDocument, onBindingDispose, bindEditors)
var backendDocumentId: BackendDocumentId? = null
try {
backendDocumentId = backendDocumentIdProvider(frontendDocumentId)
@@ -164,7 +165,12 @@ interface FrontendDocumentIdRegistry {
// TODO: should we deal with session here,
// so that it will be registered for session not not app level?
fun registerFrontendDocumentId(frontendDocumentId: FrontendDocumentId, frontendDocument: Document, onBindingDispose: (() -> Unit)?)
fun registerFrontendDocumentId(
frontendDocumentId: FrontendDocumentId,
frontendDocument: Document,
onBindingDispose: (() -> Unit)?,
bindEditors: Boolean,
)
fun unregisterFrontendDocumentId(frontendDocumentId: FrontendDocumentId)
}
@@ -13,7 +13,7 @@ import org.jetbrains.annotations.ApiStatus
*/
// TODO: it is not ok to attach Document to fileType
@ApiStatus.Internal
internal fun Document.bindEditorsToBackend() {
fun Document.bindEditorsToBackend() {
this.putUserData(BIND_DOCUMENT_EDITORS, true)
}
@@ -34,4 +34,4 @@ fun Editor.shouldBindToBackend(): Boolean {
}
@ApiStatus.Internal
private val BIND_DOCUMENT_EDITORS: Key<Boolean> = Key<Boolean>("bindDocumentEditors")
private val BIND_DOCUMENT_EDITORS: Key<Boolean> = Key<Boolean>("bindDocumentEditors")