orionis 0.404.0__py3-none-any.whl → 0.406.0__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 (165) hide show
  1. orionis/console/base/command.py +57 -50
  2. orionis/console/base/contracts/command.py +68 -0
  3. orionis/console/dynamic/contracts/progress_bar.py +3 -3
  4. orionis/console/dynamic/progress_bar.py +8 -8
  5. orionis/console/output/console.py +8 -2
  6. orionis/console/output/contracts/console.py +1 -1
  7. orionis/container/container.py +2 -2
  8. orionis/container/context/scope.py +4 -1
  9. orionis/container/contracts/service_provider.py +2 -2
  10. orionis/container/entities/binding.py +31 -44
  11. orionis/container/enums/lifetimes.py +22 -1
  12. orionis/container/facades/facade.py +1 -2
  13. orionis/container/providers/service_provider.py +2 -2
  14. orionis/foundation/application.py +542 -248
  15. orionis/foundation/config/app/entities/app.py +107 -90
  16. orionis/foundation/config/auth/entities/auth.py +4 -33
  17. orionis/foundation/config/cache/entities/cache.py +18 -41
  18. orionis/foundation/config/cache/entities/file.py +8 -35
  19. orionis/foundation/config/cache/entities/stores.py +17 -38
  20. orionis/foundation/config/cors/entities/cors.py +41 -54
  21. orionis/foundation/config/database/entities/connections.py +40 -56
  22. orionis/foundation/config/database/entities/database.py +11 -38
  23. orionis/foundation/config/database/entities/mysql.py +48 -76
  24. orionis/foundation/config/database/entities/oracle.py +30 -57
  25. orionis/foundation/config/database/entities/pgsql.py +45 -61
  26. orionis/foundation/config/database/entities/sqlite.py +26 -53
  27. orionis/foundation/config/filesystems/entitites/aws.py +28 -49
  28. orionis/foundation/config/filesystems/entitites/disks.py +27 -47
  29. orionis/foundation/config/filesystems/entitites/filesystems.py +15 -37
  30. orionis/foundation/config/filesystems/entitites/local.py +9 -35
  31. orionis/foundation/config/filesystems/entitites/public.py +14 -41
  32. orionis/foundation/config/logging/entities/channels.py +56 -86
  33. orionis/foundation/config/logging/entities/chunked.py +18 -10
  34. orionis/foundation/config/logging/entities/daily.py +17 -9
  35. orionis/foundation/config/logging/entities/hourly.py +15 -7
  36. orionis/foundation/config/logging/entities/logging.py +12 -18
  37. orionis/foundation/config/logging/entities/monthly.py +16 -8
  38. orionis/foundation/config/logging/entities/stack.py +15 -7
  39. orionis/foundation/config/logging/entities/weekly.py +15 -7
  40. orionis/foundation/config/logging/validators/path.py +6 -0
  41. orionis/foundation/config/mail/entities/file.py +9 -36
  42. orionis/foundation/config/mail/entities/mail.py +22 -40
  43. orionis/foundation/config/mail/entities/mailers.py +29 -44
  44. orionis/foundation/config/mail/entities/smtp.py +47 -48
  45. orionis/foundation/config/queue/entities/brokers.py +19 -41
  46. orionis/foundation/config/queue/entities/database.py +24 -46
  47. orionis/foundation/config/queue/entities/queue.py +28 -40
  48. orionis/foundation/config/roots/paths.py +272 -468
  49. orionis/foundation/config/session/entities/session.py +23 -53
  50. orionis/foundation/config/startup.py +165 -135
  51. orionis/foundation/config/testing/entities/testing.py +137 -122
  52. orionis/foundation/config/testing/enums/__init__.py +6 -2
  53. orionis/foundation/config/testing/enums/drivers.py +16 -0
  54. orionis/foundation/config/testing/enums/verbosity.py +18 -0
  55. orionis/foundation/contracts/application.py +152 -362
  56. orionis/foundation/providers/console_provider.py +24 -2
  57. orionis/foundation/providers/dumper_provider.py +24 -2
  58. orionis/foundation/providers/logger_provider.py +24 -2
  59. orionis/foundation/providers/path_resolver_provider.py +25 -2
  60. orionis/foundation/providers/progress_bar_provider.py +24 -2
  61. orionis/foundation/providers/testing_provider.py +39 -0
  62. orionis/foundation/providers/workers_provider.py +24 -2
  63. orionis/metadata/framework.py +1 -1
  64. orionis/services/environment/helpers/functions.py +1 -2
  65. orionis/services/environment/key/__init__.py +0 -0
  66. orionis/services/environment/key/key_generator.py +37 -0
  67. orionis/services/log/handlers/filename.py +64 -0
  68. orionis/services/log/handlers/size_rotating.py +9 -40
  69. orionis/services/log/handlers/timed_rotating.py +9 -41
  70. orionis/services/log/log_service.py +9 -52
  71. orionis/support/entities/__init__.py +0 -0
  72. orionis/support/entities/base.py +104 -0
  73. orionis/support/facades/testing.py +15 -0
  74. orionis/support/facades/workers.py +1 -1
  75. orionis/test/cases/asynchronous.py +0 -11
  76. orionis/test/cases/synchronous.py +0 -9
  77. orionis/test/contracts/dumper.py +11 -4
  78. orionis/test/contracts/kernel.py +5 -110
  79. orionis/test/contracts/logs.py +27 -65
  80. orionis/test/contracts/printer.py +16 -128
  81. orionis/test/contracts/test_result.py +100 -0
  82. orionis/test/contracts/unit_test.py +87 -150
  83. orionis/test/core/unit_test.py +608 -554
  84. orionis/test/entities/result.py +22 -2
  85. orionis/test/enums/__init__.py +0 -2
  86. orionis/test/enums/status.py +14 -9
  87. orionis/test/exceptions/config.py +9 -1
  88. orionis/test/exceptions/failure.py +34 -11
  89. orionis/test/exceptions/persistence.py +10 -2
  90. orionis/test/exceptions/runtime.py +9 -1
  91. orionis/test/exceptions/value.py +13 -1
  92. orionis/test/kernel.py +87 -289
  93. orionis/test/output/dumper.py +82 -18
  94. orionis/test/output/printer.py +399 -156
  95. orionis/test/records/logs.py +203 -82
  96. orionis/test/validators/__init__.py +33 -0
  97. orionis/test/validators/base_path.py +45 -0
  98. orionis/test/validators/execution_mode.py +45 -0
  99. orionis/test/validators/fail_fast.py +37 -0
  100. orionis/test/validators/folder_path.py +34 -0
  101. orionis/test/validators/module_name.py +31 -0
  102. orionis/test/validators/name_pattern.py +40 -0
  103. orionis/test/validators/pattern.py +36 -0
  104. orionis/test/validators/persistent.py +42 -0
  105. orionis/test/validators/persistent_driver.py +43 -0
  106. orionis/test/validators/print_result.py +37 -0
  107. orionis/test/validators/tags.py +37 -0
  108. orionis/test/validators/throw_exception.py +39 -0
  109. orionis/test/validators/verbosity.py +37 -0
  110. orionis/test/validators/web_report.py +35 -0
  111. orionis/test/validators/workers.py +31 -0
  112. orionis/test/view/render.py +48 -54
  113. {orionis-0.404.0.dist-info → orionis-0.406.0.dist-info}/METADATA +1 -1
  114. {orionis-0.404.0.dist-info → orionis-0.406.0.dist-info}/RECORD +160 -108
  115. tests/container/__init__.py +0 -0
  116. tests/container/context/__init__.py +0 -0
  117. tests/container/context/test_manager.py +27 -0
  118. tests/container/context/test_scope.py +23 -0
  119. tests/container/entities/__init__.py +0 -0
  120. tests/container/entities/test_binding.py +133 -0
  121. tests/container/enums/__init__.py +0 -0
  122. tests/container/enums/test_lifetimes.py +63 -0
  123. tests/container/facades/__init__.py +0 -0
  124. tests/container/facades/test_facade.py +61 -0
  125. tests/container/mocks/__init__.py +0 -0
  126. tests/container/mocks/mock_complex_classes.py +482 -0
  127. tests/container/mocks/mock_simple_classes.py +32 -0
  128. tests/container/providers/__init__.py +0 -0
  129. tests/container/providers/test_providers.py +48 -0
  130. tests/container/resolver/__init__.py +0 -0
  131. tests/container/resolver/test_resolver.py +55 -0
  132. tests/container/test_container.py +254 -0
  133. tests/container/test_singleton.py +98 -0
  134. tests/container/test_thread_safety.py +217 -0
  135. tests/container/validators/__init__.py +0 -0
  136. tests/container/validators/test_implements.py +140 -0
  137. tests/container/validators/test_is_abstract_class.py +99 -0
  138. tests/container/validators/test_is_callable.py +73 -0
  139. tests/container/validators/test_is_concrete_class.py +97 -0
  140. tests/container/validators/test_is_instance.py +105 -0
  141. tests/container/validators/test_is_not_subclass.py +117 -0
  142. tests/container/validators/test_is_subclass.py +115 -0
  143. tests/container/validators/test_is_valid_alias.py +113 -0
  144. tests/container/validators/test_lifetime.py +75 -0
  145. tests/foundation/config/logging/test_foundation_config_logging_chunked.py +12 -34
  146. tests/foundation/config/logging/test_foundation_config_logging_daily.py +11 -11
  147. tests/foundation/config/logging/test_foundation_config_logging_hourly.py +7 -8
  148. tests/foundation/config/logging/test_foundation_config_logging_monthly.py +7 -10
  149. tests/foundation/config/logging/test_foundation_config_logging_stack.py +6 -11
  150. tests/foundation/config/logging/test_foundation_config_logging_weekly.py +6 -5
  151. tests/foundation/config/testing/test_foundation_config_testing.py +1 -1
  152. tests/metadata/test_metadata_framework.py +18 -18
  153. tests/testing/test_testing_result.py +117 -117
  154. tests/testing/test_testing_unit.py +209 -209
  155. orionis/foundation/config/base.py +0 -112
  156. orionis/test/arguments/parser.py +0 -187
  157. orionis/test/contracts/parser.py +0 -43
  158. orionis/test/entities/arguments.py +0 -38
  159. orionis/test/enums/execution_mode.py +0 -16
  160. /orionis/{test/arguments → console/base/contracts}/__init__.py +0 -0
  161. /orionis/foundation/config/testing/enums/{test_mode.py → mode.py} +0 -0
  162. {orionis-0.404.0.dist-info → orionis-0.406.0.dist-info}/WHEEL +0 -0
  163. {orionis-0.404.0.dist-info → orionis-0.406.0.dist-info}/licenses/LICENCE +0 -0
  164. {orionis-0.404.0.dist-info → orionis-0.406.0.dist-info}/top_level.txt +0 -0
  165. {orionis-0.404.0.dist-info → orionis-0.406.0.dist-info}/zip-safe +0 -0
