Skip to content

Fix race condition in modal editor part singleton creation - #327123

Merged
Benjamin Christopher Simmonds (benibenj) merged 1 commit into
mainfrom
fix/modal-editor-singleton-race
Jul 23, 2026
Merged

Benjamin Christopher Simmonds (benibenj) merged 1 commit into
mainfrom
fix/modal-editor-singleton-race

Conversation

@benibenj

Copy link
Copy Markdown
Contributor

Summary

Fixes a race condition in modal editor part singleton creation identified while reviewing #326885.

EditorParts.createModalEditorPart awaited the ModalEditorPart creation (�wait this.instantiationService.createInstance(ModalEditorPart, this).create(...)) before assigning his.modalEditorPart. If createModalEditorPart was called concurrently (e.g. two callers racing to open a modal editor), both calls could pass the "reuse existing instance" check and each create its own ModalEditorPart, resulting in duplicate modal editor parts/groups and duplicate onDidAddGroup events.

Fix

  • Track the in-flight creation as a promise (modalEditorPartCreatePromise).
  • If a creation is already in flight when createModalEditorPart is called again, await that promise and apply the caller's options to the resulting singleton instance instead of starting a second creation.
  • Preserves existing option-update behavior for both the "already created" and "creation in flight" cases.

This does not include the separate stable-ID change from #326885 — that should land separately.

Testing

  • createModalEditorPart is race-proof: concurrent creation returns same singleton instance (new test in modalEditorGroup.test.ts) fires 3 concurrent createModalEditorPart() calls via Promise.all and asserts:
    • all three calls resolve to the exact same instance/group
    • only one onDidAddGroup event fires
  • Ran the full Modal Editor Group suite (42 tests) - all passing.

pm run typecheck-client - 0 errors.

createModalEditorPart awaited the ModalEditorPart creation before assigning
the singleton reference, so concurrent callers could each pass the
"already exists" check and create duplicate modal parts/groups. Track the
in-flight creation promise and have concurrent callers await and reuse it,
applying their own options to the shared instance once it resolves.

Adds a regression test that invokes createModalEditorPart concurrently via
Promise.all and asserts a single instance/group is returned and only one
group-registration event fires.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Prevents duplicate modal editor parts during concurrent singleton creation.

Changes:

  • Tracks in-flight modal editor part creation.
  • Adds concurrent singleton creation coverage.
Show a summary per file
File Description
editorParts.ts Reuses an in-flight modal creation promise.
modalEditorGroup.test.ts Tests concurrent creation and event count.

Review details

  • Files reviewed: 2/2 changed files
  • Comments generated: 2
  • Review effort level: Medium

Comment on lines +204 to +208
const [modalPart1, modalPart2, modalPart3] = await Promise.all([
parts.createModalEditorPart(),
parts.createModalEditorPart(),
parts.createModalEditorPart()
]);
Comment on lines +211 to +216
const createPromise = this.doCreateModalEditorPart(options).finally(() => {
this.modalEditorPartCreatePromise = undefined;
});
this.modalEditorPartCreatePromise = createPromise;

return createPromise;
@benibenj
Benjamin Christopher Simmonds (benibenj) merged commit b8d3a33 into main Jul 23, 2026
30 checks passed
@benibenj
Benjamin Christopher Simmonds (benibenj) deleted the fix/modal-editor-singleton-race branch July 23, 2026 13:30
@vs-code-engineering vs-code-engineering Bot added this to the 1.131.0 milestone Jul 23, 2026
@vs-code-engineering vs-code-engineering Bot locked and limited conversation to collaborators Sep 6, 2026
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants