尧图网络 高端网站定制 · 原创设计
免费咨询热线
400-888-6620
免费获取方案
鸿蒙Flutter 依赖注入模式:使用Provider管理服务类
一、依赖注入概述依赖注入Dependency Injection简称DI是一种软件设计模式用于实现控制反转Inversion of Control简称IoC。在Flutter开发中依赖注入可以帮助我们解耦组件组件不直接创建依赖降低耦合度提高可测试性方便替换为mock对象进行测试简化维护集中管理依赖易于维护和替换实现复用同一个服务可以在多个组件中复用Provider不仅可以用于状态管理还可以作为依赖注入容器管理服务类的生命周期。二、创建服务类在使用Provider进行依赖注入之前我们需要先创建服务类。服务类通常是无状态的工具类提供特定的功能。2.1 日志服务classLogService{voidinfo(Stringmessage){debugPrint([INFO]$message);}voiderror(Stringmessage,[Object?error]){debugPrint([ERROR]$message:$error);}}2.2 存储服务classStorageService{String_data;FuturevoidsaveData(Stringdata)async{awaitFuture.delayed(constDuration(milliseconds:100));_datadata;}FutureStringloadData()async{awaitFuture.delayed(constDuration(milliseconds:100));return_data;}}2.3 API服务classApiService{FutureMapString,dynamicfetchProduct(Stringid)async{awaitFuture.delayed(constDuration(seconds:1));return{id:id,name:商品$id,price:99.9,};}}三、使用Provider注入服务使用Provider注入服务非常简单只需要在MultiProvider中声明即可MultiProvider(providers:[ProviderLogService(create:(_)LogService()),ProviderStorageService(create:(_)StorageService()),ProviderApiService(create:(_)ApiService()),ChangeNotifierProvider(create:(context)DataProvider(logService:context.readLogService(),storageService:context.readStorageService(),),),],child:constMyApp(),)3.1 注入不可变服务对于无状态的服务类使用Provider即可ProviderLogService(create:(_)LogService())3.2 注入可变状态对于需要管理状态的类使用ChangeNotifierProviderChangeNotifierProvider(create:(context)DataProvider(logService:context.readLogService(),storageService:context.readStorageService(),),)四、在Provider中使用依赖在ChangeNotifier中使用依赖注入的服务classDataProviderextendsChangeNotifier{finalLogService_logService;finalStorageService_storageService;String_data初始数据;DataProvider({requiredLogServicelogService,requiredStorageServicestorageService,}):_logServicelogService,_storageServicestorageService;Stringgetdata_data;FuturevoidupdateData(StringnewData)async{_logService.info(更新数据:$newData);_datanewData;await_storageService.saveData(newData);notifyListeners();}FuturevoidloadData()async{_logService.info(加载数据);_dataawait_storageService.loadData();notifyListeners();}}五、在Widget中使用服务在Widget中使用依赖注入的服务5.1 获取服务classProductDetailPageextendsStatelessWidget{constProductDetailPage({super.key});overrideWidgetbuild(BuildContextcontext){finallogServicecontext.readLogService();returnScaffold(appBar:AppBar(title:constText(商品详情)),body:Center(child:ElevatedButton(onPressed:(){logService.info(用户点击加入购物车);context.readCartProvider().addItem(1,商品,19.9);},child:constText(加入购物车),),),);}}5.2 注意事项使用context.readT()获取不需要监听的服务使用context.watchT()获取需要监听变化的状态服务必须在当前Provider之前声明依赖注入的服务默认是单例六、单例服务与工厂模式6.1 Provider默认创建单例Provider默认创建单例实例整个应用中只创建一次MultiProvider(providers:[Provider(create:(_)ApiService()),],child:constMyApp(),)6.2 使用Provider.value如果需要传入已存在的实例可以使用Provider.valuefinalapiServiceApiService();MultiProvider(providers:[Provider.value(value:apiService),],child:constMyApp(),)6.3 延迟初始化使用ProxyProvider进行延迟初始化只有在需要时才创建ProviderMultiProvider(providers:[Provider(create:(_)ApiService()),ChangeNotifierProxyProviderApiService,CartProvider(create:(context)CartProvider(apiService:context.read()),update:(context,apiService,cartProvider){returncartProvider!..updateApiService(apiService);},),],child:constMyApp(),)七、依赖注入的优势优势说明解耦组件不直接创建依赖降低耦合可测试方便替换为mock对象进行测试可维护集中管理依赖易于维护可复用同一个服务可以在多个组件中复用生命周期管理Provider自动管理服务生命周期八、最佳实践8.1 将服务类与状态类分离服务类应该是无状态的工具类状态类应该只负责管理状态// 服务类 - 无状态classApiService{FutureUserfetchUser(Stringid)async{...}}// 状态类 - 管理状态classUserProviderextendsChangeNotifier{finalApiService_apiService;User?_user;UserProvider({requiredApiServiceapiService}):_apiServiceapiService;}8.2 使用Provider注入不可变服务对于无状态的服务使用Provider而不是ChangeNotifierProviderProviderLogService(create:(_)LogService())8.3 使用ChangeNotifierProvider管理可变状态对于需要管理状态的类使用ChangeNotifierProviderChangeNotifierProvider(create:(_)CartProvider())8.4 按依赖顺序声明Provider依赖其他Provider的Provider必须在被依赖的Provider之后声明MultiProvider(providers:[ProviderApiService(create:(_)ApiService()),// CartProvider依赖ApiService必须在ApiService之后ChangeNotifierProvider(create:(context)CartProvider(apiService:context.read()),),],child:constMyApp(),)8.5 在构造函数中注入依赖不要在方法中直接使用context.read而是在构造函数中注入依赖classCartProviderextendsChangeNotifier{finalApiService_apiService;// 正确在构造函数中注入CartProvider({requiredApiServiceapiService}):_apiServiceapiService;voidfetchProducts(){// 使用注入的依赖_apiService.fetchProducts();}}九、代码示例9.1 创建一个依赖注入演示页面classDependencyInjectionPageextendsStatelessWidget{constDependencyInjectionPage({super.key});overrideWidgetbuild(BuildContextcontext){returnMultiProvider(providers:[ProviderLogService(create:(_)LogService()),ProviderStorageService(create:(_)StorageService()),ChangeNotifierProvider(create:(context)DataProvider(logService:context.readLogService(),storageService:context.readStorageService(),),),],child:Scaffold(appBar:AppBar(title:constText(依赖注入模式演示)),body:ListView(padding:constEdgeInsets.all(16),children:[_buildSection(服务类定义,_serviceDefinition()),_buildSection(依赖注入演示,_diDemo()),_buildSection(在Provider中使用依赖,_providerWithDependencies()),_buildSection(依赖注入优势,_diAdvantages()),],),),);}Widget_buildSection(Stringtitle,Widgetcontent){returnCard(margin:constEdgeInsets.only(bottom:16),child:Padding(padding:constEdgeInsets.all(16),child:Column(crossAxisAlignment:CrossAxisAlignment.start,children:[Text(title,style:constTextStyle(fontSize:18,fontWeight:FontWeight.bold)),constSizedBox(height:12),content,],),),);}Widget_diDemo(){returnColumn(children:[ConsumerDataProvider(builder:(context,provider,child){returnText(当前数据:${provider.data},style:constTextStyle(fontSize:18),);},),constSizedBox(height:16),TextField(decoration:constInputDecoration(labelText:输入新数据),onSubmitted:(value){context.readDataProvider().updateData(value);},),constSizedBox(height:16),ElevatedButton(onPressed:()context.readDataProvider().updateData(Hello DI!),child:constText(设置Hello),),],);}}9.2 代码解析在这个演示页面中服务类定义展示了LogService、StorageService等服务类的定义方式依赖注入演示展示了如何使用MultiProvider注入多个服务在Provider中使用依赖展示了如何在DataProvider中使用注入的服务依赖注入优势总结了依赖注入的优势十、关键要点10.1 Provider可作为依赖注入容器使用Provider不仅可以管理状态还可以管理服务类的生命周期。10.2 使用Provider注入不可变服务对于无状态的服务类使用Provider即可不需要使用ChangeNotifierProvider。10.3 Provider默认创建单例实例Provider默认创建单例实例整个应用中只创建一次。10.4 服务之间可以有依赖关系一个Provider可以依赖其他Provider但必须按依赖顺序声明。10.5 便于测试和维护使用依赖注入可以方便地替换为mock对象进行测试同时也便于维护和扩展。十一、总结依赖注入是一种重要的软件设计模式可以帮助我们解耦组件、提高可测试性和可维护性。在Flutter中Provider不仅可以用于状态管理还可以作为依赖注入容器使用。在实际开发中建议遵循以下原则将服务类与状态类分离使用Provider注入不可变服务使用ChangeNotifierProvider管理可变状态按依赖顺序声明Provider在构造函数中注入依赖不要直接使用context.read希望本文能帮助你掌握依赖注入模式的使用并在实际项目中正确应用
RELATED

