injectable
injectable copied to clipboard
PreResolve does not ensure dependent registrations are not asynchronous when it depends on an non-preresolved dependency.
Consider the following code:
@module
abstract class MyServiceRegistrations {
/// Example 1 (Working)
@singleton
@preResolve
Future<MyServiceA1> myServiceA1() async => MyServiceA1();
@singleton
MyServiceA2 myServiceA2(MyServiceA1 s1) => MyServiceA2();
/// Example 2 (Broken)
@singleton
Future<MyServiceB0> myServiceB0() async => MyServiceB0();
@singleton
@preResolve
Future<MyServiceB1> myServiceB1(MyServiceB0 s0) async => MyServiceB1();
@singleton
MyServiceB2 myServiceB2(MyServiceB1 s1) => MyServiceB2();
}
which generates:
extension GetItInjectableX on _i1.GetIt {
// initializes the registration of main-scope dependencies inside of GetIt
Future<_i1.GetIt> init({
String? environment,
_i2.EnvironmentFilter? environmentFilter,
}) async {
final gh = _i2.GetItHelper(
this,
environment,
environmentFilter,
);
final myServiceRegistrations = _$MyServiceRegistrations();
await gh.singletonAsync<_i5.MyServiceA1>(
() => myServiceRegistrations.myServiceA1(),
preResolve: true,
);
gh.singletonAsync<_i5.MyServiceB0>(
() => myServiceRegistrations.myServiceB0());
gh.singleton<_i5.MyServiceA2>(
() => myServiceRegistrations.myServiceA2(gh<_i5.MyServiceA1>()));
await gh.singletonAsync<_i5.MyServiceB1>(
() async =>
myServiceRegistrations.myServiceB1(await getAsync<_i5.MyServiceB0>()),
preResolve: true,
);
gh.singletonAsync<_i5.MyServiceB2>(() async =>
myServiceRegistrations.myServiceB2(await getAsync<_i5.MyServiceB1>()));
return this;
}
}
As you can see, it works for the first example: A1 is pre-resolved and A2 is registered as singleton
(synchronously), which is correct.
However, for the second example, it does not work. Because B1 (which IS preresolved) now depends on B0 (which is NOT), B2 is registered using singletonAsync
(asynchronously). In my opinion, this is wrong, as since B1 is still pre-resolved, B2 can be synchronous and should be, because it does not know or care about B0.