digitalkin 0.2.12__py3-none-any.whl → 0.2.13__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (36) hide show
  1. digitalkin/__version__.py +1 -1
  2. digitalkin/grpc_servers/_base_server.py +15 -17
  3. digitalkin/grpc_servers/module_server.py +9 -10
  4. digitalkin/grpc_servers/module_servicer.py +107 -85
  5. digitalkin/grpc_servers/registry_server.py +3 -6
  6. digitalkin/grpc_servers/registry_servicer.py +18 -19
  7. digitalkin/grpc_servers/utils/grpc_client_wrapper.py +3 -5
  8. digitalkin/logger.py +45 -1
  9. digitalkin/models/module/module.py +1 -0
  10. digitalkin/modules/_base_module.py +44 -5
  11. digitalkin/modules/job_manager/base_job_manager.py +139 -0
  12. digitalkin/modules/job_manager/job_manager_models.py +44 -0
  13. digitalkin/modules/job_manager/single_job_manager.py +218 -0
  14. digitalkin/modules/job_manager/taskiq_broker.py +173 -0
  15. digitalkin/modules/job_manager/taskiq_job_manager.py +213 -0
  16. digitalkin/services/cost/default_cost.py +8 -4
  17. digitalkin/services/cost/grpc_cost.py +15 -7
  18. digitalkin/services/filesystem/default_filesystem.py +2 -4
  19. digitalkin/services/filesystem/grpc_filesystem.py +8 -5
  20. digitalkin/services/setup/__init__.py +1 -0
  21. digitalkin/services/setup/default_setup.py +10 -12
  22. digitalkin/services/setup/grpc_setup.py +8 -10
  23. digitalkin/services/storage/default_storage.py +11 -5
  24. digitalkin/services/storage/grpc_storage.py +23 -8
  25. digitalkin/utils/arg_parser.py +5 -48
  26. digitalkin/utils/development_mode_action.py +51 -0
  27. {digitalkin-0.2.12.dist-info → digitalkin-0.2.13.dist-info}/METADATA +42 -11
  28. {digitalkin-0.2.12.dist-info → digitalkin-0.2.13.dist-info}/RECORD +35 -28
  29. {digitalkin-0.2.12.dist-info → digitalkin-0.2.13.dist-info}/WHEEL +1 -1
  30. modules/cpu_intensive_module.py +271 -0
  31. modules/minimal_llm_module.py +200 -56
  32. modules/storage_module.py +5 -6
  33. modules/text_transform_module.py +1 -1
  34. digitalkin/modules/job_manager.py +0 -177
  35. {digitalkin-0.2.12.dist-info → digitalkin-0.2.13.dist-info}/licenses/LICENSE +0 -0
  36. {digitalkin-0.2.12.dist-info → digitalkin-0.2.13.dist-info}/top_level.txt +0 -0
digitalkin/__version__.py CHANGED
@@ -5,4 +5,4 @@ from importlib.metadata import PackageNotFoundError, version
5
5
  try:
6
6
  __version__ = version("digitalkin")
7
7
  except PackageNotFoundError:
8
- __version__ = "0.2.12"
8
+ __version__ = "0.2.13"
@@ -2,7 +2,6 @@
2
2
 
3
3
  import abc
4
4
  import asyncio
5
- import logging
6
5
  from collections.abc import Callable
7
6
  from concurrent import futures
8
7
  from pathlib import Path
@@ -20,8 +19,7 @@ from digitalkin.grpc_servers.utils.exceptions import (
20
19
  )
21
20
  from digitalkin.grpc_servers.utils.models import SecurityMode, ServerConfig, ServerMode
22
21
  from digitalkin.grpc_servers.utils.types import GrpcServer, ServiceDescriptor, T
23
-
24
- logger = logging.getLogger(__name__)
22
+ from digitalkin.logger import logger
25
23
 
26
24
 
27
25
  class BaseServer(abc.ABC):
@@ -132,7 +130,7 @@ class BaseServer(abc.ABC):
132
130
  # reflection queries with detailed service information
133
131
  reflection.enable_server_reflection(service_names, self.server)
134
132
 
135
- logger.info("Added gRPC reflection service with services: %s", service_names)
133
+ logger.debug("Added gRPC reflection service with services: %s", service_names)
136
134
  except ImportError:
