当前位置:网站首页>[Android kotlin collaboration] use coroutinecontext to realize the retry logic after a network request fails
[Android kotlin collaboration] use coroutinecontext to realize the retry logic after a network request fails
2022-07-07 04:55:00 【Programmer Xiao He SS】
Preface
stay Android There is a typical scenario in development : Try again after the network request fails : The general logic is to pop up a Dialog Remind users “ Network request failed ”, And provide a retry button .

If the current page has only one network request , Then the logic is very simple : Just call the method that initiates the network request again . When a page has multiple network requests , My common method is to add status for failure callback , Call different methods according to different states . But this method is somewhat cumbersome , It's also a little unsafe . First , You need to add extra status , And pass it around . In some cases , You even need to reinitialize the network request parameters . What's worse : You have to manage this state , Once mismanaged , Will result in calling methods that should not be called , Introduce serious BUG.
Until one day I saw CoroutineExceptionHandler, Flash of light —— You can use the collaboration context to save network requests and... That may need to be retried in the future Request data , This will solve the above problem .
Because most of the projects I have developed adopt ViewModel Implement network request logic and UI Decoupling of layers , The network request is basically based on Coroutine+Retrofit The way to achieve , It's basically using viewModelScope.
viewModelScope.launch() {
request()
}
viewModelScope It's essentially a ViewModel The extension function of , It can be used conveniently in ViewModel Create coroutines , The specific code will not be expanded . By default , its CoroutineContext from Job and CoroutineDispatcher form . The context of a collaborative process is essentially an implementation key-value Linked list structure of access mode . We can do it through inheritance AbstractCoroutineContextElement To implement custom CoroutineContext Context :
class RetryCallback(val callback: () -> Unit) : AbstractCoroutineContextElement(RetryCallback) {
companion object Key : CoroutineContext.Key<RetryCallback>
}
Then , When the network request is abnormal CoroutineExceptionHandler Get the operation we need to perform again :
val coroutineExceptionHandler = CoroutineExceptionHandler { coroutineContext, throwable ->
val callback = coroutineContext[RetryCallback]
?.callback
}
Then , To put coroutineExceptionHandler Add to the context of the process that initiates the network request :
viewModelScope.launch(exceptionHandler
+ RetryCallback { request() }) {
request()
}
here , Just get it on the page that initiates the network request callback, And call it when you click the retry button , The logic of retry can be realized .
Further encapsulate it and add automatic retry logic after failure , Create for ViewModel Interface used , Subsequent logic used to handle network request errors :
interface ViewModelFailed {
/**
* @param throwable: Abnormal information
* @param callback: Function to retry
* */
fun requestFailed(throwable: Throwable, callback: () -> Unit)
}
Create an extension function for it , Used to create CoroutineExceptionHandler and RetryCallback Context instance :
/**
* @param autoReTry: Retry automatically
* @param callback: Function to retry
* */
fun ViewModelFailed.initRetry(autoReTry: Boolean = false, callback: () -> Unit) =
CoroutineExceptionHandler { coroutineContext, throwable ->
val retryCallBack = {
coroutineContext[RetryCallback]
?.callback?.invoke()
}
if (autoReTry) {
// Automatic start retry logic
onRetry()
retryCallBack.invoke()
} else {
// Do not automatically start retry , Subsequent operations are left to the user for decision
requestFailed(throwable) {
retryCallBack
}
}
} + RetryCallback(callback)
ViewModel Need to achieve ViewModelFailed Interface , And calls in the association of the network requests. initRetry Method to add an exception handling context :
class MainViewViewModel : ViewModel(), ViewModelFailed {
val liveData: MutableLiveData<BaseData> = MutableLiveData()
/**
* @param num: For demonstration Request Request data
* @param repeat: Number of automatic retries after failure
* */
fun request(num: Int, repeat: Int = 0) {
liveData.value = BaseData.loading()
viewModelScope.launch(initRetry(repeat > 0) {
request(num,repeat - 1)
}) {
liveData.value = BaseData.success(simulateHttp(num))
}
}
private suspend fun simulateHttp(num: Int) = withContext(Dispatchers.IO) {
// Simulate network requests
...
}
override fun requestFailed(throwable: Throwable, callback: () -> Unit) {
// Processing failure logic
dialog()
// retry
callback.invoke()
}
override fun onRetry() {
}
}
Last
Android Learning is a long way to go , What we need to learn is not only superficial technology , We have to go down to the bottom , Figure out the following principle , That's the only way , We can improve our competitiveness , In today's highly competitive world .
Life can't be smooth , When there are peaks, there are valleys , To believe in , Those who can't beat us , It will make us stronger in the end , To be your own ferry man .
I've sorted myself out in this period of time Android The most important and popular learning direction materials are placed in the QR code below , There are also different directions of self-study programming route 、 Interview question set / Face the 、 And a series of technical articles .**
Resources are constantly updated , Welcome to study and discuss together .
边栏推荐
- 《原动力 x 云原生正发声 降本增效大讲堂》第三讲——Kubernetes 集群利用率提升实践
- Jetson nano配置pytorch深度学习环境//待完善
- Have you got the same "artifact" of cross architecture development praised by various industry leaders?
- 谈谈讲清楚这件事的重要性
- A detailed explanation of head pose estimation [collect good articles]
- You can't sell the used lithography machine to China! The United States unreasonably pressured the Dutch ASML, and domestic chips were suppressed again
- Deeply cultivate the developer ecosystem, accelerate the innovation and development of AI industry, and Intel brings many partners together
- 深入解析Kubebuilder
- jvm是什么?jvm调优有哪些目的?
- DFS和BFS概念及实践+acwing 842 排列数字(dfs) +acwing 844. 走迷宫(bfs)
猜你喜欢

