Skip to content

Commit 0d539ff

Browse files
Support WorkflowImplementationOptionsCustomizer (#2503)
Support WorkflowImplementationOptionsCustomizer
1 parent 2e1c89e commit 0d539ff

File tree

4 files changed

+78
-10
lines changed

4 files changed

+78
-10
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
package io.temporal.spring.boot;
2+
3+
import io.temporal.common.metadata.POJOWorkflowMethodMetadata;
4+
import io.temporal.worker.Worker;
5+
import io.temporal.worker.WorkflowImplementationOptions;
6+
import javax.annotation.Nonnull;
7+
import javax.annotation.Nullable;
8+
9+
/**
10+
* Bean of this class can be added to Spring context to get a fine control over {@link
11+
* WorkflowImplementationOptions} objects that are created by Temporal Spring Boot Autoconfigure
12+
* module.
13+
*
14+
* <p>Only one bean of this or {@code
15+
* TemporalOptionsCustomizer<WorkflowImplementationOptions.Builder>} type can be added to Spring
16+
* context.
17+
*/
18+
public interface WorkflowImplementationOptionsCustomizer
19+
extends TemporalOptionsCustomizer<WorkflowImplementationOptions.Builder> {
20+
21+
@Nonnull
22+
@Override
23+
default WorkflowImplementationOptions.Builder customize(
24+
@Nonnull WorkflowImplementationOptions.Builder optionsBuilder) {
25+
return optionsBuilder;
26+
}
27+
28+
/**
29+
* This method can modify some fields of the provided {@code
30+
* WorkflowImplementationOptions.Builder} or create a new builder altogether and return it back to
31+
* be used. This method is called after the {@code WorkflowImplementationOptions.Builder} is
32+
* initialized by the Temporal Spring Boot module, so changes done by this method will override
33+
* Spring Boot configuration values.
34+
*
35+
* @param optionsBuilder {@code *Options.Builder} to customize
36+
* @param worker the worker that the workflow implementation is being registered to.
37+
* @param clazz the class of the workflow implementation that is being registered.
38+
* @param workflowMethod the metadata of the workflow method on the interface that is being
39+
* registered. null if the class is a {@link io.temporal.workflow.DynamicWorkflow}.
40+
* @return modified {@code optionsBuilder} or a new builder instance to be used by the caller code
41+
*/
42+
@Nonnull
43+
WorkflowImplementationOptions.Builder customize(
44+
@Nonnull WorkflowImplementationOptions.Builder optionsBuilder,
45+
@Nonnull Worker worker,
46+
@Nonnull Class<?> clazz,
47+
@Nullable POJOWorkflowMethodMetadata workflowMethod);
48+
}

temporal-spring-boot-autoconfigure/src/main/java/io/temporal/spring/boot/autoconfigure/template/WorkersTemplate.java

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -501,7 +501,7 @@ private <T> void configureWorkflowImplementation(Worker worker, Class<?> clazz)
501501
clazz, Collections.singletonList(executeMethod));
502502
WorkflowImplementationOptions workflowImplementationOptions =
503503
new WorkflowImplementationOptionsTemplate(workflowImplementationCustomizer)
504-
.createWorkflowImplementationOptions();
504+
.createWorkflowImplementationOptions(worker, clazz, null);
505505
worker.registerWorkflowImplementationFactory(
506506
DynamicWorkflow.class,
507507
(encodedValues) -> {
@@ -544,10 +544,6 @@ private <T> void configureWorkflowImplementation(Worker worker, Class<?> clazz)
544544
+ clazz);
545545
}
546546

547-
WorkflowImplementationOptions workflowImplementationOptions =
548-
new WorkflowImplementationOptionsTemplate(workflowImplementationCustomizer)
549-
.createWorkflowImplementationOptions();
550-
551547
WorkerDeploymentOptions deploymentOptions = worker.getWorkerOptions().getDeploymentOptions();
552548

553549
// If the workflow implementation class has a constructor annotated with @WorkflowInit,
@@ -570,6 +566,9 @@ private <T> void configureWorkflowImplementation(Worker worker, Class<?> clazz)
570566
deploymentOptions.isUsingVersioning());
571567
}
572568

