《Android 架构演进:手把手带你构建一个规范的 Compose + MVI 项目》

0 阅读2分钟

1. 在现代 Android 开发中,如何组织代码结构才能既易于维护又方便测试?本文将分享一个基于 Jetpack Compose + Hilt + Clean Architecture + MVI 构建的项目实战经验。

2. 为什么选择这套架构?

  • Clean Architecture: 将业务逻辑与 UI、框架解耦,哪怕以后想把 Retrofit 换成 Ktor,也只需改动 Data 层。
  • MVI: 强制性的单向数据流。相比于 MVVM,MVI 通过 Intent 和 State 解决了 UI 状态碎片化的问题,让调试变得异常清晰。

3. 项目结构分层演示

com.example.cleanmvicompose
├── domain         # 领域层:包含纯净业务逻辑 (Model, Repository Interface, UseCase)
├── data           # 数据层:负责数据来源 (Remote API, Repository Impl)
├── ui             # UI层:MVI 状态管理与 Compose 组件渲染
│   ├── user       # 用户功能模块 (Intent, State, ViewModel, Screen)
│   └── theme      # 主题样式 (Color, Theme, Type)
└── di             # 依赖注入层:Hilt 模块配置 (NetworkModule, RepositoryModule)

4. 核心代码片段

  • MVI 核心循环:展示如何通过 Flow 在 ViewModel 中处理 Intent 并更新 State。
  • Domain 层 UseCase:展示如何编写一个只负责单一业务逻辑的类。

5. 避坑指南:消失的 Hilt 绑定 (这是本文的干货点) 在项目初期,我遇到了一个让人头秃的报错:[Dagger/MissingBinding] UserApiService cannot be provided。

排查过程:明明在 NetworkModule 里写了 fun provideUserApiService(),为什么 Hilt 还是说找不到?

  • 解决方案:
@Module
@InstallIn(SingletonComponent::class)
object NetworkModule {
    @Provides // 敲黑板!这个注解绝对不能漏
    @Singleton
    fun provideUserApiService(): UserApiService {
        return UserApiService()
    }
}
  • 心得:Hilt 的魔法全靠注解。漏掉一个 @Provides,整个依赖注入大厦就会轰然倒塌。

6. 总结与反思 一套好的架构不是为了增加代码量,而是为了在项目变大时,我们依然能优雅地增加功能而不引入 Bug。MVI + Compose 的组合目前看来是 Android UI 开发的终极答案之一。

7. 源码地址