137
135
  logger.warning("Could not enable reflection: grpcio-reflection package not installed")
138
136
  except Exception as e:
@@ -165,7 +163,7 @@ class BaseServer(abc.ABC):
165
163
  if service_name not in self._service_names:
166
164
  self._service_names.append(service_name)
167
165
 
168
- logger.info("Added gRPC health checking service")
166
+ logger.debug("Added gRPC health checking service")
169
167
 
170
168
  # Set all services as SERVING
171
169
  for service_name in self._service_names:
@@ -255,7 +253,7 @@ class BaseServer(abc.ABC):
255
253
  sync_server = cast("grpc.Server", server)
256
254
  sync_server.add_secure_port(self.config.address, server_credentials)
257
255
 
258
- logger.info("Added secure port %s", self.config.address)
256
+ logger.debug("Added secure port %s", self.config.address)
259
257
  except Exception as e:
260
258
  msg = f"Failed to configure secure port: {e}"
261
259
  raise SecurityError(msg) from e
@@ -277,7 +275,7 @@ class BaseServer(abc.ABC):
277
275
  sync_server = cast("grpc.Server", server)
278
276
  sync_server.add_insecure_port(self.config.address)
279
277
 
280
- logger.info("Added insecure port %s", self.config.address)
278
+ logger.debug("Added insecure port %s", self.config.address)
281
279
  except Exception as e:
282
280
  msg = f"Failed to add insecure port: {e}"
283
281
  raise ConfigurationError(msg) from e
@@ -301,7 +299,7 @@ class BaseServer(abc.ABC):
301
299
  self._add_reflection()
302
300
 
303
301
  # Start the server
304
- logger.info("Starting gRPC server on %s", self.config.address)
302
+ logger.debug("Starting gRPC server on %s", self.config.address)
305
303
  try:
306
304
  if self.config.mode == ServerMode.ASYNC:
307
305
  # For async server, use the event loop
@@ -314,7 +312,7 @@ class BaseServer(abc.ABC):
314
312
  # For sync server, directly call start
315
313
  sync_server = cast("grpc.Server", self.server)
316
314
  sync_server.start()
317
- logger.info("✅ gRPC server started on %s", self.config.address)
315
+ logger.debug("✅ gRPC server started on %s", self.config.address)
318
316
  except Exception as e:
319
317
  logger.exception("❎ Error starting server")
320
318
  msg = f"Failed to start server: {e}"
@@ -351,7 +349,7 @@ class BaseServer(abc.ABC):
351
349
  self._add_reflection()
352
350
 
353
351
  # Start the server
354
- logger.info("Starting gRPC server on %s", self.config.address)
352
+ logger.debug("Starting gRPC server on %s", self.config.address)
355
353
  try:
356
354
  if self.config.mode == ServerMode.ASYNC:
357
355
  await self._start_async()
@@ -359,7 +357,7 @@ class BaseServer(abc.ABC):
359
357
  # For sync server in async context
360
358
  sync_server = cast("grpc.Server", self.server)
361
359
  sync_server.start()
362
- logger.info("✅ gRPC server started on %s", self.config.address)
360
+ logger.debug("✅ gRPC server started on %s", self.config.address)
363
361
  except Exception as e:
364
362
  logger.exception("❎ Error starting server")
365
363
  msg = f"Failed to start server: {e}"
@@ -375,7 +373,7 @@ class BaseServer(abc.ABC):
375
373
  logger.warning("Attempted to stop server, but no server is running")
376
374
  return
377
375
 
378
- logger.info("Stopping gRPC server...")
376
+ logger.debug("Stopping gRPC server...")
379
377
  if self.config.mode == ServerMode.ASYNC:
380
378
  # We'll use a different approach that works whether we're in a running event loop or not
381
379
  try:
@@ -392,13 +390,13 @@ class BaseServer(abc.ABC):
392
390
  )
393
391
  # Set server to None to avoid further operations
394
392
  self.server = None
395
- logger.info("✅ gRPC server marked as stopped")
393
+ logger.debug("✅ gRPC server marked as stopped")
396
394
  return
397
395
  # If not in a running event loop, use run_until_complete
398
396
  loop.run_until_complete(self._stop_async(grace))
399
397
  except RuntimeError:
400
398
  # Event loop issues - try with a new loop
