Kotlin 的 DSL是一个神奇的存在,可以帮助我们实现一些非常特别的用法,这里介绍一个类似RxJava的封装。
class ResponseHandler<T> {
private var onNext: (T) -> Unit = {}
private var onError: (Throwable) -> Unit = {}
private var onCompleted: () -> Unit = {}
private var load: () -> T? = { null }
fun onNext(onNext: (T) -> Unit) {
this.onNext = onNext
}
fun onError(onError: (Throwable) -> Unit) {
this.onError = onError
}
fun onCompleted(onCompleted: () -> Unit) {
this.onCompleted = onCompleted
}
fun load(load: () -> T?) {
this.load = load
}
fun doWork() {
try {
val result = load.invoke()
if (result != null) {
onNext.invoke(result)
}
onCompleted.invoke()
} catch (throwable: Throwable) {
onError.invoke(throwable)
}
}
companion object {
fun <T> loadData(block: ResponseHandler<T>.() -> Unit) {
val responseHandler = ResponseHandler<T>()
block(responseHandler)
responseHandler.doWork()
}
}
}
测试
class ExampleUnitTest {
@Test
fun testResponseHandler() {
println("测试一")
ResponseHandler.loadData<String> {
load {
"Hello World!"
}
onNext { println("onNext $it") }
onCompleted { println("onCompleted") }
onError { it.printStackTrace() }
}
println()
println("测试二")
ResponseHandler.loadData<String> {
load {
throw Exception("模拟异常")
}
onNext { println("onNext $it") }
onCompleted { println("onCompleted") }
onError { it.printStackTrace() }
}
}
}
结果
测试一
onNext Hello World!
onCompleted
测试二
java.lang.Exception: 模拟异常
结合协程 Coroutine 封装
class ResponseHandlerCoroutine<T> {
private var onNext: (T) -> Unit = {}
private var onError: (Throwable) -> Unit = {}
private var onCompleted: () -> Unit = {}
private var load: suspend () -> T? = { null }
fun onNext(onNext: (T) -> Unit) {
this.onNext = onNext
}
fun onError(onError: (Throwable) -> Unit) {
this.onError = onError
}
fun onCompleted(onCompleted: () -> Unit) {
this.onCompleted = onCompleted
}
fun load(load: suspend () -> T?) {
this.load = load
}
fun doWork() {
// MainScope().launch {} 如果是Android使用 MainScope()代替GlobalScope
GlobalScope.launch {
try {
val result = withContext(Dispatchers.IO) {
load.invoke()
}
if (result != null) {
onNext.invoke(result)
}
onCompleted.invoke()
} catch (throwable: Throwable) {
onError.invoke(throwable)
}
}
}
companion object {
fun <T> loadData(block: ResponseHandlerCoroutine<T>.() -> Unit) {
val responseHandler = ResponseHandlerCoroutine<T>()
block(responseHandler)
responseHandler.doWork()
}
}
}
测试
class ExampleUnitTest {
@Test
fun testResponseHandlerCoroutine() {
println("测试一")
ResponseHandlerCoroutine.loadData<String> {
load {
delay(1000)
"Hello World!"
}
onNext { println("onNext $it") }
onCompleted { println("onCompleted") }
onError { it.printStackTrace() }
}
Thread.sleep(2000)
println()
println("测试二")
ResponseHandlerCoroutine.loadData<String> {
load {
delay(1000)
throw Exception("模拟异常")
}
onNext { println("onNext $it") }
onCompleted { println("onCompleted") }
onError { it.printStackTrace() }
}
Thread.sleep(2000)
}
}
输出结果
测试一
onNext Hello World!
onCompleted
测试二
java.lang.Exception: 模拟异常
网友评论