restartSignalPath(); } private function removeSentinel(): void { $path = $this->sentinelPath(); if (is_file($path)) { @unlink($path); } } protected function setUp(): void { parent::setUp(); $this->removeSentinel(); // never inherit a stray sentinel from a prior run } protected function tearDown(): void { $this->removeSentinel(); // leave the storage dir as we found it parent::tearDown(); } public function test_request_restart_creates_the_sentinel_and_request_reports_it(): void { $deployment = app(DeploymentService::class); $this->assertFalse($deployment->restartRequested(), 'no sentinel before requesting'); $deployment->requestRestart(); $this->assertTrue(is_file($this->sentinelPath()), 'sentinel file exists on disk'); $this->assertTrue($deployment->restartRequested(), 'restartRequested() reflects the file'); $this->assertNotSame('', trim((string) file_get_contents($this->sentinelPath())), 'sentinel carries a marker'); } public function test_clear_restart_request_removes_the_sentinel(): void { $deployment = app(DeploymentService::class); $deployment->requestRestart(); $this->assertTrue($deployment->restartRequested()); $deployment->clearRestartRequest(); $this->assertFalse($deployment->restartRequested(), 'sentinel is gone after clearing'); } public function test_restart_now_writes_the_sentinel_and_sets_the_flag(): void { $this->actingAs(User::factory()->create(['must_change_password' => false])); Livewire::test(Index::class) ->call('restartNow', app(DeploymentService::class)) ->assertSet('restartRequested', true); $this->assertTrue( app(DeploymentService::class)->restartRequested(), 'the one-click action persisted the sentinel a host watcher will see', ); } }