401
- logger.info("Creating new event loop for shutdown")
399
+ logger.debug("Creating new event loop for shutdown")
402
400
  try:
403
401
  new_loop = asyncio.new_event_loop()
404
402
  asyncio.set_event_loop(new_loop)
@@ -410,7 +408,7 @@ class BaseServer(abc.ABC):
410
408
  sync_server = cast("grpc.Server", self.server)
411
409
  sync_server.stop(grace=grace)
412
410
 
413
- logger.info("✅ gRPC server stopped")
411
+ logger.debug("✅ gRPC server stopped")
414
412
  self.server = None
415
413
 
416
414
  async def _stop_async(self, grace: float | None = None) -> None:
@@ -437,7 +435,7 @@ class BaseServer(abc.ABC):
437
435
  logger.warning("Attempted to stop server, but no server is running")
438
436
  return
439
437
 
440
- logger.info("Stopping gRPC server asynchronously...")
438
+ logger.debug("Stopping gRPC server asynchronously...")
441
439
  if self.config.mode == ServerMode.ASYNC:
442
440
  await self._stop_async(grace)
443
441
  else:
@@ -445,7 +443,7 @@ class BaseServer(abc.ABC):
445
443
  sync_server = cast("grpc.Server", self.server)
446
444
  sync_server.stop(grace=grace)
447
445
 
448
- logger.info("✅ gRPC server stopped")
446
+ logger.debug("✅ gRPC server stopped")
449
447
  self.server = None
450
448
 
451
449
  def wait_for_termination(self) -> None:
@@ -1,6 +1,5 @@
1
1
  """Module gRPC server implementation for DigitalKin."""
2
2
 
3
- import logging
4
3
  from pathlib import Path
5
4
  import uuid
6
5
 
@@ -25,8 +24,7 @@ from digitalkin_proto.digitalkin.module_registry.v2 import (
25
24
  module_registry_service_pb2_grpc,
26
25
  registration_pb2,
27
26
  )
28
-
29
- logger = logging.getLogger(__name__)
27
+ from digitalkin.logger import logger
30
28
 
31
29
 
32
30
  class ModuleServer(BaseServer):
@@ -70,14 +68,14 @@ class ModuleServer(BaseServer):
70
68
  msg = "Server must be created before registering servicers"
71
69
  raise RuntimeError(msg)
72
70
 
73
- logger.info("Registering module servicer for %s", self.module_class.__name__)
71
+ logger.debug("Registering module servicer for %s", self.module_class.__name__)
74
72
  self.module_servicer = ModuleServicer(self.module_class)
75
73
  self.register_servicer(
76
74
  self.module_servicer,
77
75
  module_service_pb2_grpc.add_ModuleServiceServicer_to_server,
78
76
  service_descriptor=module_service_pb2.DESCRIPTOR,
79
77
  )
80
- logger.info("Registered Module servicer")
78
+ logger.debug("Registered Module servicer")
81
79
 
82
80
  def start(self) -> None:
83
81
  """Start the module server and register with the registry if configured."""
@@ -115,6 +113,7 @@ class ModuleServer(BaseServer):
115
113
  logger.critical(
116
114
  "Setup post init started with config: %s", self.client_config
117
115
  )
116
+ await self.module_servicer.job_manager._start()
118
117
  self.module_servicer.setup.__post_init__(self.client_config)
119
118
 
120
119
  def stop(self, grace: float | None = None) -> None:
@@ -134,7 +133,7 @@ class ModuleServer(BaseServer):
134
133
  Raises:
135
134
  ServerError: If communication with the registry server fails.
136
135
  """
137
- logger.info(
136
+ logger.debug(
138
137
  "Registering module with registry at %s",
139
138
  self.server_config.registry_address,
140
139
  )
@@ -172,7 +171,7 @@ class ModuleServer(BaseServer):
172
171
 
173
172
  try:
174
173
  # Call the register method
175
- logger.info(
174
+ logger.debug(
176
175
  "Request sent to registry for module: %s:%s",
177
176
  self.module_class.metadata["name"],
178
177
  self.module_class.metadata["module_id"],
@@ -180,7 +179,7 @@ class ModuleServer(BaseServer):
180
179
  response = stub.RegisterModule(request)
181
180
 
182
181
  if response.success:
183
- logger.info("Module registered successfully")
182
+ logger.debug("Module registered successfully")
184
183
  else:
185
184
  logger.error("Module registration failed")
186
185
  except grpc.RpcError:
@@ -193,7 +192,7 @@ class ModuleServer(BaseServer):
193
192
  Raises:
194
193
  ServerError: If communication with the registry server fails.
195
194
  """
