如何用Riverpod实现依赖注入?如何使其像get_it一样通过locator调用?
用Riverpod实现类似GetIt的全局Locator方案
1. 搭建全局Locator基础
首先创建全局的ProviderContainer实例,再封装一个locator函数来统一获取依赖,替代重复的ref.read():
import 'package:flutter_riverpod/flutter_riverpod.dart'; // 全局单例Provider容器 final globalContainer = ProviderContainer(); // 泛型Locator函数,参数为目标Provider,返回对应类型的实例 T locator<T>(ProviderBase<T> provider) { return globalContainer.read(provider); }
2. 构造函数参数类型的确定逻辑
构造函数的参数类型就是你要注入的依赖的实际类型,而非Provider类型。举个具体例子:
假设你有一个业务服务的Provider:
// 定义AuthService及其Provider class AuthService { void performLogin(String email, String password) { // 登录逻辑实现 } } final authServiceProvider = Provider<AuthService>((ref) => AuthService());
那么在需要依赖AuthService的类中,构造函数参数直接声明为AuthService类型,通过locator注入实例:
class LoginViewModel { final AuthService _authService; // 参数类型为AuthService,直接用locator获取实例传入 LoginViewModel(this._authService); void login(String email, String password) { _authService.performLogin(email, password); } } // 使用ViewModel时 final loginVM = LoginViewModel(locator(authServiceProvider));
3. 确保全局容器与Widget树同步
如果你的Flutter应用中同时使用Widget树内的ref和全局locator,要把ProviderScope的容器指定为全局实例,避免依赖实例不一致:
void main() { runApp( ProviderScope( container: globalContainer, child: const MyApp(), ), ); }
这样不管是在Widget组件里用ref.read,还是在ViewModel、工具类里用locator,拿到的都是同一个依赖实例。
内容的提问来源于stack exchange,提问作者Abdullah Mohamed
相关产品推荐
相关产品推荐

