1010from ellar .core .modules import ModuleRefBase
1111from ellar .di import EllarInjector , ProviderConfig
1212from ellar .reflect import reflect
13- from ellar .utils import get_unique_type
13+ from ellar .threading .sync_worker import execute_async_context_manager
14+ from ellar .utils import get_name , get_unique_type
1415from starlette .routing import BaseRoute , Host , Mount
1516
17+ from .context import ApplicationContext
1618from .main import App
1719from .services import EllarAppService
1820
@@ -118,13 +120,15 @@ def _build_modules(
118120 return routes
119121
120122 @classmethod
123+ @t .no_type_check
121124 def _create_app (
122125 cls ,
123126 module : t .Type [t .Union [ModuleBase , t .Any ]],
124127 global_guards : t .Optional [
125128 t .List [t .Union [t .Type ["GuardCanActivate" ], "GuardCanActivate" ]]
126129 ] = None ,
127130 config_module : t .Union [str , t .Dict , None ] = None ,
131+ injector : t .Optional [EllarInjector ] = None ,
128132 ) -> App :
129133 def _get_config_kwargs () -> t .Dict :
130134 if config_module is None :
@@ -141,45 +145,54 @@ def _get_config_kwargs() -> t.Dict:
141145
142146 config = Config (app_configured = True , ** _get_config_kwargs ())
143147
144- injector = EllarInjector (auto_bind = config .INJECTOR_AUTO_BIND )
148+ injector = EllarInjector (auto_bind = config .INJECTOR_AUTO_BIND , parent = injector )
145149 injector .container .register_instance (config , concrete_type = Config )
146150
147151 service = EllarAppService (injector , config )
148152 service .register_core_services ()
149153
150- routes = cls ._build_modules (app_module = module , injector = injector , config = config )
151-
152- app = App (
153- routes = routes ,
154- config = config ,
155- injector = injector ,
156- lifespan = config .DEFAULT_LIFESPAN_HANDLER ,
157- global_guards = global_guards ,
158- )
159-
160- for module_config in reversed (list (injector .get_app_dependent_modules ())):
161- if injector .get_module (module_config .module ): # pragma: no cover
162- continue
154+ with execute_async_context_manager (ApplicationContext (injector )) as context :
155+ routes = cls ._build_modules (
156+ app_module = module , injector = injector , config = config
157+ )
163158
164- module_ref = module_config .configure_with_factory (
165- config , injector .container
159+ app = App (
160+ routes = routes ,
161+ config = config ,
162+ injector = injector ,
163+ lifespan = config .DEFAULT_LIFESPAN_HANDLER ,
164+ global_guards = global_guards ,
166165 )
166+ # tag application instance by ApplicationModule name
167+ context .injector .container .register_instance (app , App , tag = get_name (module ))
168+
169+ for module_config in reversed (
170+ list (context .injector .get_app_dependent_modules ())
171+ ):
172+ if context .injector .get_module (
173+ module_config .module
174+ ): # pragma: no cover
175+ continue
176+
177+ module_ref = module_config .configure_with_factory (
178+ config , context .injector .container
179+ )
167180
168- assert isinstance (
169- module_ref , ModuleRefBase
170- ), f"{ module_config .module } is not properly configured."
181+ assert isinstance (
182+ module_ref , ModuleRefBase
183+ ), f"{ module_config .module } is not properly configured."
171184
172- injector .add_module (module_ref )
173- app .router .extend (module_ref .routes )
185+ context . injector .add_module (module_ref )
186+ app .router .extend (module_ref .routes )
174187
175- # app.setup_jinja_environment
176- app .setup_jinja_environment ()
188+ # app.setup_jinja_environment
189+ app .setup_jinja_environment ()
177190
178- for module , module_ref in app .injector .get_modules ().items ():
179- module_ref .run_module_register_services ()
191+ for module , module_ref in context .injector .get_modules ().items ():
192+ module_ref .run_module_register_services ()
180193
181- if issubclass (module , IApplicationReady ):
182- app .injector .get (module ).on_ready (app )
194+ if issubclass (module , IApplicationReady ):
195+ context .injector .get (module ).on_ready (app )
183196
184197 return app
185198
@@ -198,6 +211,7 @@ def create_app(
198211 ] = None ,
199212 commands : t .Sequence [t .Union [click .Command , click .Group , t .Any ]] = (),
200213 config_module : t .Union [str , t .Dict , None ] = None ,
214+ injector : t .Optional [EllarInjector ] = None ,
201215 ) -> App :
202216 module = Module (
203217 controllers = controllers ,
@@ -211,11 +225,13 @@ def create_app(
211225 )
212226 app_factory_module = get_unique_type ()
213227 module (app_factory_module )
214- return cls ._create_app (
228+ app = cls ._create_app (
215229 module = app_factory_module ,
216230 config_module = config_module ,
217231 global_guards = global_guards ,
232+ injector = injector ,
218233 )
234+ return t .cast (App , app )
219235
220236 @classmethod
221237 def create_from_app_module (
@@ -224,8 +240,14 @@ def create_from_app_module(
224240 global_guards : t .Optional [
225241 t .List [t .Union [t .Type ["GuardCanActivate" ], "GuardCanActivate" ]]
226242 ] = None ,
243+ injector : t .Optional [EllarInjector ] = None ,
227244 config_module : t .Union [str , t .Dict , None ] = None ,
228245 ) -> App :
229- return cls ._create_app (
230- module , config_module = config_module , global_guards = global_guards
246+ app = cls ._create_app (
247+ module ,
248+ config_module = config_module ,
249+ global_guards = global_guards ,
250+ injector = injector ,
231251 )
252+
253+ return t .cast (App , app )
0 commit comments