196
- logger.info(
195
+ logger.debug(
197
196
  "Deregistering module from registry at %s",
198
197
  self.server_config.registry_address,
199
198
  )
@@ -214,7 +213,7 @@ class ModuleServer(BaseServer):
214
213
  response = stub.DeregisterModule(request)
215
214
 
216
215
  if response.success:
217
- logger.info("Module deregistered successfull")
216
+ logger.debug("Module deregistered successfull")
218
217
  else:
219
218
  logger.error("Module deregistration failed")
220
219
  except grpc.RpcError:
@@ -1,7 +1,6 @@
1
1
  """Module servicer implementation for DigitalKin."""
2
2
 
3
- import asyncio
4
- import logging
3
+ from argparse import ArgumentParser, Namespace
5
4
  from collections.abc import AsyncGenerator
6
5
  from typing import Any
7
6
 
@@ -15,19 +14,20 @@ from digitalkin_proto.digitalkin.module.v2 import (
15
14
  from google.protobuf import json_format, struct_pb2
16
15
 
17
16
  from digitalkin.grpc_servers.utils.exceptions import ServicerError
18
- from digitalkin.models.module import OutputModelT
17
+ from digitalkin.logger import logger
19
18
  from digitalkin.models.module.module import ModuleStatus
20
19
  from digitalkin.modules._base_module import BaseModule
21
- from digitalkin.modules.job_manager import JobManager
20
+ from digitalkin.modules.job_manager.base_job_manager import BaseJobManager
21
+ from digitalkin.modules.job_manager.job_manager_models import JobManagerMode
22
22
  from digitalkin.services.services_models import ServicesMode
23
23
  from digitalkin.services.setup.default_setup import DefaultSetup
24
24
  from digitalkin.services.setup.grpc_setup import GrpcSetup
25
25
  from digitalkin.services.setup.setup_strategy import SetupStrategy
26
+ from digitalkin.utils.arg_parser import ArgParser
27
+ from digitalkin.utils.development_mode_action import DevelopmentModeMappingAction
26
28
 
27
- logger = logging.getLogger(__name__)
28
29
 
29
-
30
- class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
30
+ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer, ArgParser):
31
31
  """Implementation of the ModuleService.
32
32
 
33
33
  This servicer handles interactions with a DigitalKin module.
@@ -37,7 +37,31 @@ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
37
37
  active_jobs: Dictionary tracking active module jobs.
38
38
  """
39
39
 
40
+ args: Namespace
40
41
  setup: SetupStrategy
42
+ job_manager: BaseJobManager
43
+
44
+ def _add_parser_args(self, parser: ArgumentParser) -> None:
45
+ super()._add_parser_args(parser)
46
+ parser.add_argument(
47
+ "-d",
48
+ "--dev-mode",
49
+ env_var="SERVICE_MODE",
50
+ choices=ServicesMode.__members__,
51
+ default="local",
52
+ action=DevelopmentModeMappingAction,
53
+ dest="services_mode",
54
+ help="Define Module Service configurations for endpoints",
55
+ )
56
+ parser.add_argument(
57
+ "-jm",
58
+ "--job-manager",
59
+ type=JobManagerMode,
60
+ choices=list(JobManagerMode),
61
+ default=JobManagerMode.SINGLE,
62
+ dest="job_manager_mode",
63
+ help="Define Module job manager configurations for load balancing",
64
+ )
41
65
 
42
66
  def __init__(self, module_class: type[BaseModule]) -> None:
43
67
  """Initialize the module servicer.
@@ -46,15 +70,16 @@ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
46
70
  module_class: The module type to serve.
47
71
  """
48
72
  super().__init__()
49
- self.queue: asyncio.Queue = asyncio.Queue()
50
73
  self.module_class = module_class
51
- self.job_manager = JobManager(module_class)
52
- self.setup = GrpcSetup() if self.job_manager.args.services_mode == ServicesMode.REMOTE else DefaultSetup()
74
+ job_manager_class = self.args.job_manager_mode.get_manager_class()
75
+ self.job_manager = job_manager_class(module_class, self.args.services_mode)
53
76
 
54
- async def add_to_queue(self, job_id: str, output_data: OutputModelT) -> None: # type: ignore
55
- """Callback used to add the output data to the queue of messages."""
56
- logger.info("JOB: %s added an output_data: %s", job_id, output_data)
57
- await self.queue.put({job_id: output_data})
77
+ logger.debug(
78
+ "ModuleServicer initialized with job manager: %s | %s",
79
+ self.args.job_manager_mode,
80
+ self.job_manager,
81
+ )
82
+ self.setup = GrpcSetup() if self.args.services_mode == ServicesMode.REMOTE else DefaultSetup()
58
83
 
59
84
  async def StartModule( # noqa: N802
60
85
  self,
@@ -87,47 +112,45 @@ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
87
112
  if not setup_data_class:
88
113
  msg = "No setup data returned."
89
114
  raise ServicerError(msg)
90
- # TODO: Check failure of setup data format
115
+
91
116
  setup_data = self.module_class.create_setup_model(setup_data_class.current_setup_version.content)
92
117
 
93
- # setup_id should be use to request a precise setup from the module
94
- # Create a job for this execution
95
- result: tuple[str, BaseModule] = await self.job_manager.create_job(
118
+ # create a task to run the module in background
119
+ job_id = await self.job_manager.create_job(
96
120
  input_data,
97
121
  setup_data,
98
122
  mission_id=request.mission_id,
99
123
  setup_version_id=setup_data_class.current_setup_version.id,
100
- callback=self.add_to_queue,
101
124
  )
102
- job_id, module = result
103
-
104
- while module.status == ModuleStatus.RUNNING or not self.queue.empty():
105
- output_data: dict = await self.queue.get()
106
-
107
- if job_id not in output_data or job_id not in self.job_manager.modules:
108
- message = f"Job {job_id} not found"
109
- logger.warning(message)
110
- context.set_code(grpc.StatusCode.NOT_FOUND)
111
- context.set_details(message)
112
- yield lifecycle_pb2.StartModuleResponse(success=False)
113
- return
114
-
115
- if output_data[job_id].get("error", None) is not None:
116
- context.set_code(output_data[job_id]["error"]["code"])
117
- context.set_details(output_data[job_id]["error"]["error_message"])
118
- yield lifecycle_pb2.StartModuleResponse(success=False)
119
- return
120
-
121
- output_proto = json_format.ParseDict(
122
- output_data[job_id],
123
- struct_pb2.Struct(),
124
- ignore_unknown_fields=True,
125
- )
126
- yield lifecycle_pb2.StartModuleResponse(
127
- success=True,
128
- output=output_proto,
129
- job_id=job_id,
130
- )
125
+
126
+ if job_id is None:
127
+ context.set_code(grpc.StatusCode.NOT_FOUND)
128
+ context.set_details("Failed to create module instance")
129
+ yield lifecycle_pb2.StartModuleResponse(success=False)
130
+ return
131
+
132
+ async with self.job_manager.generate_stream_consumer(job_id) as stream: # type: ignore
133
+ async for message in stream:
134
+ if message.get("error", None) is not None:
135
+ context.set_code(message["error"]["code"])
136
+ context.set_details(message["error"]["error_message"])
137
+ yield lifecycle_pb2.StartModuleResponse(success=False, job_id=job_id)
138
+ break
139
+
140
+ if message.get("exception", None) is not None:
141
+ logger.error("Error in output_data")
142
+ context.set_code(message["short_description"])
143
+ context.set_details(message["exception"])
144
+ yield lifecycle_pb2.StartModuleResponse(success=False, job_id=job_id)
145
+ break
146
+
147
+ if message.get("code", None) is not None and message.get("code") == "__END_OF_STREAM__":
148
+ yield lifecycle_pb2.StartModuleResponse(success=True, job_id=job_id)
149
+ break
150
+
151
+ proto = json_format.ParseDict(message, struct_pb2.Struct(), ignore_unknown_fields=True)
152
+ yield lifecycle_pb2.StartModuleResponse(success=True, output=proto, job_id=job_id)
153
+ logger.info("Job %s finished", job_id)
131
154
 
132
155
  async def StopModule( # noqa: N802
133
156
  self,
@@ -143,23 +166,20 @@ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
143
166
  Returns:
144
167
  A response indicating success or failure.
145
168
  """
146
- logger.info("StopModule called for module: '%s'", self.module_class.__name__)
169
+ logger.debug("StopModule called for module: '%s'", self.module_class.__name__)
147
170
 
148
- job_id = request.job_id
149
- if job_id not in self.job_manager.modules:
150
- message = f"Job {job_id} not found"
171
+ response: bool = await self.job_manager.stop_module(request.job_id)
172
+ if not response:
173
+ message = f"Job {request.job_id} not found"
151
174
  logger.warning(message)
152
175
  context.set_code(grpc.StatusCode.NOT_FOUND)
153
176
  context.set_details(message)
154
177
  return lifecycle_pb2.StopModuleResponse(success=False)
155
178
 
156
- # Update the job status
157
- await self.job_manager.modules[job_id].stop()
158
-
159
- logger.info("Job %s stopped successfully", job_id)
179
+ logger.debug("Job %s stopped successfully", request.job_id)
160
180
  return lifecycle_pb2.StopModuleResponse(success=True)
161
181
 
162
- def GetModuleStatus( # noqa: N802
182
+ async def GetModuleStatus( # noqa: N802
163
183
  self,
164
184
  request: monitoring_pb2.GetModuleStatusRequest,
165
185
  context: grpc.ServicerContext,
@@ -173,33 +193,33 @@ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
173
193
  Returns:
174
194
  A response with the module status.
175
195
  """
176
- logger.info("GetModuleStatus called for module: '%s'", self.module_class.__name__)
177
-
178
- # If job_id is specified, get status for that job
179
- if request.job_id:
180
- if request.job_id not in self.job_manager.modules:
181
- message = f"Job {request.job_id} not found"
182
- logger.warning(message)
183
- context.set_code(grpc.StatusCode.NOT_FOUND)
184
- context.set_details(message)
185
- return monitoring_pb2.GetModuleStatusResponse()
186
-
187
- status = self.job_manager.modules[request.job_id].status
188
- logger.info("Job %s status: '%s'", request.job_id, status)
196
+ logger.debug("GetModuleStatus called for module: '%s'", self.module_class.__name__)
197
+
198
+ if not request.job_id:
199
+ logger.debug("Job %s status: '%s'", request.job_id, ModuleStatus.NOT_FOUND)
189
200
  return monitoring_pb2.GetModuleStatusResponse(
190
- success=True,
191
- status=status.name,
201
+ success=False,
202
+ status=ModuleStatus.NOT_FOUND.name,
192
203
  job_id=request.job_id,
193
204
  )
194
205
 
195
- logger.info("Job %s status: '%s'", request.job_id, ModuleStatus.NOT_FOUND)
206
+ status = await self.job_manager.get_module_status(request.job_id)
207
+
208
+ if status is None:
209
+ message = f"Job {request.job_id} not found"
210
+ logger.warning(message)
211
+ context.set_code(grpc.StatusCode.NOT_FOUND)
212
+ context.set_details(message)
213
+ return monitoring_pb2.GetModuleStatusResponse()
214
+
215
+ logger.debug("Job %s status: '%s'", request.job_id, status)
196
216
  return monitoring_pb2.GetModuleStatusResponse(
197
- success=False,
198
- status=ModuleStatus.NOT_FOUND.name,
217
+ success=True,
218
+ status=status.name,
199
219
  job_id=request.job_id,
200
220
  )
201
221
 
202
- def GetModuleJobs( # noqa: N802
222
+ async def GetModuleJobs( # noqa: N802
203
223
  self,
204
224
  request: monitoring_pb2.GetModuleJobsRequest, # noqa: ARG002
205
225
  context: grpc.ServicerContext, # noqa: ARG002
@@ -213,20 +233,22 @@ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
213
233
  Returns:
214
234
  A response with information about active jobs.
215
235
  """
216
- logger.info("GetModuleJobs called for module: '%s'", self.module_class.__name__)
236
+ logger.debug("GetModuleJobs called for module: '%s'", self.module_class.__name__)
237
+
238
+ modules = await self.job_manager.list_modules()
217
239
 
218
240
  # Create job info objects for each active job
219
241
  return monitoring_pb2.GetModuleJobsResponse(
220
242
  jobs=[
221
243
  monitoring_pb2.JobInfo(
222
244
  job_id=job_id,
223
- job_status=job_data.status.name,
245
+ job_status=job_data["status"].name,
224
246
  )
225
- for job_id, job_data in self.job_manager.modules.items()
247
+ for job_id, job_data in modules.items()
226
248
  ],
227
249
  )
228
250
 
229
- def GetModuleInput( # noqa: N802
251
+ async def GetModuleInput( # noqa: N802
230
252
  self,
231
253
  request: information_pb2.GetModuleInputRequest,
232
254
  context: grpc.ServicerContext,
@@ -240,7 +262,7 @@ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
240
262
  Returns:
241
263
  A response with the module's input schema.
242
264
  """
243
- logger.info("GetModuleInput called for module: '%s'", self.module_class.__name__)
265
+ logger.debug("GetModuleInput called for module: '%s'", self.module_class.__name__)
244
266
 
245
267
  # Get input schema if available
246
268
  try:
@@ -262,7 +284,7 @@ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
262
284
  input_schema=input_format_struct,
263
285
  )
264
286
 
265
- def GetModuleOutput( # noqa: N802
287
+ async def GetModuleOutput( # noqa: N802
266
288
  self,
267
289
  request: information_pb2.GetModuleOutputRequest,
268
290
  context: grpc.ServicerContext,
@@ -276,7 +298,7 @@ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
276
298
  Returns:
277
299
  A response with the module's output schema.
278
300
  """
279
- logger.info("GetModuleOutput called for module: '%s'", self.module_class.__name__)
301
+ logger.debug("GetModuleOutput called for module: '%s'", self.module_class.__name__)
280
302
 
281
303
  # Get output schema if available
282
304
  try:
@@ -298,7 +320,7 @@ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
298
320
  output_schema=output_format_struct,
299
321
  )
300
322
 
301
- def GetModuleSetup( # noqa: N802
323
+ async def GetModuleSetup( # noqa: N802
302
324
  self,
303
325
  request: information_pb2.GetModuleSetupRequest,
304
326
  context: grpc.ServicerContext,
@@ -312,7 +334,7 @@ class ModuleServicer(module_service_pb2_grpc.ModuleServiceServicer):
312
334
  Returns:
313
335
  A response with the module's setup information.
314
336
  """
315
- logger.info("GetModuleSetup called for module: '%s'", self.module_class.__name__)
337
+ logger.debug("GetModuleSetup called for module: '%s'", self.module_class.__name__)
316
338
 
317
339
  # Get setup schema if available
318
340
  try:
@@ -1,7 +1,5 @@
1
1
  """Registry gRPC server implementation for DigitalKin."""
2
2
 
3
- import logging
4
-
5
3
  from digitalkin_proto.digitalkin.module_registry.v2 import (
6
4
  module_registry_service_pb2,
7
5
  module_registry_service_pb2_grpc,
@@ -10,8 +8,7 @@ from digitalkin_proto.digitalkin.module_registry.v2 import (
10
8
  from digitalkin.grpc_servers._base_server import BaseServer
11
9
  from digitalkin.grpc_servers.registry_servicer import RegistryModule, RegistryServicer
12
10
  from digitalkin.grpc_servers.utils.models import RegistryServerConfig
13
-
14
- logger = logging.getLogger(__name__)
11
+ from digitalkin.logger import logger
15
12
 
16
13
 
17
14
  class RegistryServer(BaseServer):
@@ -48,14 +45,14 @@ class RegistryServer(BaseServer):
48
45
  msg = "Server must be created before registering servicers"
49
46
  raise RuntimeError(msg)
50
47
 
51
- logger.info("Registering registry servicer")
48
+ logger.debug("Registering registry servicer")
52
49
  self.registry_servicer = RegistryServicer()
53
50
  self.register_servicer(
54
51
  self.registry_servicer,
55
52
  module_registry_service_pb2_grpc.add_ModuleRegistryServiceServicer_to_server,
56
53
  service_descriptor=module_registry_service_pb2.DESCRIPTOR,
57
54
  )
58
- logger.info("Registered registry servicer")
55
+ logger.debug("Registered registry servicer")
59
56
 
60
57
  def get_registered_modules(self) -> list[RegistryModule]:
61
58
  """Get a list of all registered modules.