diff --git a/app/Livewire/Server/PrivateKey/Show.php b/app/Livewire/Server/PrivateKey/Show.php index 72b9d31b02..1f35a9ec6c 100644 --- a/app/Livewire/Server/PrivateKey/Show.php +++ b/app/Livewire/Server/PrivateKey/Show.php @@ -62,7 +62,7 @@ class Show extends Component $this->server->save(); ['uptime' => $uptime, 'error' => $error] = $this->server->validateConnection(justCheckingNewKey: true); if (! $uptime) { - throw new \Exception($error); + throw new \Exception($this->unreachableMessage($error)); } }); $this->loadPrivateKeys(); @@ -113,8 +113,7 @@ class Show extends Component $this->dispatch('success', 'Server is reachable.'); $this->dispatch('refreshServerShow'); } else { - $sanitizedError = htmlspecialchars($error ?? '', ENT_QUOTES, 'UTF-8'); - $this->dispatch('error', 'Server is not reachable.

Check this documentation for further help.

Error: '.$sanitizedError); + $this->dispatch('error', $this->unreachableMessage($error)); return; } @@ -123,6 +122,13 @@ class Show extends Component } } + private function unreachableMessage(?string $error): string + { + $sanitizedError = htmlspecialchars($error ?? '', ENT_QUOTES, 'UTF-8'); + + return 'Server is not reachable.

Check this documentation for further help.

Error: '.$sanitizedError; + } + public function render() { return view('livewire.server.private-key.show'); diff --git a/app/Models/Server.php b/app/Models/Server.php index 58b1b3f0b0..31c851af99 100644 --- a/app/Models/Server.php +++ b/app/Models/Server.php @@ -2539,10 +2539,7 @@ $siteAddress { return ['uptime' => true, 'error' => null]; } catch (\Throwable $e) { - if ($justCheckingNewKey) { - return ['uptime' => false, 'error' => 'This key is not valid for this server.']; - } - if ($this->settings->is_reachable === true) { + if (! $justCheckingNewKey && $this->settings->is_reachable === true) { $this->settings->is_reachable = false; $this->settings->save(); ServerReachabilityChanged::dispatch($this); diff --git a/tests/Feature/ServerPrivateKeyDropdownTest.php b/tests/Feature/ServerPrivateKeyDropdownTest.php index a8d9aaeced..8c3da60795 100644 --- a/tests/Feature/ServerPrivateKeyDropdownTest.php +++ b/tests/Feature/ServerPrivateKeyDropdownTest.php @@ -145,3 +145,19 @@ describe('after the user switches the session team', function () { ->and($keys->pluck('id'))->toContain($this->currentPrivateKey->id); }); }); + +test('shows the SSH error when the new key cannot connect and keeps the old key', function () { + Process::fake(['*' => Process::result(errorOutput: 'root@host.docker.internal: Permission denied (publickey,password).', exitCode: 255)]); + Storage::fake('ssh-mux'); + $newKey = PrivateKey::factory()->create([ + 'team_id' => $this->team->id, + 'private_key' => PrivateKey::generateNewKeyPair('ed25519')['private_key'], + ]); + + Livewire::test(Show::class, ['server_uuid' => $this->server->uuid]) + ->call('setPrivateKey', $newKey->id) + ->assertDispatched('error', fn (string $event, array $params): bool => str_contains($params[0], 'Permission denied (publickey,password).') + && str_contains($params[0], 'https://coolify.io/docs/knowledge-base/server/openssh')); + + expect($this->server->fresh()->private_key_id)->toBe($this->currentPrivateKey->id); +});