Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit 3566334

Browse files
Fix multiple clients launching with running backend
1 parent 01dedfd commit 3566334

File tree

3 files changed

+37
-15
lines changed

3 files changed

+37
-15
lines changed

‎CHANGELOG.md‎

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,10 @@
44

55
## Unreleased
66

7+
### Fixed
8+
9+
- Multiple clients being launched when a backend was already running.
10+
711
## 2.11.5 - 2024年05月06日
812

913
### Added

‎gradle.properties‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
pluginGroup=com.coder.gateway
44
pluginName=coder-gateway
55
# SemVer format -> https://semver.org
6-
pluginVersion=2.11.5
6+
pluginVersion=2.11.6
77
# See https://plugins.jetbrains.com/docs/intellij/build-number-ranges.html
88
# for insight into build numbers and IntelliJ Platform versions.
99
pluginSinceBuild=233.6745

‎src/main/kotlin/com/coder/gateway/CoderRemoteConnectionHandle.kt‎

Lines changed: 32 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -145,7 +145,7 @@ class CoderRemoteConnectionHandle {
145145
setupCommand: String,
146146
ignoreSetupFailure: Boolean,
147147
timeout: Duration = Duration.ofMinutes(10),
148-
): Unit {
148+
) {
149149
workspace.lastOpened = localTimeFormatter.format(LocalDateTime.now())
150150

151151
// This establishes an SSH connection to a remote worker binary.
@@ -168,6 +168,7 @@ class CoderRemoteConnectionHandle {
168168
this.setup(workspace, indicator, setupCommand, ignoreSetupFailure)
169169

170170
// Wait for the IDE to come up.
171+
indicator.text = "Waiting for ${workspace.ideName} backend..."
171172
var status: UnattendedHostStatus? = null
172173
val remoteProjectPath = accessor.makeRemotePath(ShellArgument.PlainText(workspace.projectPath))
173174
val logsDir = accessor.getLogsDir(workspace.ideProductCode.productCode, remoteProjectPath)
@@ -374,7 +375,8 @@ class CoderRemoteConnectionHandle {
374375
}
375376

376377
/**
377-
* Ensure the backend is started. Link is null if not ready to join.
378+
* Ensure the backend is started. Status and/or links may be null if the
379+
* backend has not started.
378380
*/
379381
private suspend fun ensureIDEBackend(
380382
workspace: WorkspaceProjectIDE,
@@ -385,23 +387,39 @@ class CoderRemoteConnectionHandle {
385387
lifetime: LifetimeDefinition,
386388
currentStatus: UnattendedHostStatus?,
387389
): UnattendedHostStatus? {
390+
val details = "${workspace.hostname}:${ideDir.toRawString()}, project=${remoteProjectPath.toRawString()}"
388391
return try {
389-
// Start the backend if not running.
390-
val currentPid =currentStatus?.appPid
391-
if (currentPid ==null||!accessor.isPidAlive(currentPid.toInt())) {
392-
logger.info("Starting ${workspace.ideName} backend from ${workspace.hostname}:${ideDir.toRawString()}, project=${remoteProjectPath.toRawString()}, logs=${logsDir.toRawString()}")
393-
// This appears to be idempotent.
394-
accessor.startHostIdeInBackgroundAndDetach(lifetime, ideDir, remoteProjectPath, logsDir)
395-
} elseif (!currentStatus.joinLink.isNullOrBlank()) {
396-
// We already have a valid join link.
392+
if (currentStatus?.appPid !=null&&
393+
!currentStatus.joinLink.isNullOrBlank() &&
394+
accessor.isPidAlive(currentStatus.appPid.toInt())
395+
) {
396+
// If the PID is alive, assume the join link we have is still
397+
// valid. The join link seems to change even if it is the same
398+
// backend running, so if we always fetched the link the client
399+
// would relaunch over and over.
397400
return currentStatus
398401
}
399-
// Get new PID and join link.
402+
403+
// See if there is already a backend running. Weirdly, there is
404+
// always a PID, even if there is no backend running, and
405+
// backendUnresponsive is always false, but the links are null so
406+
// hopefully that is an accurate indicator that the IDE is up.
400407
val status = accessor.getHostIdeStatus(ideDir, remoteProjectPath)
401-
logger.info("Got ${workspace.ideName} status from ${workspace.hostname}:${ideDir.toRawString()}, pid=${status.appPid} project=${remoteProjectPath.toRawString()} joinLink=${status.joinLink}")
402-
status
408+
if (!status.joinLink.isNullOrBlank()) {
409+
logger.info("Found existing ${workspace.ideName} backend on $details")
410+
return status
411+
}
412+
413+
// Otherwise, spawn a new backend. This does not seem to spawn a
414+
// second backend if one is already running, yet it does somehow
415+
// cause a second client to launch. So only run this if we are
416+
// really sure we have to launch a new backend.
417+
logger.info("Starting ${workspace.ideName} backend on $details")
418+
accessor.startHostIdeInBackgroundAndDetach(lifetime, ideDir, remoteProjectPath, logsDir)
419+
// Get the newly spawned PID and join link.
420+
return accessor.getHostIdeStatus(ideDir, remoteProjectPath)
403421
} catch (ex: Exception) {
404-
logger.info("Failed to get ${workspace.ideName} status from ${workspace.hostname}:${ideDir.toRawString()}, project=${remoteProjectPath.toRawString()}", ex)
422+
logger.info("Failed to get ${workspace.ideName} status from $details", ex)
405423
currentStatus
406424
}
407425
}

0 commit comments

Comments
(0)

AltStyle によって変換されたページ (->オリジナル) /