Skip to content

Commit

Permalink
Don't do constructor injection on dataclasses.
Browse files Browse the repository at this point in the history
  • Loading branch information
runemalm committed Aug 8, 2024
1 parent 40cba46 commit 748d626
Show file tree
Hide file tree
Showing 2 changed files with 28 additions and 0 deletions.
4 changes: 4 additions & 0 deletions src/dependency_injection/container.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import inspect
from dataclasses import is_dataclass

from typing import Any, Callable, Dict, List, Optional, TypeVar, Type

Expand Down Expand Up @@ -176,6 +177,9 @@ def _inject_dependencies(
scope_name: str = None,
constructor_args: Optional[Dict[str, Any]] = None,
) -> Type:
if is_dataclass(implementation):
return implementation() # Do not inject into dataclasses

constructor = inspect.signature(implementation.__init__)
params = constructor.parameters

Expand Down
24 changes: 24 additions & 0 deletions tests/unit_test/container/resolve/test_resolve_with_injection.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
from dataclasses import dataclass

from dependency_injection.container import DependencyContainer
from unit_test.unit_test_case import UnitTestCase

Expand Down Expand Up @@ -25,3 +27,25 @@ def __init__(self, engine: Engine):
self.assertIsInstance(resolved_dependency, Car)
self.assertIsNotNone(resolved_dependency.engine)
self.assertIsInstance(resolved_dependency.engine, Engine)

def test_resolve_skips_constructor_injection_for_dataclass(self):
# arrange
class Engine:
pass

@dataclass
class Car:
engine: Engine = None

dependency_container = DependencyContainer.get_instance()
dependency_container.register_transient(Engine)
dependency_container.register_transient(Car)

# act
resolved_dependency = dependency_container.resolve(Car)

# assert
self.assertIsInstance(resolved_dependency, Car)
self.assertIsNone(
resolved_dependency.engine
) # Should be None since injection is skipped

0 comments on commit 748d626

Please sign in to comment.