Java 如何在后端控制器中使用Kotlin协程同时使用多个端点
上下文:我发现很少有教程解释如何同时使用Kotlin的多个端点,但它们是基于Android的,在我的例子中,它是一个后端应用程序。我有一些使用CompleteableFuture的经验,但我认为我应该使用Coroutine,因为它是一个Kotlin,并且没有Spring依赖性 根据一些建议,我达成了协议Java 如何在后端控制器中使用Kotlin协程同时使用多个端点,java,kotlin,async-await,kotlin-coroutines,Java,Kotlin,Async Await,Kotlin Coroutines,上下文:我发现很少有教程解释如何同时使用Kotlin的多个端点,但它们是基于Android的,在我的例子中,它是一个后端应用程序。我有一些使用CompleteableFuture的经验,但我认为我应该使用Coroutine,因为它是一个Kotlin,并且没有Spring依赖性 根据一些建议,我达成了协议 @Singleton class PersonEndpoint() { @Inject lateinit var employeClient: EmployeClien
@Singleton
class PersonEndpoint()
{
@Inject
lateinit var employeClient: EmployeClient
override suspend fun getPersonDetails(request: PersonRequest): PersonResponse {
var combinedResult: String
GlobalScope.launch {
val resultA: String
val resultB: String
val employeesA = async{ employeClient.getEmployeesA()}
val employeesB = async{ employeClient.getEmployeesB()}
try{
combinedResult = employeesA.await() + employeesB.await()
print(combinedResult)
} catch (ex: Exception) {
ex.printStackTrace()
}
// ISSUE 1
if I try add return over here it is not allowed.
I understand it is working how it is designed to work: GlobalScope is running in different thread
}
// ISSUE 2
if I try return combinedResult over here combinedResult isn't initialized.
I understand it is working how it is designed to work: GlobalScope is running in different thread and I can
debug and see that return over here executes earlier than employeesA.await = employeesB.await
}
那么,在返回到客户端之前,如何执行combinedResult=employeesA.await()+employeesB.await()
***在Denis/answer之后编辑
@Singleton
class CustomerEndpoint(){
fun serve(): Collection<Int> {
return runBlocking {
async {
getItemDouble(1)
}
async {
getItemTriple(1)
}
}.map { it.await() }
}
suspend fun getItemDouble(i: Int): Int {
delay(1000)
return i * 2
}
suspend fun getItemTriple(i: Int): Int {
delay(1000)
return i * 3
}
override suspend fun getPersonDetails(request: PersonRequest): PersonResponse {
val result = serve()
println("Got result $result")
...
}
@Singleton
类CustomerEndpoint(){
趣味服务():收藏{
返回运行阻塞{
异步的{
getItemDouble(1)
}
异步的{
getItemTriple(1)
}
}.map{it.await()}
}
暂停趣味getItemDouble(i:Int):Int{
延迟(1000)
返回i*2
}
暂停有趣的getItemTriple(i:Int):Int{
延迟(1000)
返回i*3
}
覆盖suspend fun getPersonDetails(请求:PersonRequest):PersonResponse{
val结果=serve()
println(“获得结果$result”)
...
}
导入kotlinx.coroutines.async
导入kotlinx.coroutines.delay
导入kotlinx.coroutines.runBlocking
导入kotlin.system.measureTimeMillis
主要内容(){
val durationMs=测量值{
val结果=serve()
println(“获得结果$result”)
}
println(“处理在$durationMs中完成”)
}
趣味服务():收藏{
返回运行阻塞{
(1..2)地图{
异步的{
getItem(it)
}
}.map{it.await()}
}
}
暂停趣味getItem(i:Int):Int{
延迟(1000)//模拟项目检索工作
返回i*2
}
注意,这里有两个嵌套调用-
getItem(1)
和getItem(2)
。我们可以看到它们是并行执行的,因为总体运行时间约为1秒。Denis,谢谢。如果必须并行调用不同的方法,您会怎么做?我编辑了上面的问题,以举例说明我的问题。这不会改变任何事情-我们仍有两个调用并行运行。您可以运行此代码并确保它是正确的仍然在1秒钟内执行-欢迎,Jim!关于协同路由的一个很酷的事情是,它们提供所谓的结构化并发,即如果一个协同路由失败,当前的协同路由上下文也会失败(所有同级协同路由都被取消)。因为协同路由上下文是分层的(例如,在这里我们在runBlocking()中创建一个根上下文)和每个<代码> AycNo()/Case>创建了一个子上下文),整个执行结束。异常处理是通过TIG/catch进行的。作为可选选项,在那里添加一个额外的try/catch,不要在异常情况下停止,只是以防万一,一个关于结构化并发的链接-还有一个注意事项,正如您所说,协同路由将调用不同的端点,即I/O,这就是为什么使用它更好的原因。请随时检查相应的
import kotlinx.coroutines.async
import kotlinx.coroutines.delay
import kotlinx.coroutines.runBlocking
import kotlin.system.measureTimeMillis
fun main() {
val durationMs = measureTimeMillis {
val result = serve()
println("Got result $result")
}
println("The processing is done in $durationMs ms")
}
fun serve(): Collection<Int> {
return runBlocking {
(1..2).map {
async {
getItem(it)
}
}.map { it.await() }
}
}
suspend fun getItem(i: Int): Int {
delay(1000) // Emulate item retrieval work
return i * 2
}