@Test public void start_does_not_nothing_if_already_started_once() { SQProcess underTest = SQProcess.builder(A_PROCESS_ID).build(); try (TestProcess testProcess = new TestProcess()) { assertThat(underTest.start(() -> testProcess)).isTrue(); assertThat(underTest.getState()).isEqualTo(Lifecycle.State.STARTED); assertThat(underTest.start(() -> {throw new IllegalStateException();})).isFalse(); assertThat(underTest.getState()).isEqualTo(Lifecycle.State.STARTED); } }
@Test public void start_and_stop_process() { ProcessLifecycleListener listener = mock(ProcessLifecycleListener.class); SQProcess underTest = SQProcess.builder(A_PROCESS_ID) .addProcessLifecycleListener(listener) .build(); try (TestProcess testProcess = new TestProcess()) { assertThat(underTest.start(() -> testProcess)).isTrue(); assertThat(underTest.getState()).isEqualTo(Lifecycle.State.STARTED); assertThat(testProcess.isAlive()).isTrue(); assertThat(testProcess.streamsClosed).isFalse(); verify(listener).onProcessState(A_PROCESS_ID, Lifecycle.State.STARTED); testProcess.close(); // do not wait next run of watcher threads underTest.refreshState(); assertThat(underTest.getState()).isEqualTo(Lifecycle.State.STOPPED); assertThat(testProcess.isAlive()).isFalse(); assertThat(testProcess.streamsClosed).isTrue(); verify(listener).onProcessState(A_PROCESS_ID, Lifecycle.State.STOPPED); } }
@Test public void stopForcibly_stops_the_process_without_graceful_request_for_stop() { SQProcess underTest = SQProcess.builder(A_PROCESS_ID).build(); try (TestProcess testProcess = new TestProcess()) { underTest.start(() -> testProcess); underTest.stopForcibly(); assertThat(underTest.getState()).isEqualTo(Lifecycle.State.STOPPED); assertThat(testProcess.askedForStop).isFalse(); assertThat(testProcess.destroyedForcibly).isTrue(); // second execution of stopForcibly does nothing. It's still stopped. underTest.stopForcibly(); assertThat(underTest.getState()).isEqualTo(Lifecycle.State.STOPPED); } }
@Test public void process_stops_after_graceful_request_for_stop() throws Exception { ProcessLifecycleListener listener = mock(ProcessLifecycleListener.class); SQProcess underTest = SQProcess.builder(A_PROCESS_ID) .addProcessLifecycleListener(listener) .build(); try (TestProcess testProcess = new TestProcess()) { underTest.start(() -> testProcess); Thread stopperThread = new Thread(() -> underTest.stop(1, TimeUnit.HOURS)); stopperThread.start(); // thread is blocked until process stopped assertThat(stopperThread.isAlive()).isTrue(); // wait for the stopper thread to ask graceful stop while (!testProcess.askedForStop) { Thread.sleep(1L); } assertThat(underTest.getState()).isEqualTo(Lifecycle.State.STOPPING); verify(listener).onProcessState(A_PROCESS_ID, Lifecycle.State.STOPPING); // process stopped testProcess.close(); // waiting for stopper thread to detect and handle the stop stopperThread.join(); assertThat(underTest.getState()).isEqualTo(Lifecycle.State.STOPPED); verify(listener).onProcessState(A_PROCESS_ID, Lifecycle.State.STOPPED); } }
@Test public void operational_event_is_sent_once() { ProcessEventListener listener = mock(ProcessEventListener.class); SQProcess underTest = SQProcess.builder(A_PROCESS_ID) .addEventListener(listener) .build(); try (TestProcess testProcess = new TestProcess()) { underTest.start(() -> testProcess); testProcess.operational = true; underTest.refreshState(); verify(listener).onProcessEvent(A_PROCESS_ID, ProcessEventListener.Type.OPERATIONAL); // second run underTest.refreshState(); verifyNoMoreInteractions(listener); } }
@Test public void process_is_stopped_forcibly_if_graceful_stop_is_too_long() throws Exception { ProcessLifecycleListener listener = mock(ProcessLifecycleListener.class); SQProcess underTest = SQProcess.builder(A_PROCESS_ID) .addProcessLifecycleListener(listener) .build(); try (TestProcess testProcess = new TestProcess()) { underTest.start(() -> testProcess); underTest.stop(1L, TimeUnit.MILLISECONDS); testProcess.waitFor(); assertThat(testProcess.askedForStop).isTrue(); assertThat(testProcess.destroyedForcibly).isTrue(); assertThat(testProcess.isAlive()).isFalse(); assertThat(underTest.getState()).isEqualTo(Lifecycle.State.STOPPED); verify(listener).onProcessState(A_PROCESS_ID, Lifecycle.State.STOPPED); } }
@Test public void send_event_when_process_is_operational() { ProcessEventListener listener = mock(ProcessEventListener.class); SQProcess underTest = SQProcess.builder(A_PROCESS_ID) .addEventListener(listener) .build(); try (TestProcess testProcess = new TestProcess()) { underTest.start(() -> testProcess); testProcess.operational = true; underTest.refreshState(); verify(listener).onProcessEvent(A_PROCESS_ID, ProcessEventListener.Type.OPERATIONAL); } verifyNoMoreInteractions(listener); }