我有一系列Rx Completables,我想一个接一个地运行。我使用concat()
来执行此操作,因为我不希望它们同时启动。
view.welcome_message_edittext.verifyNotEmpty(getString(R.string.enter_your_email_address))
.concatWith(view.welcome_message_edittext.verifyEmailAddress())
.concatWith(sendMessageToBot())
.subscribe({
// The user has successfully entered data into the edittext, entered an email into the edittext, and sent message to bot.
}, { error -> })
上面的代码是这样说的,“断言用户已经在EditText中输入了文本。如果是这样,断言用户已经在EditText中输入了一封电子邮件。如果两者都是真的,请向机器人发送消息“。如果用户在EditText中输入文本但它不是电子邮件,我希望Completables链断开并调用onError()。
这就是我想要发生的事情^^^。当任何的Completables调用onError()
(如verifyNotEmpty()
和verifyEmailAddress()
时,如果用户将EditText留空或未输入电子邮件地址)那么我期待整个链终止并调用.subscribe()
onError()
函数。
但是,查看.concat()
的文档,这就是它的实际行为:
concat()
只会在调用onError
时移至下一个Completable。链条继续。
所以我的问题是,当任何一个Completables调用onError()
时,我需要使用什么来打破链?
答案 0 :(得分:1)
感谢@Buckstabue在评论中帮助我调试此问题。他的评论:
让我猜一下。方法verifyEmailAddress()被调用是绝对正常的,我怀疑你正在一个可观察的外部做一些业务逻辑。你可以将这个逻辑放在observable中,它将被懒惰地计算它类似于Observable.just(getMyInteger())和Observable.fromCallable(() - > getMyInteger())之间的区别。在第二种情况下,getMyInteger()将在订阅后被懒惰地调用,而第一个被立即调用
返回我的代码并查看我的verifyEmailAddress()
和sendMessageToBot()
函数:
private fun sendMessageToBot(): Completable {
insertChatMessageIntoConversation(ChatMessage(view!!. welcome_message_edittext.text.toString()))
return Completable.complete()
}
fun EditText.verifyEmailAddress(): Completable {
if (!android.util.Patterns.EMAIL_ADDRESS.matcher(text.trim()).matches()) {
return Completable.error(RuntimeException("Enter a valid email"))
} else {
return Completable.complete()
}
}
函数的逻辑不是sendMessageToBot()
和verifyEmailAddress()
函数。不是这样的。
这有效:
fun EditText.verifyEmailAddress(): Completable {
return Completable.fromCallable({
if (!android.util.Patterns.EMAIL_ADDRESS.matcher(text.trim()).matches()) {
val errorMessage = context.getString(R.string.enter_email_address)
error = errorMessage
throw RuntimeException(errorMessage)
}
})
}
private fun sendMessageToBot(): Completable {
return Completable.fromCallable {
insertChatMessageIntoConversation(sage(view!!. welcome_message_edittext.text.toString()))
}
}