2017-07-18 49 views
0

我想定義一個可以與Akka actor混合的特性,該特性可以在一定的持續時間之後調度接收超時。這裏是什麼,我想要做一個素描......訪問mixin中的Akka Actor上下文

trait BidderInActivityClearingSchedule[T <: Tradable, A <: Auction[T, A]] 
    extends ClearingSchedule[T, A] { 
    this: AuctionActor[T, A] => 

    context.setReceiveTimeout(timeout) // can I call this here? 

    def timeout: FiniteDuration 

    override def receive: Receive = { 
    case ReceiveTimeout => 
     val (clearedAuction, contracts) = auction.clear 
     contracts.foreach(contract => settlementService ! contract) 
     auction = clearedAuction 
    case message => this.receive(message) 
    } 

} 


class FancyAuctionActor[T <: Tradable](val timeout: FiniteDuration, ...) 
    extends AuctionActor[T, FancyAuctionActor[T]] 
    with BidderInActivityClearingSchedule[T, FancyAuctionActor[T]] 

...但我不明白,當context.setReceiveTimeout將被調用。當MyFancyAuctionActor被調用時,它會作爲構造函數的一部分被調用嗎?或者它會早些時候被調用,並因此拋出某種錯誤,因爲事實上timeout尚未定義。

回答

0

我建議你的日程安排的控制觸發使用演員的生命週期事件hooks.if你有你的特質延長像這樣的演員:

trait AuctionActor[T, A] extends Actor 
trait BidderInActivityClearingSchedule[T, A] extends AuctionActor[T,A] 

你就會有很多演員的生命週期事件掛鉤的訪問如preStart()postStop()等等。

所以,你可以很容易做到:

trait BidderInActivityClearingSchedule[T, A] extends AuctionActor[T,A] { 
    override def preStart() = { 
    supre.preStart() // or call this after the below line if must. 
    context.setReceiveTimeout(timeout) // can I call this here? 
    }  
} 

更新

如果你想實現一個可堆疊混入結構。你會做類似於上面的事情。

//your AuctionActor is now a class as you wanted it 
class AuctionActor[T, A] extends Actor 

//Look below; the trait is extending a class! it's ok! this means you can 
//only use this trait to extend an instance of AuctionActor class 
trait BidderInActivityClearingSchedule[T, A] extends AuctionActor[T,A]{ 
    def timeout: FiniteDuration 

    //take note of the weird "abstract override keyword! it's a thing!" 
    abstract override def preStart() = { 
    super.preStart() 
    context.setReceiveTimeout(timeout) 
    } 
} 

您可以擁有儘可能多的特徵,將類AuctionActor擴展到一起。

+0

使用actor生命週期鉤子並不是一個壞主意,但我不想擴展Actor我想保持特性爲混合。 – davidrpugh

+0

據我所知,可堆疊mixin的最佳實踐方法是讓所有mixin擴展基本特徵。你實際上只是在你的情況下使用自我類型註釋來做同樣的事情,而你卻剝奪了重載方法的優勢。還有另一個技巧來實現可堆疊的mixin,我將其描述爲更新回答 – shayan

+0

我熟悉可堆疊的actor模式,並在庫中使用它。也許我很迂腐,但我不喜歡有明顯的mixin從Actor延伸出來的特質。 – davidrpugh

0

你可以使用自我類型來要求一個特質只能混入到Actors中。

trait MyMixin { self: Actor => 
    println(self.path) 
} 

trait MyActor extends Actor with MyMixin 

MyMixin相當演員,但它只能通過是演員的類進行擴展。

+0

我向mixin提供了一個自我類型註釋,以強制它必須與AuctionActor(它擴展了Actor)混合的約束。任何使用「自我」而不是「本」的理由? – davidrpugh

+0

你可以任意調用它。 – Ryan