@@ -1,85 +1,92 @@
1
- import argparse
1
+ from typing import Any, Dict
2
2
  from orionis.console.dynamic.progress_bar import ProgressBar
3
3
  from orionis.console.output.console import Console
4
+ from orionis.console.base.contracts.command import IBaseCommand
4
5
 
5
- class BaseCommand(Console, ProgressBar):
6
+ class BaseCommand(Console, ProgressBar, IBaseCommand):
6
7
  """
7
- Base abstract class for implementing console commands in the Orionis framework.
8
+ Abstract base class for console commands in Orionis.
8
9
 
9
- This class provides a foundation for creating command-line interface commands by
10
- combining console output capabilities and progress bar functionality. It serves
11
- as an abstract base that enforces the implementation of command-specific logic
12
- while providing common argument handling functionality.
13
-
14
- The class inherits from both Console and ProgressBar, providing access to:
15
- - Console output methods for displaying messages, errors, and formatted text
16
- - Progress bar functionality for long-running operations
17
- - Argument parsing and management capabilities
10
+ Inherits from Console and ProgressBar, allowing commands to:
11
+ - Display messages, errors, and formatted text in the console.
12
+ - Manage progress bars for long-running tasks.
13
+ - Access and manipulate parsed arguments from the command line.
18
14
 
19
15
  Attributes
20
16
  ----------
21
17
  args : dict
22
- Dictionary containing the parsed command-line arguments passed to the command.
23
- This is populated by calling the `setArgs` method with either an
24
- `argparse.Namespace` object or a dictionary.
18
+ Dictionary containing the parsed arguments for the command. Set via the setArgs method.
25
19
 
26
20
  Methods
27
21
  -------
28
22
  handle()
29
- Abstract method that must be implemented by subclasses to define the
30
- command's execution logic.
31
- setArgs(args)
32
- Sets the command arguments from either an argparse.Namespace or dict.
23
+ Must be implemented by each subclass to define the main logic of the command.
24
+ argument(key)
25
+ Retrieves the value of a specific argument by key.
26
+ arguments()
27
+ Returns all parsed arguments as a dictionary.
33
28
  """
