@@ -42,16 +42,14 @@ def __init__(
4242 name : str ,
4343 * ,
4444 data_converter : PluginParameter [temporalio .converter .DataConverter ] = None ,
45- client_interceptors : PluginParameter [
46- Sequence [temporalio .client .Interceptor ]
47- ] = None ,
45+ interceptors : Sequence [
46+ temporalio .client .Interceptor | temporalio .worker .Interceptor
47+ ]
48+ | None = None ,
4849 activities : PluginParameter [Sequence [Callable ]] = None ,
4950 nexus_service_handlers : PluginParameter [Sequence [Any ]] = None ,
5051 workflows : PluginParameter [Sequence [type ]] = None ,
5152 workflow_runner : PluginParameter [WorkflowRunner ] = None ,
52- worker_interceptors : PluginParameter [
53- Sequence [temporalio .worker .Interceptor ]
54- ] = None ,
5553 workflow_failure_exception_types : PluginParameter [
5654 Sequence [type [BaseException ]]
5755 ] = None ,
@@ -66,9 +64,10 @@ def __init__(
6664 name: The name of the plugin.
6765 data_converter: Data converter for serialization, or callable to customize existing one.
6866 Applied to the Client and Replayer.
69- client_interceptors: Client interceptors to append, or callable to customize existing ones.
70- Applied to the Client. Note, if the provided interceptor is also a worker.Interceptor,
71- it will be added to any worker which uses that client.
67+ interceptors: Interceptors to append.
68+ Client interceptors are applied to the Client, worker interceptors are applied
69+ to the Worker and Replayer. Interceptors that implement both interfaces will
70+ be applied to both, with exactly one instance used per worker to avoid duplication.
7271 activities: Activity functions to append, or callable to customize existing ones.
7372 Applied to the Worker.
7473 nexus_service_handlers: Nexus service handlers to append, or callable to customize existing ones.
@@ -77,8 +76,6 @@ def __init__(
7776 Applied to the Worker and Replayer.
7877 workflow_runner: Workflow runner, or callable to customize existing one.
7978 Applied to the Worker and Replayer.
80- worker_interceptors: Worker interceptors to append, or callable to customize existing ones.
81- Applied to the Worker and Replayer.
8279 workflow_failure_exception_types: Exception types for workflow failures to append,
8380 or callable to customize existing ones. Applied to the Worker and Replayer.
8481 run_context: A place to run custom code to wrap around the Worker (or Replayer) execution.
@@ -89,12 +86,11 @@ def __init__(
8986 """
9087 self ._name = name
9188 self .data_converter = data_converter
92- self .client_interceptors = client_interceptors
89+ self .interceptors = interceptors
9390 self .activities = activities
9491 self .nexus_service_handlers = nexus_service_handlers
9592 self .workflows = workflows
9693 self .workflow_runner = workflow_runner
97- self .worker_interceptors = worker_interceptors
9894 self .workflow_failure_exception_types = workflow_failure_exception_types
9995 self .run_context = run_context
10096
@@ -110,11 +106,22 @@ def configure_client(self, config: ClientConfig) -> ClientConfig:
110106 if data_converter :
111107 config ["data_converter" ] = data_converter
112108
113- interceptors = _resolve_append_parameter (
114- config .get ("interceptors" ), self .client_interceptors
109+ # Resolve the combined interceptors first, then filter to client ones
110+ all_interceptors = _resolve_append_parameter (
111+ cast (
112+ Sequence [temporalio .client .Interceptor | temporalio .worker .Interceptor ]
113+ | None ,
114+ config .get ("interceptors" ),
115+ ),
116+ self .interceptors ,
115117 )
116- if interceptors is not None :
117- config ["interceptors" ] = interceptors
118+ if all_interceptors is not None :
119+ client_interceptors = [
120+ interceptor
121+ for interceptor in all_interceptors
122+ if isinstance (interceptor , temporalio .client .Interceptor )
123+ ]
124+ config ["interceptors" ] = client_interceptors
118125
119126 return config
120127
@@ -150,36 +157,24 @@ def configure_worker(self, config: WorkerConfig) -> WorkerConfig:
150157 if workflow_runner :
151158 config ["workflow_runner" ] = workflow_runner
152159
153- interceptors = list (
154- _resolve_append_parameter (
155- config . get ("interceptors" ), self . worker_interceptors
160+ if self . interceptors is not None :
161+ client_interceptors_list = (
162+ config [ "client" ]. config ( active_config = True ). get ("interceptors" , []) # type:ignore[reportTypedDictNotRequiredAccess]
156163 )
157- or []
158- )
159164
160- # Only propagate client interceptors if they are provided as a simple list (not callable)
161- if self .client_interceptors is not None and not callable (
162- self .client_interceptors
163- ):
164- client_worker_interceptors = [
165+ # Exclude any already registered interceptors and client only interceptors
166+ worker_interceptors = [
165167 interceptor
166- for interceptor in self .client_interceptors
168+ for interceptor in self .interceptors
167169 if isinstance (interceptor , temporalio .worker .Interceptor )
170+ and interceptor not in client_interceptors_list
168171 ]
169- for interceptor in client_worker_interceptors :
170- if interceptor not in interceptors :
171- # Check if interceptor is already in client's interceptors to avoid duplication
172- client_config = config .get ("client" )
173- if client_config is not None :
174- client_interceptors_list = client_config .config (
175- active_config = True
176- ).get ("interceptors" , [])
177- if interceptor not in client_interceptors_list :
178- interceptors .append (interceptor )
179- else :
180- interceptors .append (interceptor )
181-
182- config ["interceptors" ] = interceptors
172+
173+ provided_interceptors = _resolve_append_parameter (
174+ config .get ("interceptors" ), worker_interceptors
175+ )
176+ if provided_interceptors is not None :
177+ config ["interceptors" ] = provided_interceptors
183178
184179 failure_exception_types = _resolve_append_parameter (
185180 config .get ("workflow_failure_exception_types" ),
@@ -208,11 +203,21 @@ def configure_replayer(self, config: ReplayerConfig) -> ReplayerConfig:
208203 if workflow_runner :
209204 config ["workflow_runner" ] = workflow_runner
210205
211- interceptors = _resolve_append_parameter (
212- config .get ("interceptors" ), self .worker_interceptors
206+ all_interceptors = _resolve_append_parameter (
207+ cast (
208+ Sequence [temporalio .client .Interceptor | temporalio .worker .Interceptor ]
209+ | None ,
210+ config .get ("interceptors" ),
211+ ),
212+ self .interceptors ,
213213 )
214- if interceptors is not None :
215- config ["interceptors" ] = interceptors
214+ if all_interceptors is not None :
215+ worker_interceptors = [
216+ interceptor
217+ for interceptor in all_interceptors
218+ if isinstance (interceptor , temporalio .worker .Interceptor )
219+ ]
220+ config ["interceptors" ] = worker_interceptors
216221
217222 failure_exception_types = _resolve_append_parameter (
218223 config .get ("workflow_failure_exception_types" ),
0 commit comments