569+
WorkflowImplementationOptions workflowImplementationOptions =
570+
new WorkflowImplementationOptionsTemplate(workflowImplementationCustomizer)
571+
.createWorkflowImplementationOptions(worker, clazz, workflowMethod);
573572
worker.registerWorkflowImplementationFactory(
574573
(Class<T>) workflowMethod.getWorkflowInterface(),
575574
(encodedValues) -> {
@@ -602,6 +601,9 @@ private <T> void configureWorkflowImplementation(Worker worker, Class<?> clazz)
602601
deploymentOptions.getDefaultVersioningBehavior(),
603602
deploymentOptions.isUsingVersioning());
604603
}
604+
WorkflowImplementationOptions workflowImplementationOptions =
605+
new WorkflowImplementationOptionsTemplate(workflowImplementationCustomizer)
606+
.createWorkflowImplementationOptions(worker, clazz, workflowMethod);
605607
worker.registerWorkflowImplementationFactory(
606608
(Class<T>) workflowMethod.getWorkflowInterface(),
607609
() -> (T) beanFactory.createBean(clazz),

temporal-spring-boot-autoconfigure/src/main/java/io/temporal/spring/boot/autoconfigure/template/WorkflowImplementationOptionsTemplate.java

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
package io.temporal.spring.boot.autoconfigure.template;
22

3+
import io.temporal.common.metadata.POJOWorkflowMethodMetadata;
34
import io.temporal.spring.boot.TemporalOptionsCustomizer;
5+
import io.temporal.spring.boot.WorkflowImplementationOptionsCustomizer;
6+
import io.temporal.worker.Worker;
47
import io.temporal.worker.WorkflowImplementationOptions;
58
import javax.annotation.Nullable;
69

@@ -13,11 +16,17 @@ public WorkflowImplementationOptionsTemplate(
1316
this.customizer = customizer;
1417
}
1518

16-
public WorkflowImplementationOptions createWorkflowImplementationOptions() {
19+
public WorkflowImplementationOptions createWorkflowImplementationOptions(
20+
Worker worker, Class<?> clazz, POJOWorkflowMethodMetadata workflowMethod) {
1721
WorkflowImplementationOptions.Builder options = WorkflowImplementationOptions.newBuilder();
1822

1923
if (customizer != null) {
2024
options = customizer.customize(options);
25+
if (customizer instanceof WorkflowImplementationOptionsCustomizer) {
26+
options =
27+
((WorkflowImplementationOptionsCustomizer) customizer)
28+
.customize(options, worker, clazz, workflowMethod);
29+
}
2130
}
2231

2332
return options.build();

temporal-spring-boot-autoconfigure/src/test/java/io/temporal/spring/boot/autoconfigure/OptionsCustomizersTest.java

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,9 +7,10 @@
77
import io.temporal.client.WorkflowClientOptions;
88
import io.temporal.spring.boot.TemporalOptionsCustomizer;
99
import io.temporal.spring.boot.WorkerOptionsCustomizer;
10+
import io.temporal.spring.boot.WorkflowImplementationOptionsCustomizer;
11+
import io.temporal.spring.boot.autoconfigure.bytaskqueue.TestWorkflowImpl;
1012
import io.temporal.testing.TestEnvironmentOptions;
1113
import io.temporal.worker.WorkerFactoryOptions;
12-
import io.temporal.worker.WorkflowImplementationOptions;
1314
import java.util.List;
1415
import org.junit.jupiter.api.BeforeEach;
1516
import org.junit.jupiter.api.Test;
@@ -31,6 +32,7 @@ public class OptionsCustomizersTest {
3132

3233
@Autowired List<TemporalOptionsCustomizer<?>> customizers;
3334
@Autowired WorkerOptionsCustomizer workerCustomizer;
35+
@Autowired WorkflowImplementationOptionsCustomizer workflowImplementationOptionsCustomizer;
3436

3537
@BeforeEach
3638
void setUp() {
@@ -43,6 +45,8 @@ public void testCustomizersGotCalled() {
4345
assertEquals(5, customizers.size());
4446
customizers.forEach(c -> verify(c).customize(any()));
4547
verify(workerCustomizer).customize(any(), eq("UnitTest"), eq("UnitTest"));
48+
verify(workflowImplementationOptionsCustomizer)
49+
.customize(any(), any(), eq(TestWorkflowImpl.class), any());
4650
}
4751

4852
@ComponentScan(
@@ -68,9 +72,14 @@ public TemporalOptionsCustomizer<WorkerFactoryOptions.Builder> workerFactoryCust
6872
}
6973

7074
@Bean
71-
public TemporalOptionsCustomizer<WorkflowImplementationOptions.Builder>
72-
WorkflowImplementationCustomizer() {
73-
return getReturningMock();
75+
public WorkflowImplementationOptionsCustomizer WorkflowImplementationCustomizer() {
76+
WorkflowImplementationOptionsCustomizer mock =
77+
mock(WorkflowImplementationOptionsCustomizer.class);
78+
when(mock.customize(any())).thenAnswer(invocation -> invocation.getArgument(0)).getMock();
79+
when(mock.customize(any(), any(), any(), any()))
80+
.thenAnswer(invocation -> invocation.getArgument(0))
81+
.getMock();
82+
return mock;
7483
}
7584

7685
@Bean

0 commit comments

Comments
 (0)