diff --git a/lib/get_it_impl.dart b/lib/get_it_impl.dart index a19b830..45fa185 100644 --- a/lib/get_it_impl.dart +++ b/lib/get_it_impl.dart @@ -171,7 +171,8 @@ class _ServiceFactory { /// returns an instance depending on the type of the registration if [async==false] T getObject(dynamic param1, dynamic param2) { assert( - !(factoryType != _ServiceFactoryType.alwaysNew && + !(![_ServiceFactoryType.alwaysNew, _ServiceFactoryType.cachedFactory] + .contains(factoryType) && (param1 != null || param2 != null)), 'You can only pass parameters to factories!', ); @@ -201,6 +202,8 @@ class _ServiceFactory { param2 == lastParam2) { return weakReferenceInstance!.target!; } else { + lastParam1 = param1 as P1?; + lastParam2 = param2 as P2?; T newInstance; if (creationFunctionParam != null) { newInstance = creationFunctionParam!(param1 as P1, param2 as P2); @@ -254,7 +257,8 @@ class _ServiceFactory { /// if [dependsOn.isNotEmpty]. Future getObjectAsync(dynamic param1, dynamic param2) async { assert( - !(factoryType != _ServiceFactoryType.alwaysNew && + !(![_ServiceFactoryType.alwaysNew, _ServiceFactoryType.cachedFactory] + .contains(factoryType) && (param1 != null || param2 != null)), 'You can only pass parameters to factories!', ); @@ -291,6 +295,8 @@ class _ServiceFactory { return Future.value(weakReferenceInstance!.target! as R); } else { if (creationFunctionParam != null) { + lastParam1 = param1 as P1?; + lastParam2 = param2 as P2?; return asyncCreationFunctionParam!(param1 as P1, param2 as P2) .then((value) { weakReferenceInstance = WeakReference(value); diff --git a/test/get_it_test.dart b/test/get_it_test.dart index fcadac5..113f50e 100644 --- a/test/get_it_test.dart +++ b/test/get_it_test.dart @@ -39,11 +39,13 @@ class TestClassDisposable extends TestBaseClass with Disposable { class TestClass2 {} -class TestClassParam { +class TestClassParam extends TestBaseClass { final String? param1; final int? param2; - TestClassParam({this.param1, this.param2}); + TestClassParam({this.param1, this.param2}) { + constructorCounter++; + } } class TestClassDisposableWithDependency with Disposable { @@ -216,6 +218,80 @@ void main() { GetIt.I.reset(); }); + test('register cached factory', () { + final getIt = GetIt.instance; + constructorCounter = 0; + getIt.registerCachedFactory(() => TestClass()); + final TestBaseClass instance1 = getIt(); + expect(instance1 is TestClass, true); + final instance2 = getIt.get(); + expect(getIt.isRegistered(), true); + expect(instance1, instance2); + expect(constructorCounter, 1); + }); + + test('register cached factory with one param ', () { + final getIt = GetIt.instance; + constructorCounter = 0; + getIt.registerCachedFactoryParam( + (s, _) => TestClassParam(param1: s), + ); + final instance1 = getIt(param1: 'abc'); + final instance2 = getIt(param1: 'abc'); + expect(instance1 is TestClassParam, true); + expect(instance1.param1, 'abc'); + expect(instance1, instance2); + expect(constructorCounter, 1); + }); + + test('register cached factory with different params', () { + final getIt = GetIt.instance; + constructorCounter = 0; + getIt.registerCachedFactoryParam( + (s, _) => TestClassParam(param1: s), + ); + final instance1 = getIt(param1: 'abc'); + final instance2 = getIt(param1: '123'); + expect(instance1 is TestClassParam, true); + expect(instance1.param1, 'abc'); + expect(instance2.param1, '123'); + expect(instance2 is TestClassParam, true); + expect(instance1, isNot(instance2)); + expect(constructorCounter, 2); + }); + + test('register cached factory with two equal params', () { + final getIt = GetIt.instance; + constructorCounter = 0; + getIt.registerCachedFactoryParam( + (f, s) => TestClassParam(param1: f, param2: s), + ); + final instance1 = getIt(param1: 'abc', param2: 1); + final instance2 = getIt(param1: 'abc', param2: 1); + expect(instance1 is TestClassParam, true); + expect(instance1.param1, 'abc'); + expect(instance1, instance2); + expect(constructorCounter, 1); + }); + + test('register cached factory with one different param out of two', () { + final getIt = GetIt.instance; + constructorCounter = 0; + getIt.registerCachedFactoryParam( + (f, s) => TestClassParam(param1: f, param2: s), + ); + final instance1 = getIt(param1: 'abc', param2: 1); + final instance2 = getIt(param1: 'abc', param2: 2); + expect(instance1 is TestClassParam, true); + expect(instance1.param1, 'abc'); + expect(instance1.param2, 1); + expect(instance2.param1, 'abc'); + expect(instance2.param2, 2); + expect(instance2 is TestClassParam, true); + expect(instance1, isNot(instance2)); + expect(constructorCounter, 2); + }); + test('register constant', () { final getIt = GetIt.instance; constructorCounter = 0;