34
29
 
35
- args = {}
30
+ args: Dict[str, Any] = {}
36
31
 
37
32
  def handle(self):
38
33
  """
39
- Execute the command's main logic.
34
+ Main entry point for command execution.
40
35
 
41
- This abstract method defines the entry point for command execution and must
42
- be overridden in all subclasses. It contains the core functionality that
43
- the command should perform when invoked.
36
+ This method must be overridden in each subclass to define the specific logic of the command.
37
+ Access parsed arguments via self.args and use console and progress bar methods as needed.
44
38
 
45
- The method has access to:
46
- - `self.args`: Dictionary of parsed command-line arguments
47
- - Console output methods inherited from Console class
48
- - Progress bar methods inherited from ProgressBar class
39
+ Example:
40
+ def handle(self):
41
+ self.write("Processing...")
42
+ value = self.argument("key")
43
+ # custom logic
49
44
 
50
45
  Raises
51
46
  ------
52
47
  NotImplementedError
53
- Always raised when called on the base class, as this method must be
54
- implemented by concrete subclasses to define command-specific behavior.
48
+ Always raised in the base class. Subclasses must implement this method.
55
49
  """
56
- raise NotImplementedError("The 'handle' method must be implemented in the child class.")
50
+ raise NotImplementedError("The 'handle' method must be implemented in the subclass.")
57
51
 
