scala – Akka TypedActor – 如何使用上下文正确处理异步响应
发布时间:2020-12-16 08:43:43 所属栏目:安全 来源:网络整理
导读:我已经开始在 Scala中使用TypedActors并且遇到了一个非常简单的问题:我希望Actor A在Actor B上调用一个方法并在Actor A上的匿名函数中处理结果,但要确保: 我的响应处理功能是线程安全的,例如不会与访问Actor A状态的任何其他线程同时运行 我的响应处理函数
我已经开始在
Scala中使用TypedActors并且遇到了一个非常简单的问题:我希望Actor A在Actor B上调用一个方法并在Actor A上的匿名函数中处理结果,但要确保:
>我的响应处理功能是线程安全的,例如不会与访问Actor A状态的任何其他线程同时运行 我怎样(或者我可以)满足这两个要求? 例如,这个actor只想调用返回Future [Int]的otherActor上的API,并用结果更新它的状态,然后做一些需要它的actor上下文的事情: class MyActorImpl extends MyActor { // my mutable state var myNumber = 0 // method proxied by TypedActor ref: def doStuff(otherActor: OtherActor): Unit = { otherActor.doOtherStuff onSuccess { // oops this is no longer running in MyActorImpl.. // this could be on a concurrent thread if we case i => processResult(i) } } private def processResult(i: Int): Unit = { myNumber = 0 // oops,now we are possibly making a concurrent modification println(s"Got $i") // fails with java.lang.IllegalStateException: Calling TypedActor.context // outside of a TypedActor implementation method! println(s"My context is ${TypedActor.context}") } } 我在这里错过了什么?我是否需要编写处理程序来调用代理接口上定义的方法以保证单项?如果我不想在接口上公开那个特定的“私有”方法(例如processResult),这看起来很难看. 这是一个将在Scala REPL中运行的完整版本: import akka.actor._ import scala.concurrent._ val system = ActorSystem("mySystem") import system.dispatcher trait OtherActor { def doOtherStuff(): Future[Int] } trait MyActor { def doStuff(otherActor: OtherActor): Unit } class OtherActorImpl extends OtherActor { var i = 0 def doOtherStuff(): Future[Int] = { i += 1 Future {i} } } class MyActorImpl extends MyActor { // my mutable state var myNumber = 0 // method proxied by TypedActor ref: def doStuff(otherActor: OtherActor): Unit = { otherActor.doOtherStuff onSuccess { // oops this is no longer running in MyActorImpl.. // this could be on a concurrent thread if we case i => processResult(i) } } private def processResult(i: Int): Unit = { myNumber = 0 // oops,now we are possibly making a concurrent modification println(s"Got $i") // fails with java.lang.IllegalStateException: Calling TypedActor.context // outside of a TypedActor implementation method! println(s"My context is ${TypedActor.context}") } } val actor1: MyActor = TypedActor(system).typedActorOf(TypedProps[MyActorImpl]) val actor2: OtherActor = TypedActor(system).typedActorOf(TypedProps[OtherActorImpl]) actor1.doStuff(actor2) 解决方法
你将Actor的状态暴露给外界,这是一件非常糟糕的事情.看这里:
http://doc.akka.io/docs/akka/2.3.3/general/jmm.html部分演员和共享可变状态行9-10描述你的情况.
@philwalk已经描述了如何解决这个问题:Akka TypedActor – how to correctly handle async responses with context (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |
推荐文章
站长推荐
- 聊聊主流框架,Less/Sass/Compass/Bootstrap/H5b
- Scala以懒惰集合处理大型scala数据的功能方式
- 如何从OS X上的shell脚本运行Clozure CL(Lisp)?
- webservice的调试及第三方jar调用问题
- scala – 简单Play应用程序的最小RAM
- angularjs – 如何配置Angular2应用程序使用Mave
- WebService的helloworld,服务器端与客户端的Dem
- angularjs – chai-as-promise测试不适用于$q pr
- 如何防止我的vim autocmd在命令行窗口中运行?
- 【数据结构】C语言实现链表节点的插入和删除
热点阅读