在项目中使用Hilt Retrofit使用总结


直接开始,首先我们看看怎么使用Hilt编写Retrofit接口请求类

用@Provides注解定义可注入的实例的提供者函数,如:provideHttpClient()用于提供OkHttpClient的实例,provideRetrofit()用于提供Retrofit实例

provideUserService()用于提供UserService的实例,这样我们就可以在其他的类里用@Inject获取注入该实例了。

完整代码:

@Module
@InstallIn(SingletonComponent::class)
/** 单例 */
object RetrofitModule {

    /** 服务地址 */
    private const val BASE_URL = Constant.SERVER_ADDRESS

    /** 提供OkHttpClient */
    @Singleton
    @Provides
    fun provideHttpClient(): OkHttpClient {
        return OkHttpClient.Builder()
                .addInterceptor(LoggingInterceptor())
                .addInterceptor(HeaderInterceptor())
                .addInterceptor(BasicParamsInterceptor())
                .build()
    }

    /** 提供Retrofit */
    @Singleton
    @Provides
    fun provideRetrofit(httpClient: OkHttpClient): Retrofit {
        val builder = Retrofit.Builder()
                .baseUrl(BASE_URL)
                .client(httpClient)
                .addConverterFactory(ScalarsConverterFactory.create())
                .addConverterFactory(GsonConverterFactory.create(GsonBuilder().registerTypeAdapterFactory(
                        GsonTypeAdapterFactory()
                ).create()))

        return builder.build()
    }

    /** 用hilt就不用这种创建对象的方式了 */
    fun <T> create(serviceClass: Class<T>): T = provideRetrofit(provideHttpClient()).create(serviceClass)

    /** 提供服务 */
    @Singleton
    @Provides
    fun provideUserService(retrofit: Retrofit): UserService = retrofit.create(UserService::class.java)


    /** 日志拦截器 */
    class LoggingInterceptor : Interceptor {

        @Throws(IOException::class)
        override fun intercept(chain: Interceptor.Chain): Response {
            val request = chain.request()
            val t1 = System.nanoTime()

            //logV(TAG, "发送请求: ${request.method()} ${request.url()} ${request.headers()}")

            logV(
                    TAG, String.format("发送请求 %s on %s%n%s",
                    request.url(), request.method(), request.headers()));

            val response = chain.proceed(request)

            val t2 = System.nanoTime()
            //logV(TAG, "Received response for  ${response.request().url()} in ${(t2 - t1) / 1e6} ms\n${response.headers()}")
            val responseBody: ResponseBody = response.peekBody((1024 * 1024).toLong())
            logV(
                    TAG,
                    String.format(
                            "接收响应: [%s] %n返回json:【%s】 %.1fms%n%s",
                            response.request().url(),
                            responseBody.string(),
                            (t2 - t1) / 1e6,
                            response.headers()
                    )
            )

            return response
        }

        companion object {
            const val TAG = "LoggingInterceptor"
        }
    }

    /** 增加Header */
    class HeaderInterceptor : Interceptor {
        override fun intercept(chain: Interceptor.Chain): Response {
            val original = chain.request()
            val request = original.newBuilder().apply {
                header("model", "Android")
                header("If-Modified-Since", "${Date()}")
                header("User-Agent", System.getProperty("http.agent") ?: "unknown")
                MyApplication.instance().token?.apply {
                    header("token", MyApplication.instance().token!!)
                }

            }.build()
            return chain.proceed(request)
        }
    }

    /** 公共参数 */
    class BasicParamsInterceptor : Interceptor {
        override fun intercept(chain: Interceptor.Chain): Response {
            val originalRequest = chain.request()
            val originalHttpUrl = originalRequest.url()
            val url = originalHttpUrl.newBuilder().apply {
                addQueryParameter("version", "${Build.VERSION.SDK_INT}")
            }.build()
            val request = originalRequest.newBuilder().url(url).method(originalRequest.method(), originalRequest.body()).build()
            return chain.proceed(request)
        }
    }
}

定义UserService接口

interface UserService {

    /**
     * 获取用户信息
     */
    @GET("/user/info")
    suspend fun userInfo(@Query("userId") userId:String): ServiceResult<User>

}

接着我们定义Repository的提供类,提供UserRepository类的实例

@Module
@InstallIn(ActivityComponent::class)
object RepositoryModule {

    @ActivityScoped
    @Provides
    fun provideUserRepository(userService: UserService):UserRepository {
        return UserRepository(userService)
    }

}

到目前为止我们定义了UserRepository  UserService的实例提供

下面就是怎么在Activity和ViewModel中使用UserRepository  UserService的实例

通过@HiltViewModel   @Inject 在构造函数中注入userRepository

@HiltViewModel
class LoginViewModel @Inject constructor(private val userRepository: UserRepository): ViewModel() {
    .............
}

在Activity中定义ViewModel,在Activity上增加@AndroidEntryPoint 

@AndroidEntryPoint
class LoginActivity : BaseActivity() {  private val loginViewModel: LoginViewModel by viewModels()
}

在Application中增加@HiltAndroidApp注解

@HiltAndroidApp
class MyApplication : Application(){
}

以上。





本站内容来源于作者发布和网络转载,如有版权相关问题请及时与我们取得联系,我们将立即删除。

 关于作者
 热门教程
通过Git下载和提交代码的命令记录
安装好git后: 1、配置邮箱 git config --global user.name ymbok git con
2023-08-15
剑道仙尊
59
通过ADB在Android系统中快捷截屏和录屏的方法
连上ADB线后: 截图 创建一个BAT文件,用于截图,直接双击运行即可将图片保存到D:\screenshot目录,提前
2023-08-15
剑道仙尊
105
Android12 源码下载与编译
下载Android12 源码 sudo apt-get update 安装curl sudo apt install
2023-04-25
剑道仙尊
125
android生成签名文件jks并获取SHA1
打开Android Studio终端,输入: keytool -genkey -alias app -keyalg R
2022-07-13
剑道仙尊
93
Flutter开发APP更改状态栏文字颜色
void main(){ runApp(MyApp()); /// 状态栏文字黑色 SystemChrome
2022-06-09
剑道仙尊
132
Android Swicth按钮样式自定义
&lt;Switch android:id="@+id/switch_btn" android:layout_wi
2022-06-07
剑道仙尊
133
Pagging3写起来太麻烦,简单封装及其简单
Pagging3分页写起来很麻烦,这里分享一下我的简化开发的方法,思路就是把获取数据的函数分离出来 首先定义一个基础的
2022-06-07
剑道仙尊
187
在项目中使用Hilt Retrofit使用总结
直接开始,首先我们看看怎么使用Hilt编写 Retrofit 接口请求类 用@Provides注解定义可注入的实例的提
2022-06-07
剑道仙尊
197
Android Jetpack Paging 3 下拉刷新和加载更多代码示例
使用Paging3实现列表的下拉刷新和加载更多 首先定义列表布局文件 &lt;androidx.swiperefres
2022-06-07
剑道仙尊
434
StatefulBuilder实现Dialog的刷新
在Flutter中使用Dialog时,因为 showDialog返回的context与当前页面的 context不是同
2022-06-07
剑道仙尊
136