58
- def setArgs(self, args) -> None:
52
+ def argument(self, key: str):
59
53
  """
60
- Set command arguments from parsed command-line input.
61
-
62
- This method accepts command arguments in multiple formats and normalizes
63
- them into a dictionary format stored in `self.args`. It provides
64
- flexibility in how arguments are passed to the command while ensuring
65
- consistent internal representation.
54
+ Retrieves the value of a specific argument by its key.
66
55
 
67
56
  Parameters
68
57
  ----------
69
- args : argparse.Namespace or dict
70
- The command arguments to be set. Can be either:
71
- - argparse.Namespace: Result of argparse.ArgumentParser.parse_args()
72
- - dict: Dictionary containing argument name-value pairs
58
+ key : str
59
+ Name of the argument to retrieve.
60
+
61
+ Returns
62
+ -------
63
+ any or None
64
+ Value associated with the key, or None if it does not exist or arguments are not set.
73
65
 
74
66
  Raises
75
67
  ------
76
68
  ValueError
77
- If `args` is neither an argparse.Namespace nor a dict, indicating
78
- an unsupported argument type was passed.
69
+ If the key is not a string or if arguments are not a dictionary.
70
+
71
+ Example:
72
+ value = self.argument("user")
73
+ """
74
+ if not isinstance(key, str):
75
+ raise ValueError("Argument key must be a string.")
76
+ if not isinstance(self.args, dict):
77
+ raise ValueError("Arguments must be a dictionary.")
78
+ return self.args.get(key)
79
+
80
+ def arguments(self) -> dict:
81
+ """
82
+ Returns all parsed arguments as a dictionary.
83
+
84
+ Returns
85
+ -------
86
+ dict
87
+ Dictionary containing all arguments received by the command. If no arguments, returns an empty dictionary.
88
+
89
+ Example:
90
+ args = self.arguments()
79
91
  """