相关推荐

企业招聘管理系统JAVA源代码+数据库,实现公司职位发布,简历投递,招聘管理,开箱就能用的项目-BOSS直聘源码

企业招聘管理系统JAVA源代码+数据库,实现公司职位发布,简历投递,招聘管理,开箱就能用的项目-BOSS直聘源码

博主介绍: 所有项目都配有从入门到精通的安装教程,可二开,提供核心代码讲解,项目指导。 项目配有对应开发文档、解析等 项目都录了发布和功能操作演示视频;项目的界面和功能都可以定制,包安装运行&#xff…

📅 2026/9/14 21:52:13
【小程序课程设计/毕业设计】校园专业信息聚合与科普小程序的设计与实现 智慧校园专业报考解读服务管理系统【附源码、数据库、万字文档】

【小程序课程设计/毕业设计】校园专业信息聚合与科普小程序的设计与实现 智慧校园专业报考解读服务管理系统【附源码、数据库、万字文档】

博主介绍:✌️码农一枚 ,专注于大学生项目实战开发、讲解和毕业🚢文撰写修改等。全栈领域优质创作者,博客之星、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java、小程序技术领域和毕业项目实战 ✌️技术范围:&am…

📅 2026/9/14 14:44:19
小程序毕设项目:基于小程序的个性化健康生活指导平台 居民健康生活习惯监督与管理小程序 轻量化智慧健康生活服务管理系统 (源码+文档,讲解、调试运行,定制等)

