import 'dart:async'; import 'package:cherrypick/cherrypick.dart'; import 'package:meta/meta.dart'; class AppModule extends Module { @override void builder(Scope currentScope) { bind().withName('apiClientMock').toInstance(ApiClientMock()); bind().withName('apiClientImpl').toInstance(ApiClientImpl()); } } class FeatureModule extends Module { bool isMock; FeatureModule({required this.isMock}); @override void builder(Scope currentScope) { bind() .withName('networkRepo') .toProvide( () => NetworkDataRepository( currentScope.resolve( named: isMock ? 'apiClientMock' : 'apiClientImpl', ), ), ) .singleton(); bind().toProvide( () => DataBloc( currentScope.resolve(named: 'networkRepo'), ), ); } } void main() async { final scope = openRootScope().installModules([ AppModule(), ]); final subScope = scope .openSubScope('featureScope') .installModules([FeatureModule(isMock: true)]); final dataBloc = subScope.resolve(); dataBloc.data.listen((d) => print('Received data: $d'), onError: (e) => print('Error: $e'), onDone: () => print('DONE')); await dataBloc.fetchData(); } class DataBloc { final DataRepository _dataRepository; Stream get data => _dataController.stream; final StreamController _dataController = StreamController.broadcast(); DataBloc(this._dataRepository); Future fetchData() async { try { _dataController.sink.add(await _dataRepository.getData()); } catch (e) { _dataController.sink.addError(e); } } void dispose() { _dataController.close(); } } abstract class DataRepository { Future getData(); } class NetworkDataRepository implements DataRepository { final ApiClient _apiClient; final _token = 'token'; NetworkDataRepository(this._apiClient); @override Future getData() async => await _apiClient.sendRequest( url: 'www.google.com', token: _token, requestBody: {'type': 'data'}); } abstract class ApiClient { Future sendRequest({@required String url, String token, Map requestBody}); } class ApiClientMock implements ApiClient { @override Future sendRequest( {@required String? url, String? token, Map? requestBody}) async { return 'Local Data'; } } class ApiClientImpl implements ApiClient { @override Future sendRequest( {@required String? url, String? token, Map? requestBody}) async { return 'Network data'; } }