80
- if isinstance(args, argparse.Namespace):
81
- self.args = vars(args)
82
- elif isinstance(args, dict):
83
- self.args = args
84
- else:
85
- raise ValueError("Invalid argument type. Expected 'argparse.Namespace' or 'dict'.")
92
+ return dict(self.args) if isinstance(self.args, dict) else {}
@@ -0,0 +1,68 @@
1
+
2
+ from abc import ABC, abstractmethod
3
+ from typing import Any, Dict
4
+
5
+ class IBaseCommand(ABC):
6
+ """
7
+ Abstract base contract for console commands in Orionis.
8
+
9
+ Inherits from ABC and defines the required interface for all console commands:
10
+ - Stores parsed command-line arguments.
11
+ - Requires implementation of main execution logic and argument accessors.
12
+
13
+ Attributes
14
+ ----------
15
+ args : Dict[str, Any]
16
+ Dictionary containing the parsed arguments for the command. Should be set by the command parser.
17
+ """
18
+
19
+ args: Dict[str, Any] = {}
20
+
21
+ @abstractmethod
22
+ def handle(self):
23
+ """
24
+ Main entry point for command execution.
25
+
26
+ This method must be overridden in each subclass to define the specific logic of the command.
27
+ Access parsed arguments via self.args and use console/output methods as needed.
28
+
29
+ Raises
30
+ ------
31
+ NotImplementedError
32
+ Always raised in the base class. Subclasses must implement this method.
33
+ """
34
+ pass
35
+
36
+ @abstractmethod
37
+ def argument(self, key: str) -> Any:
38
+ """
39
+ Retrieves the value of a specific argument by its key.
40
+
41
+ Parameters
42
+ ----------
43
+ key : str
44
+ Name of the argument to retrieve.
45
+
46
+ Returns
47
+ -------
48
+ Any or None
49
+ Value associated with the key, or None if it does not exist or arguments are not set.
50
+
51
+ Raises
52
+ ------
53
+ ValueError
54
+ If the key is not a string or if arguments are not a dictionary.
55
+ """
56
+ pass
57
+
58
+ @abstractmethod
59
+ def arguments(self) -> Dict[str, Any]:
60
+ """
61
+ Returns all parsed arguments as a dictionary.
62
+
63
+ Returns
64
+ -------
65
+ dict
66
+ Dictionary containing all arguments received by the command. If no arguments, returns an empty dictionary.
67
+ """
68
+ pass
@@ -19,7 +19,7 @@ class IProgressBar(ABC):
19
19
  """
20
20
 
21
21
  @abstractmethod
22
- def start(self):
22
+ def start(self) -> None:
23
23
  """
24
24
  Initializes the progress bar.
25
25
 
@@ -34,7 +34,7 @@ class IProgressBar(ABC):
34
34
  pass
35
35
 
36
36
  @abstractmethod
37
- def advance(self, increment: int):
37
+ def advance(self, increment: int) -> None:
38
38
  """
39
39
  Advances the progress bar by a given increment.
40
40
 
@@ -51,7 +51,7 @@ class IProgressBar(ABC):
51
51
  pass
52
52
 
53
53
  @abstractmethod
54
- def finish(self):
54
+ def finish(self) -> None:
55
55
  """
56
56
  Completes the progress bar.
57
57
 
@@ -34,7 +34,7 @@ class ProgressBar(IProgressBar):
34
34
  Completes the progress bar and moves to a new line.
35
35
  """
36
36
 
37
- def __init__(self, total=100, width=50):
37
+ def __init__(self, total=100, width=50) -> None:
38
38
  """
39
39
  Constructs all the necessary attributes for the progress bar object.
40
40
 
@@ -49,7 +49,7 @@ class ProgressBar(IProgressBar):
49
49
  self.bar_width = width
50
50
  self.progress = 0
51
51
 
52
- def _update_bar(self):
52
+ def __updateBar(self) -> None:
53
53
  """
54
54
  Updates the visual representation of the progress bar.
55
55
 
@@ -64,16 +64,16 @@ class ProgressBar(IProgressBar):
64
64
  sys.stdout.write("\r" + bar)
65
65
  sys.stdout.flush()
66
66
 
67
- def start(self):
67
+ def start(self) -> None:
68
68
  """
