diff options
| author | vincent van beek <vincent@vlogic.nl> | 2026-04-15 16:19:02 +0200 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2026-04-15 16:19:02 +0200 |
| commit | 11e355321db20b70c76c35b6e8fc36dbb9d97fc6 (patch) | |
| tree | f12b8c8c2b6a642b315f2e4a7e54274bbcdb60be /opendc-web/opendc-web-server/src/test/java/org | |
| parent | 3e52cd36bed9455105f4a8c3d83ec805c1fb7b70 (diff) | |
add a job report to the scenario overview with details and time data (#406)
* add a job report to the scenario overview with details and time data
* create Report data class
Diffstat (limited to 'opendc-web/opendc-web-server/src/test/java/org')
2 files changed, 70 insertions, 15 deletions
diff --git a/opendc-web/opendc-web-server/src/test/java/org/opendc/web/server/rest/runner/JobResourceTest.java b/opendc-web/opendc-web-server/src/test/java/org/opendc/web/server/rest/runner/JobResourceTest.java index 09f60c0a..b0adfc77 100644 --- a/opendc-web/opendc-web-server/src/test/java/org/opendc/web/server/rest/runner/JobResourceTest.java +++ b/opendc-web/opendc-web-server/src/test/java/org/opendc/web/server/rest/runner/JobResourceTest.java @@ -98,7 +98,7 @@ public final class JobResourceTest { user = "test_user_1", roles = {"runner"}) public void testUpdateNonExistent() { - given().body(new org.opendc.web.proto.runner.Job.Update(JobState.PENDING, 0, null)) + given().body(new org.opendc.web.proto.runner.Job.Update(JobState.PENDING, 0, null, null)) .contentType(ContentType.JSON) .when() .post("/0") @@ -115,7 +115,7 @@ public final class JobResourceTest { user = "test_user_1", roles = {"runner"}) public void testUpdateState() { - given().body(new org.opendc.web.proto.runner.Job.Update(JobState.CLAIMED, 0, null)) + given().body(new org.opendc.web.proto.runner.Job.Update(JobState.CLAIMED, 0, null, null)) .contentType(ContentType.JSON) .when() .post("/2") @@ -141,4 +141,26 @@ public final class JobResourceTest { .statusCode(400) .contentType(ContentType.JSON); } + + /** + * Test that tries to get the report for a non-existent job. + */ + @Test + @TestSecurity( + user = "test_user_1", + roles = {"runner"}) + public void testGetReportNonExistent() { + given().get("/0/report").then().statusCode(404); + } + + /** + * Test that tries to get the report for a job with no report (returns empty map). + */ + @Test + @TestSecurity( + user = "test_user_1", + roles = {"runner"}) + public void testGetReportEmpty() { + given().get("/1/report").then().statusCode(200).contentType(ContentType.JSON); + } } diff --git a/opendc-web/opendc-web-server/src/test/java/org/opendc/web/server/service/JobServiceTest.java b/opendc-web/opendc-web-server/src/test/java/org/opendc/web/server/service/JobServiceTest.java index f6d871c0..8f6810a9 100644 --- a/opendc-web/opendc-web-server/src/test/java/org/opendc/web/server/service/JobServiceTest.java +++ b/opendc-web/opendc-web-server/src/test/java/org/opendc/web/server/service/JobServiceTest.java @@ -61,7 +61,7 @@ public class JobServiceTest { Job job = new Job(null, "test", Instant.now(), 1); job.state = JobState.RUNNING; - assertThrows(IllegalArgumentException.class, () -> service.updateJob(job, JobState.CLAIMED, 0, null)); + assertThrows(IllegalArgumentException.class, () -> service.updateJob(job, JobState.CLAIMED, 0, null, null)); Mockito.verifyNoInteractions(mockAccountingService); } @@ -73,11 +73,11 @@ public class JobServiceTest { Mockito.when(mockAccountingService.consumeSimulationBudget(any(), anyInt())) .thenReturn(true); - Mockito.doReturn(true).when(job).updateAtomically(any(), any(), anyInt(), any()); + Mockito.doReturn(true).when(job).updateAtomically(any(), any(), any(), anyInt(), any(), any()); - service.updateJob(job, JobState.RUNNING, 0, null); + service.updateJob(job, JobState.RUNNING, 0, null, null); - Mockito.verify(job).updateAtomically(eq(JobState.FAILED), any(), anyInt(), any()); + Mockito.verify(job).updateAtomically(eq(JobState.FAILED), any(), any(), anyInt(), any(), any()); } @Test @@ -87,11 +87,11 @@ public class JobServiceTest { Mockito.when(mockAccountingService.consumeSimulationBudget(any(), anyInt())) .thenReturn(true); - Mockito.doReturn(true).when(job).updateAtomically(any(), any(), anyInt(), any()); + Mockito.doReturn(true).when(job).updateAtomically(any(), any(), any(), anyInt(), any(), any()); - service.updateJob(job, JobState.FINISHED, 0, null); + service.updateJob(job, JobState.FINISHED, 0, null, null); - Mockito.verify(job).updateAtomically(eq(JobState.FINISHED), any(), anyInt(), any()); + Mockito.verify(job).updateAtomically(eq(JobState.FINISHED), any(), any(), anyInt(), any(), any()); } @Test @@ -101,11 +101,11 @@ public class JobServiceTest { Mockito.when(mockAccountingService.consumeSimulationBudget(any(), anyInt())) .thenReturn(false); - Mockito.doReturn(true).when(job).updateAtomically(any(), any(), anyInt(), any()); + Mockito.doReturn(true).when(job).updateAtomically(any(), any(), any(), anyInt(), any(), any()); - service.updateJob(job, JobState.FINISHED, 0, null); + service.updateJob(job, JobState.FINISHED, 0, null, null); - Mockito.verify(job).updateAtomically(eq(JobState.FINISHED), any(), anyInt(), any()); + Mockito.verify(job).updateAtomically(eq(JobState.FINISHED), any(), any(), anyInt(), any(), any()); } @Test @@ -115,10 +115,43 @@ public class JobServiceTest { Mockito.when(mockAccountingService.consumeSimulationBudget(any(), anyInt())) .thenReturn(false); - Mockito.doReturn(false).when(job).updateAtomically(any(), any(), anyInt(), any()); + Mockito.doReturn(false).when(job).updateAtomically(any(), any(), any(), anyInt(), any(), any()); - assertThrows(IllegalStateException.class, () -> service.updateJob(job, JobState.FINISHED, 0, null)); + assertThrows(IllegalStateException.class, () -> service.updateJob(job, JobState.FINISHED, 0, null, null)); - Mockito.verify(job).updateAtomically(eq(JobState.FINISHED), any(), anyInt(), any()); + Mockito.verify(job).updateAtomically(eq(JobState.FINISHED), any(), any(), anyInt(), any(), any()); + } + + @Test + public void testStartedAtSetOnFirstTransitionToRunning() { + Job job = Mockito.spy(new Job(null, "test", Instant.now(), 1)); + job.state = JobState.CLAIMED; + + Mockito.when(mockAccountingService.consumeSimulationBudget(any(), anyInt())) + .thenReturn(false); + Mockito.doReturn(true).when(job).updateAtomically(any(), any(), any(), anyInt(), any(), any()); + + service.updateJob(job, JobState.RUNNING, 0, null, null); + + // startedAt should be set (non-null) when transitioning to RUNNING for the first time + Mockito.verify(job).updateAtomically(eq(JobState.RUNNING), any(), Mockito.notNull(), anyInt(), any(), any()); + } + + @Test + public void testStartedAtNotOverriddenWhenAlreadyRunning() { + Job job = Mockito.spy(new Job(null, "test", Instant.now(), 1)); + job.state = JobState.RUNNING; + Instant originalStartedAt = Instant.now().minusSeconds(60); + job.startedAt = originalStartedAt; + + Mockito.when(mockAccountingService.consumeSimulationBudget(any(), anyInt())) + .thenReturn(false); + Mockito.doReturn(true).when(job).updateAtomically(any(), any(), any(), anyInt(), any(), any()); + + service.updateJob(job, JobState.RUNNING, 30, null, null); + + // startedAt should remain the original value (not reset) + Mockito.verify(job) + .updateAtomically(eq(JobState.RUNNING), any(), eq(originalStartedAt), anyInt(), any(), any()); } } |