小程序毕设项目:基于小程序的个性化健康生活指导平台 居民健康生活习惯监督与管理小程序 轻量化智慧健康生活服务管理系统 (源码+文档,讲解、调试运行,定制等)

博主介绍:✌️码农一枚 ,专注于大学生项目实战开发、讲解和毕业🚢文撰写修改等。全栈领域优质创作者,博客之星、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java、小程序技术领域和毕业项目实战 ✌️技术范围:&am…

📅 2026/9/14 13:26:18
MORE NEWS

更多资讯

📰

Wazuh 5.x SCA 自定义策略迁移指南:从 4.x 格式到 PCRE2 与 YAML 新规范的完整实战

Wazuh 5.x SCA 自定义策略迁移指南:从 4.x 格式到 PCRE2 与 YAML 新规范的完整实战 【免费下载链接】wazuh Wazuh - The Open Source Security Platform. Unified XDR and SIEM protection for endpoints and cloud workloads. 项目地址: https://gitcode.com/Git…

📰

Cilium Hubble Relay 节点状态协议解析:relay.proto 中的 NodeStatusEvent 与 NodeState

Cilium Hubble Relay 节点状态协议解析:relay.proto 中的 NodeStatusEvent 与 NodeState 【免费下载链接】cilium eBPF-based Networking, Security, and Observability 项目地址: https://gitcode.com/GitHub_Trending/ci/cilium 导读 本文深入解析 Cilium…

📰

Codex 配 TaoToken:复现 HumanEval 的 pass@k 评估

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

📰

微电网虚拟惯性控制仿真技术与应用实践

1. 微电网虚拟惯性控制仿真概述微电网虚拟惯性控制仿真作为新能源电力系统研究的前沿领域,正在重塑分布式能源的并网方式。传统直流微电网由于缺乏类似交流系统中同步发电机的旋转惯性支撑,在应对新能源功率波动和负荷突变时,电压稳定性面临严…

📰

永磁同步电机转矩分解技术与Maxwell实现

1. 永磁同步电机转矩分解的工程意义 在永磁同步电机(Permanent Magnet Synchronous Motor, PMSM)设计与优化过程中,转矩特性的精确分析直接关系到电机性能评估的准确性。传统方法通常将输出转矩视为整体进行测量或计算,但实际应用…

📰

【uni-app项目实战】心理健康服务平台(三)

目录 三、项目启动 3.1 创建项目 3.1.1 .prettierrc 3.1.2 配置 tabBar 3.1.3 公共样式 3.1.4 引入字体图标与 uni-icons 3.1.5 网站图标 3.2 公共封装 3.2.1 网络请求 3.2.2 轻提示 四、Pinia 状态管理 4.1 安装 4.2 Store 4.3 State 4.4 持久化 五、用户登录…

TODAY

今日更新

THIS WEEK

本周精选

THIS MONTH

本月热门

读完文章,想聊聊您的网站?

告诉我们您的行业与需求,资深顾问一对一梳理方案与报价,全程免费。

📞 💬