use of io.temporal.client.WorkflowOptions in project sdk-java by temporalio.
the class TestWorkflowEnvironmentSleepTest method timeskippingCanBeDisabled.
@Test
public void timeskippingCanBeDisabled() throws TimeoutException {
// Use a differently configured TestWorkflowEnvironment
tearDown();
setUp(TestEnvironmentOptions.newBuilder().setUseTimeskipping(false).build());
WorkflowOptions workflowAOptions = WorkflowOptions.newBuilder().setTaskQueue(WORKFLOW_TASK_QUEUE).setWorkflowExecutionTimeout(Duration.ofMinutes(30)).build();
WorkflowStub stubA = client.newUntypedWorkflowStub("ConfigurableSleepWorkflow", workflowAOptions);
// The workflow sleeps for 10 minutes - we'll wait for significantly less than that to verify
// that timeskipping can be disabled. Unfortunately there's tension between this assertion's
// false positive rate and how long it takes.
long durationToSleep = Duration.ofMinutes(10).toMillis();
Duration durationToWait = Duration.ofSeconds(1);
stubA.start(durationToSleep);
WorkflowServiceException e = Assert.assertThrows(WorkflowServiceException.class, () -> stubA.getResult(durationToWait.toMillis(), TimeUnit.MILLISECONDS, Void.class));
Assert.assertNotNull(e.getCause());
Assert.assertEquals(io.grpc.StatusRuntimeException.class, e.getCause().getClass());
Assert.assertEquals(Status.Code.DEADLINE_EXCEEDED, ((io.grpc.StatusRuntimeException) e.getCause()).getStatus().getCode());
// With timeskipping off, a workflow that doesn't sleep for very long should still finish
WorkflowStub stubB = client.newUntypedWorkflowStub("ConfigurableSleepWorkflow", workflowAOptions);
WorkflowExecution executionB = stubB.start(Duration.ZERO);
stubB.getResult(durationToWait.toMillis(), TimeUnit.MILLISECONDS, Void.class);
}
use of io.temporal.client.WorkflowOptions in project sdk-java by temporalio.
the class TestWorkflowEnvironmentSleepTest method timeskippingWorksForBothTypesOfUntypedStubs.
@Test
public void timeskippingWorksForBothTypesOfUntypedStubs() {
WorkflowOptions workflowAOptions = WorkflowOptions.newBuilder().setTaskQueue(WORKFLOW_TASK_QUEUE).setWorkflowExecutionTimeout(Duration.ofMinutes(30)).build();
WorkflowStub stubA = client.newUntypedWorkflowStub("ConfigurableSleepWorkflow", workflowAOptions);
// The workflow sleeps for 10 minutes, which will take less than 10 seconds if timeskipping
// works
long durationToSleep = Duration.ofMinutes(10).toMillis();
Duration durationToWait = Duration.ofSeconds(10);
stubA.start(durationToSleep);
waitForWorkflow(stubA, "newUntypedStubWithOptions", durationToWait);
// Now use one stub to start the workflow and create another stub using its WorkflowExecution.
// This simulates the scenario where someone stored a WorkflowExecution in their database,
// looked it up, and wants to check status.
WorkflowStub stubB = client.newUntypedWorkflowStub("ConfigurableSleepWorkflow", workflowAOptions);
WorkflowExecution executionB = stubB.start(durationToSleep);
WorkflowStub stubBPrime = client.newUntypedWorkflowStub(executionB, Optional.empty());
waitForWorkflow(stubBPrime, "newUntypedStubForWorkflowExecution", durationToWait);
}
use of io.temporal.client.WorkflowOptions in project sdk-java by temporalio.
the class TestWorkflowEnvironmentSleepTest method timeoutDoesNotBlockTimer.
/**
* The test service skips ahead for timers, but (correctly) does not skip ahead for timeouts. We
* used to have a bug that's best explained by example.
*
* <p>Start workflow A with an execution timeout of T. Start workflow B that sleeps for X, which
* is after T. This will leave SelfAdvancingTimerImpl's internal task queue as follows:
*
* <pre>
* [@ now+T] workflow execution timeout, canceled = true
* [@ now+X] fire timer, canceled = false
* </pre>
*
* <p>The test service will let real-time pass until T, then skip time to T+X. This blocks all
* forward progress for however long X is.
*
* <p>If you're thinking "That's silly - the first task is canceled, it should obviously be
* skipped!" then congratulations, you identified the bug and the fix!
*/
@Test
public void timeoutDoesNotBlockTimer() {
// This is T from the example
Duration workflowExecutionTimeout = Duration.ofMinutes(5);
// This is X from the example.
Duration sleepDuration = workflowExecutionTimeout.multipliedBy(2);
// This test verifies time-skipping by waiting a small amount of real time for the workflows to
// complete. In bug-land, they wouldn't complete on time.
Duration howLongWeWaitForFutures = Duration.ofSeconds(5);
WorkflowOptions workflowAOptions = WorkflowOptions.newBuilder().setTaskQueue(WORKFLOW_TASK_QUEUE).setWorkflowExecutionTimeout(workflowExecutionTimeout).build();
WorkflowStub workflowAStub = client.newUntypedWorkflowStub("ConfigurableSleepWorkflow", workflowAOptions);
// workflowA completes immediately, even in bug-land
workflowAStub.start(0);
waitForWorkflow(workflowAStub, "A", howLongWeWaitForFutures);
// Workflow B's execution timeout needs to be longer than its sleep.
WorkflowOptions workflowBOptions = WorkflowOptions.newBuilder().setTaskQueue(WORKFLOW_TASK_QUEUE).setWorkflowExecutionTimeout(sleepDuration.multipliedBy(2)).build();
WorkflowStub workflowBStub = client.newUntypedWorkflowStub("ConfigurableSleepWorkflow", workflowBOptions);
// In bug land, workflow B wouldn't complete until workflowExecutionTimeout real seconds from
// now (minus epsilon). Without the bug, it should complete immediately.
workflowBStub.start(sleepDuration.toMillis());
waitForWorkflow(workflowBStub, "B", howLongWeWaitForFutures);
}
use of io.temporal.client.WorkflowOptions in project sdk-java by temporalio.
the class SignalAndQueryListenerTest method testSignalAndQueryListener.
@Test
public void testSignalAndQueryListener() {
WorkflowOptions options = SDKTestOptions.newWorkflowOptionsWithTimeouts(testWorkflowRule.getTaskQueue());
TestSignalAndQueryListenerWorkflow stub = testWorkflowRule.newWorkflowStubTimeoutOptions(TestSignalAndQueryListenerWorkflow.class);
WorkflowExecution execution = WorkflowClient.start(stub::execute);
SignalQueryBase signalStub = testWorkflowRule.getWorkflowClient().newWorkflowStub(SignalQueryBase.class, execution.getWorkflowId());
// Send signals before listener is registered to test signal buffering
signalStub.signal("a");
signalStub.signal("b");
try {
signalStub.getSignal();
// as not listener is not registered yet
Assert.fail("unreachable");
} catch (WorkflowQueryException e) {
Assert.assertTrue(e.getCause().getMessage().contains("Unknown query type: getSignal"));
}
stub.register();
while (true) {
try {
Assert.assertEquals("a, b", signalStub.getSignal());
break;
} catch (WorkflowQueryException e) {
Assert.assertTrue(e.getMessage().contains("Unknown query type: getSignal"));
}
}
testWorkflowRule.getInterceptor(TracingWorkerInterceptor.class).setExpected("interceptExecuteWorkflow " + SDKTestWorkflowRule.UUID_REGEXP, "registerSignalHandlers register", "newThread workflow-method", "await await", "handleSignal register", "registerQuery getSignal", "registerSignalHandlers signal", "handleSignal signal", "handleSignal signal", "handleQuery getSignal", "query getSignal");
}
use of io.temporal.client.WorkflowOptions in project sdk-java by temporalio.
the class SignalExternalWorkflowFailureTest method testTerminateWorkflowSignalError.
@Test
public void testTerminateWorkflowSignalError() throws InterruptedException {
WorkflowOptions options = WorkflowOptions.newBuilder().setTaskQueue(testWorkflowRule.getTaskQueue()).setWorkflowId(WORKFLOW_ID).build();
TestSignaledWorkflow terminatedWorkflow = testWorkflowRule.getWorkflowClient().newWorkflowStub(TestSignaledWorkflow.class, options);
WorkflowClient.start(terminatedWorkflow::execute);
TestWorkflowReturnString signalingWorkflow = testWorkflowRule.newWorkflowStub(TestWorkflowReturnString.class);
WorkflowClient.start(signalingWorkflow::execute);
// Wait for terminatedWorkflow to start
latch.await();
WorkflowStub stub = WorkflowStub.fromTyped(terminatedWorkflow);
stub.terminate("Mock terminating workflow");
// Wait for signalingWorkflow to start and terminatedWorkflow to terminate
latch2.countDown();
WorkflowStub workflowStub2 = WorkflowStub.fromTyped(signalingWorkflow);
assertEquals(workflowStub2.getResult(String.class), "Success!");
}
Aggregations