Introduction to namespace Basics

九章云极DataCanvas公司蝉联中国机器学习平台市场TOP 3

R语言主成分pca、因子分析、聚类对地区经济研究分析重庆市经济指标

5G VoNR+之IMS Data Channel概念

九章云极DataCanvas公司摘获「第五届数字金融创新大赛」最高荣誉!

Chapter 9 Yunji datacanvas company won the highest honor of the "fifth digital finance innovation competition"!

树与图的深度优先遍历模版原理

指针与数组在函数中输入实现逆序输出

What if win11 pictures cannot be opened? Repair method of win11 unable to open pictures

Oracle - views and sequences
随机推荐
AttributeError: module ‘torch._C‘ has no attribute ‘_cuda_setDevice‘
R language principal component PCA, factor analysis, clustering analysis of regional economy analysis of Chongqing Economic Indicators
Thesis landing strategy | how to get started quickly in academic thesis writing
Run the command once per second in Bash- Run command every second in Bash?
leetcode 53. Maximum Subarray 最大子数组和(中等)
微信能开小号了,拼多多“砍一刀”被判侵权,字节VR设备出货量全球第二,今日更多大新闻在此
C语言中函数指针与指针函数
Case reward: Intel brings many partners to promote the innovation and development of multi domain AI industry
ESG Global Leaders Summit | Intel Wang Rui: coping with global climate challenges with the power of science and technology
Up to 5million per person per year! Choose people instead of projects, focus on basic scientific research, and scientists dominate the "new cornerstone" funded by Tencent to start the application
3GPP信道模型路损基础知识
深入解析Kubebuilder
Win11 control panel shortcut key win11 multiple methods to open the control panel
GPT-3当一作自己研究自己,已投稿,在线蹲一个同行评议
什么是Web3
ServiceMesh主要解决的三大痛点
PLC模拟量输出 模拟量输出FB analog2NDA(三菱FX3U)
【愚公系列】2022年7月 Go教学课程 005-变量
[line segment tree practice] recent requests + area and retrieval - array modifiable + my schedule I / III
为什么很多人对技术债务产生误解