diff --git a/platform/completion/common/src/protocol/RpcLookupElementEvent.kt b/platform/completion/common/src/protocol/RpcLookupElementEvent.kt index 195b14d4a7d4..35fb75cc8bfd 100644 --- a/platform/completion/common/src/protocol/RpcLookupElementEvent.kt +++ b/platform/completion/common/src/protocol/RpcLookupElementEvent.kt @@ -42,14 +42,23 @@ sealed interface RpcLookupElementEvent { /** * the lookup is closed with completion + * + * [requestId] is the request the chosen item belongs to, and it is what the backend must resolve + * [selectedItemId] against: items live in a per-request storage + * (`BackendCompletionRequestSession.findCompletionResult`), and the mirror lookup's arranger can still belong to an + * older request when this event is handled (IJPL-252099 — the frontend swaps a stale-seeded request for a fresh one + * right before the accept). Resolving against the arranger's own session instead would fail to find the item and + * insert one carrying a shorter prefix matcher, leaving the leading typed characters in the document. */ @Serializable data class ItemSelected( val projectId: ProjectId, + val requestId: RpcCompletionRequestId, val selectedItemId: RpcCompletionItemId? = null, ) : RpcLookupElementEvent { override fun toString(): String = buildToString("ItemSelected") { field("projectId", projectId) + field("requestId", requestId) fieldWithNullDefault("selectedItemId", selectedItemId) } }