69
69
  Initializes the progress bar to the starting state.
70
70
 
71
71
  This method resets the progress to zero and displays the initial bar.
72
72
  """
73
73
  self.progress = 0
74
- self._update_bar()
74
+ self.__updateBar()
75
75
 
76
- def advance(self, increment=1):
76
+ def advance(self, increment=1) -> None:
77
77
  """
78
78
  Advances the progress bar by a specific increment.
79
79
 
@@ -85,9 +85,9 @@ class ProgressBar(IProgressBar):
85
85
  self.progress += increment
86
86
  if self.progress > self.total:
87
87
  self.progress = self.total
88
- self._update_bar()
88
+ self.__updateBar()
89
89
 
90
- def finish(self):
90
+ def finish(self) -> None:
91
91
  """
92
92
  Completes the progress bar.
93
93
 
@@ -95,6 +95,6 @@ class ProgressBar(IProgressBar):
95
95
  and moves the cursor to a new line for cleaner output.
96
96
  """
97
97
  self.progress = self.total
98
- self._update_bar()
98
+ self.__updateBar()
99
99
  sys.stdout.write("\n")
100
100
  sys.stdout.flush()
@@ -537,7 +537,10 @@ class Console(IConsole):
537
537
  """
538
538
  if message:
539
539
  self.success(message)
540
- sys.exit(0)
540
+ try:
541
+ sys.exit(0)
542
+ except SystemExit:
543
+ os._exit(0)
541
544
 
542
545
  def exitError(self, message: str = None) -> None:
543
546
  """
@@ -550,4 +553,7 @@ class Console(IConsole):
550
553
  """
551
554
  if message:
552
555
  self.error(message)
553
- sys.exit(1)
556
+ try:
557
+ sys.exit(0)
558
+ except SystemExit:
559
+ os._exit(0)
@@ -1,5 +1,5 @@
1
1
  from abc import ABC, abstractmethod
2
- from typing import List, Union, Optional
2
+ from typing import List, Optional
3
3
 
4
4
  class IConsole(ABC):
5
5
  """
@@ -32,8 +32,8 @@ class Container(IContainer):
32
32
  """
33
33
  Creates and returns a singleton instance for each specific class.
34
34
 
35
- This method implements a truly thread-safe singleton pattern with proper
36
- inheritance support, ensuring that each class in the hierarchy has its own
35
+ This method implements a truly thread-safe singleton pattern with proper
36
+ inheritance support, ensuring that each class in the hierarchy has its own
37
37
  singleton instance. Uses double-checked locking with proper memory barriers.
38
38
 
39
39
  Returns
@@ -4,7 +4,10 @@ class ScopedContext:
4
4
  """
5
5
  Holds scoped instances for the current context.
6
6
  """
7
- _active_scope = contextvars.ContextVar("orionis_scope", default=None)
7
+ _active_scope = contextvars.ContextVar(
8
+ "orionis_scope",
9
+ default=None
10
+ )
8
11
 
9
12
  @classmethod
10
13
  def getCurrentScope(cls):
@@ -3,7 +3,7 @@ from abc import ABC, abstractmethod
3
3
  class IServiceProvider(ABC):
4
4
 
5
5
  @abstractmethod
6
- def register(self) -> None:
6
+ async def register(self) -> None:
7
7
  """
8
8
  Register services into the application container.
9
9
 
@@ -19,7 +19,7 @@ class IServiceProvider(ABC):
19
19
  pass
20
20
 
21
21
  @abstractmethod
22
- def boot(self) -> None:
22
+ async def boot(self) -> None:
23
23
  """
24
24
  Perform any post-registration bootstrapping or initialization.
25
25
 
@@ -1,14 +1,15 @@
1
- from dataclasses import asdict, dataclass, field, fields
1
+ from dataclasses import dataclass, field
2
2
  from orionis.container.enums.lifetimes import Lifetime
3
3
  from orionis.container.exceptions import OrionisContainerTypeError
4
+ from orionis.support.entities.base import BaseEntity
4
5
 
5
6
  @dataclass(unsafe_hash=True, kw_only=True)
6
- class Binding:
7
+ class Binding(BaseEntity):
7
8
 
8
9
  contract: type = field(
9
10
  default=None,
10
11
  metadata={
11
- "description": "Contrato de la clase concreta a inyectar.",
12
+ "description": "Contract of the concrete class to inject.",
12
13
  "default": None
13
14
  }
14
15
  )
@@ -16,7 +17,7 @@ class Binding:
16
17
  concrete: type = field(
17
18
  default=None,
18
19
  metadata={
19
- "description": "Clase concreta que implementa el contrato.",
20
+ "description": "Concrete class implementing the contract.",
20
21
  "default": None
21
22
  }
22
23
  )
@@ -24,7 +25,7 @@ class Binding:
24
25
  instance: object = field(
25
26
  default=None,
26
27
  metadata={
27
- "description": "Instancia concreta de la clase, si se proporciona.",
28
+ "description": "Concrete instance of the class, if provided.",
28
29
  "default": None
29
30
  }
30
31
  )
@@ -32,7 +33,7 @@ class Binding:
32
33
  function: callable = field(
33
34
  default=None,
34
35
  metadata={
35
- "description": "Función que se invoca para crear la instancia.",
36
+ "description": "Function invoked to create the instance.",
36
37
  "default": None
37
38
  }
38
39
  )
@@ -40,7 +41,7 @@ class Binding:
40
41
  lifetime: Lifetime = field(
41
42
  default=Lifetime.TRANSIENT,
42
43
  metadata={
43
- "description": "Tiempo de vida de la instancia.",
44
+ "description": "Lifetime of the instance.",
44
45
  "default": Lifetime.TRANSIENT
45
46
  }
46
47
  )
@@ -48,7 +49,7 @@ class Binding:
48
49
  enforce_decoupling: bool = field(
49
50
  default=False,
50
51
  metadata={
51
- "description": "Indica si se debe forzar el desacoplamiento entre contrato y concreta.",
52
+ "description": "Indicates whether to enforce decoupling between contract and concrete.",
52
53
  "default": False
53
54
  }
54
55
  )
@@ -56,69 +57,55 @@ class Binding:
56
57
  alias: str = field(
57
58
  default=None,
58
59
  metadata={
59
- "description": "Alias para resolver la dependencia desde el contenedor.",
60
+ "description": "Alias for resolving the dependency from the container.",
60
61
  "default": None
61
62
  }
62
63
  )
63
64
 
64
65
  def __post_init__(self):
65
66
  """
66
- Performs type validation of instance attributes after initialization.
67
+ Validates the types of specific instance attributes after object initialization.
68
+
69
+ This method ensures that:
70
+ - The 'lifetime' attribute is an instance of the `Lifetime` enum.
71
+ - The 'enforce_decoupling' attribute is a boolean.
72
+ - The 'alias' attribute is either a string or None.
73
+
74
+ If any of these conditions are not met, an `OrionisContainerTypeError` is raised to prevent improper usage.
67
75
 
68
76
  Parameters
69
77
  ----------
70
78
  None
71
79
 
80
+ Returns
81
+ -------
82
+ None
83
+ This method does not return any value. It raises an exception if validation fails.
84
+
72
85
  Raises
73
86
  ------
74
87
  OrionisContainerTypeError
75
- If 'lifetime' is not an instance of `Lifetime` (when not None).
88
+ If 'lifetime' is not an instance of `Lifetime`.
76
89
  OrionisContainerTypeError
77
90
  If 'enforce_decoupling' is not of type `bool`.
78
91
  OrionisContainerTypeError
79
92
  If 'alias' is not of type `str` or `None`.
80
93
  """
81
- if self.lifetime is not None and not isinstance(self.lifetime, Lifetime):
94
+
95
+ # Validate that 'lifetime' is an instance of Lifetime enum if provided
96
+ if self.lifetime and not isinstance(self.lifetime, Lifetime):
82
97
  raise OrionisContainerTypeError(
83
98
  f"The 'lifetime' attribute must be an instance of 'Lifetime', but received type '{type(self.lifetime).__name__}'."
84
99
  )
85
100
 
101
+ # Validate that 'enforce_decoupling' is a boolean
86
102
  if not isinstance(self.enforce_decoupling, bool):
87
103
  raise OrionisContainerTypeError(
88
104
  f"The 'enforce_decoupling' attribute must be of type 'bool', but received type '{type(self.enforce_decoupling).__name__}'."
89
105
  )
90
106
 
91
- if self.alias is not None and not isinstance(self.alias, str):
107
+ # Validate that 'alias' is either a string or None
108
+ if self.alias and not isinstance(self.alias, str):
92
109
  raise OrionisContainerTypeError(
93
110
  f"The 'alias' attribute must be of type 'str' or 'None', but received type '{type(self.alias).__name__}'."
94
- )
95
-
96
- def toDict(self) -> dict:
97
- """
98
- Convert the object to a dictionary representation.
99
- Returns:
100
- dict: A dictionary representation of the Dataclass object.
101
- """
102
- return asdict(self)
103
-
104
- def getFields(self):
105
- """
106
- Retrieves a list of field information for the current dataclass instance.
107
-
108
- Returns:
109
- list: A list of dictionaries, each containing details about a field:
110
- - name (str): The name of the field.
111
- - type (type): The type of the field.
112
- - default: The default value of the field, if specified; otherwise, the value from metadata or None.
113
- - metadata (mapping): The metadata associated with the field.
114
- """
115
- __fields = []
116
- for field in fields(self):
117
- __metadata = dict(field.metadata) or {}
118
- __fields.append({
119
- "name": field.name,
120
- "type": field.type.__name__ if hasattr(field.type, '__name__') else str(field.type),
121
- "default": field.default if (field.default is not None and '_MISSING_TYPE' not in str(field.default)) else __metadata.get('default', None),
122
- "metadata": __metadata
123
- })
124
- return __fields
111
+ )
@@ -1,8 +1,29 @@
1
1
  from enum import Enum, auto
2
2
 
3
3
  class Lifetime(Enum):
4
- """Defines the lifecycle types for dependency injection."""
4
+ """
5
+ Represents the lifecycle types used for dependency injection.
5
6
 
7
+ This enumeration defines how and when instances of a dependency are created and shared.
8
+
9
+ Attributes
10
+ ----------
11
+ TRANSIENT : Lifetime
12
+ A new instance is created and provided every time the dependency is requested.
13
+ SINGLETON : Lifetime
14
+ A single shared instance is created and used throughout the entire application lifetime.
15
+ SCOPED : Lifetime
16
+ An instance is created and shared within a defined scope (such as per request or session).
17
+
18
+ Returns
19
+ -------
20
+ Lifetime
21
+ An enumeration member representing the selected lifecycle type.
22
+ """
23
+
24
+ # A new instance is provided every time the dependency is requested.
6
25
  TRANSIENT = auto()
26
+ # A single shared instance is provided for the entire application lifetime.
7
27
  SINGLETON = auto()
28
+ # An instance is provided per scope (e.g., per request or session).
8
29
  SCOPED = auto()
@@ -98,5 +98,4 @@ class Facade(metaclass=FacadeMeta):
98
98
  )
99
99
 
100
100
  # Resolve the service instance from the container
101
- service_instance = cls._app.make(service_name, *args, **kwargs)
102
- return service_instance
101
+ return cls._app.make(service_name, *args, **kwargs)
@@ -31,7 +31,7 @@ class ServiceProvider(IServiceProvider):
31
31
  """
32
32
  self.app = app
33
33
 
34
- def register(self) -> None:
34
+ async def register(self) -> None:
35
35
  """
36
36
  Register services into the application container.
37
37
 
@@ -46,7 +46,7 @@ class ServiceProvider(IServiceProvider):
46
46
  """
47
47
  raise NotImplementedError("This method should be overridden in the subclass")
48
48
 
49
- def boot(self) -> None:
49
+ async def boot(self) -> None:
50
50
  """
51
51
  Perform any post-registration bootstrapping or initialization.
52
52