日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Akka Notes –演员记录和测试

發布時間:2023/12/3 编程问答 21 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Akka Notes –演员记录和测试 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

在前兩部分( 一 , 二 )中,我們簡要討論了Actor以及消息傳遞的工作方式。 在這一部分中,讓我們看一下如何修復并記錄我們的TeacherActor 。

概括

這就是我們上一部分中的Actor的樣子:

class TeacherActor extends Actor {val quotes = List("Moderation is for cowards","Anything worth doing is worth overdoing","The trouble is you think you have time","You never gonna know if you never even try")def receive = {case QuoteRequest => {import util.Random//Get a random Quote from the list and construct a responseval quoteResponse=QuoteResponse(quotes(Random.nextInt(quotes.size)))println (quoteResponse)}} }

使用SLF4J記錄Akka

您會注意到,在代碼中,我們正在將quoteResponse打印到標準輸出,您顯然會認為這是一個壞主意。 讓我們通過啟用SLF4J Facade日志進行修復。

1.修復類以使用日志記錄

Akka提供了一個很好的小特征ActorLogging來實現它。 讓我們混合:

class TeacherLogActor extends Actor with ActorLogging {val quotes = List("Moderation is for cowards","Anything worth doing is worth overdoing","The trouble is you think you have time","You never gonna know if you never even try")def receive = {case QuoteRequest => {import util.Random//get a random element (for now)val quoteResponse=QuoteResponse(quotes(Random.nextInt(quotes.size)))log.info(quoteResponse.toString())}}//We'll cover the purpose of this method in the Testing sectiondef quoteList=quotes}

繞道走一圈:

在內部,當我們記錄一條消息時,ActorLogging中的記錄方法(最終)將日志消息發布到EventStream 。 是的,我確實說過publish 。 那么,EventStream實際上是什么?

EventStream和記錄

EventStream行為就像我們可以向其發布和接收消息的消息代理一樣。 與常規MOM的一個細微區別是EventStream的訂閱者只能是Actor。

在記錄消息的情況下,所有日志消息都將發布到EventStream。 默認情況下,訂閱這些消息的Actor是DefaultLogger ,它僅將消息打印到標準輸出中。

class DefaultLogger extends Actor with StdOutLogger { override def receive: Receive = {...case event: LogEvent ? print(event)} }

因此,這就是我們嘗試啟動StudentSimulatorApp的原因,我們看到了寫入控制臺的日志消息。

也就是說,Eve??ntStream不僅適合于記錄。 它是VM內ActorWorld內部可用的通用發布-訂閱機制(稍后會詳細介紹)。

返回SLF4J設置:

2.將Akka配置為使用SLF4J

akka{ loggers = ["akka.event.slf4j.Slf4jLogger"]loglevel = "DEBUG"logging-filter = "akka.event.slf4j.Slf4jLoggingFilter" }

我們將此信息存儲在一個名為application.conf的文件中,該文件應該在您的類路徑中。 在我們的sbt文件夾結構中,我們會將其放在您的main/resources目錄中。

從配置中,我們可以得出:

  • loggers屬性指示將要訂閱日志事件的Actor。 Slf4jLogger所做的只是簡單地使用日志消息,并將其委托給SLF4J Logger外觀。
  • loglevel屬性僅指示記錄日志時應考慮的最低級別。
  • logging-filter比較當前配置的日志loglevel和傳入的日志消息級別,并在發布到EventStream之前剔除配置的日志級別以下的任何日志消息。
  • 但是,為什么前面的示例沒有提供application.conf?

    僅僅是因為Akka提供了一些合理的默認值,所以我們在開始使用它之前不需要構建配置文件。 為了自定義各種內容,我們將在這里經常重新訪問該文件。 您可以在application.conf內部使用一堆很棒的參數來單獨記錄日志。 它們在這里詳細解釋。

    3.放入logback.xml

    現在,我們將配置一個由logback支持的SLF4J記錄器。

    <?xml version="1.0" encoding="UTF-8"?> <configuration> <appender name="FILE"class="ch.qos.logback.core.rolling.RollingFileAppender"><encoder><pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n</pattern></encoder><rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy"><fileNamePattern>logs\akka.%d{yyyy-MM-dd}.%i.log</fileNamePattern><timeBasedFileNamingAndTriggeringPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedFNATP"><maxFileSize>50MB</maxFileSize></timeBasedFileNamingAndTriggeringPolicy></rollingPolicy></appender><root level="DEBUG"><appender-ref ref="FILE" /></root> </configuration>

    我也將它與application.conf一起放入了main/resources文件夾中。 請確保main/resources現在位于Eclipse或其他IDE的類路徑中。 還應將logback和slf4j-api包含到build.sbt中 。

    而當我們揭開序幕我們StudentSimulatorApp和發送郵件到我們的新TeacherLogActor ,該akkaxxxxx.log文件,我們配置看起來像這樣。

    測試Akka

    請注意,這絕不是Test Akka的詳盡介紹。 我們將在以下各部分中相應標題下的“測試”的更多功能上構建測試。 這些測試用例旨在覆蓋我們之前編寫的Actor。

    當StudentSimulatorApp我們的需求時,您將同意應將其從測試用例中刪除。

    為了減輕測試的痛苦,Akka提出了一個了不起的測試工具包,使用它我們可以做一些神奇的事情,例如直接探查Actor實現的內部。

    聊夠了,讓我們看看測試用例。

    首先讓我們嘗試將StudentSimulatorApp映射到測試用例。

    現在讓我們單獨看一下聲明。

    class TeacherPreTest extends TestKit(ActorSystem("UniversityMessageSystem")) with WordSpecLikewith MustMatcherswith BeforeAndAfterAll {

    因此,從TestCase類的定義中,我們看到:

  • TestKit特性接受一個ActorSystem通過它我們可以創建Actor。 在內部,TestKit裝飾ActorSystem并替換默認的調度程序。
  • 我們使用WordSpec ,這是使用ScalaTest編寫測試用例的許多有趣方式之一。
  • MustMatchers提供方便的方法來使測試用例看起來像自然語言
  • 在測試用例完成之后,我們混入BeforeAndAfterAll以關閉ActorSystem。 特質提供的afterAll方法更像我們在JUnit中的tearDown
  • 1、2 –向演員發送消息

  • 第一個測試用例只是向PrintActor發送一條消息。 它沒有斷言!
  • 第二種情況將消息發送到Log actor,后者使用ActorLogging的log字段將消息發布到EventStream。 這也沒有斷言!
  • //1. Sends message to the Print Actor. Not even a testcase actually"A teacher" must {"print a quote when a QuoteRequest message is sent" in {val teacherRef = TestActorRef[TeacherActor]teacherRef ! QuoteRequest}}//2. Sends message to the Log Actor. Again, not a testcase per se"A teacher with ActorLogging" must {"log a quote when a QuoteRequest message is sent" in {val teacherRef = TestActorRef[TeacherLogActor]teacherRef ! QuoteRequest}

    3 –維護參與者的內部狀態

    第三種情況使用TestActorRef的underlyingActor quoteList方法,并調用TeacherActor的quoteList方法。 quoteList方法返回引號列表。 我們使用此列表來聲明其大小。

    如果對quoteList引用使您退縮,請參考上面列出的TeacherLogActor代碼,并查找:

    //From TeacherLogActor //We'll cover the purpose of this method in the Testing sectiondef quoteList=quotes//3. Asserts the internal State of the Log Actor. "have a quote list of size 4" in {val teacherRef = TestActorRef[TeacherLogActor]teacherRef.underlyingActor.quoteList must have size (4)teacherRef.underlyingActor.quoteList must have size (4)}

    4 –聲明日志消息

    正如我們前面在EventStream和Logging部分(上文)中所討論的,所有日志消息都發送到EventStream ,并且SLF4JLogger訂閱并使用其附加程序將其寫入日志文件/控制臺等。直接在我們的測試用例中使用EventStream并斷言日志消息本身的存在? 看起來我們也可以做到。

    這涉及兩個步驟:

  • 您需要像這樣向您的TestKit添加額外的配置: class TeacherTest extends TestKit(ActorSystem("UniversityMessageSystem", ConfigFactory.parseString("""akka.loggers = ["akka.testkit.TestEventListener"]"""))) with WordSpecLikewith MustMatcherswith BeforeAndAfterAll {
  • 現在我們已經訂閱了EventStream,我們可以從測試用例中將其聲明為: //4. Verifying log messages from eventStream"be verifiable via EventFilter in response to a QuoteRequest that is sent" in {val teacherRef = TestActorRef[TeacherLogActor]EventFilter.info(pattern = "QuoteResponse*", occurrences = 1) intercept {teacherRef ! QuoteRequest}}
  • EventFilter.info塊僅攔截1條以QuoteResponse( pattern='QuoteResponse* )開頭的日志消息。 (您也可以通過使用start='QuoteResponse' 。如果沒有消息發送給TeacherLogActor,則該測試用例將失敗。

    5 –使用構造函數參數測試Actor

    請注意,我們在測試用例中創建Actor的方式是通過TestActorRef[TeacherLogActor]而不是通過system.actorOf 。 這只是為了使我們可以通過TeacherActorRef中的underlyingActor Actor方法訪問Actor的內部。 我們將無法通過在常規運行時可以訪問的ActorRef來實現此ActorRef 。 (這并沒有給我們在生產中使用TestActorRef的任何借口。您會被追捕的)。

    如果Actor接受參數,那么我們創建TestActorRef的方式將是:

    val teacherRef = TestActorRef(new TeacherLogParameterActor(quotes))

    整個測試用例將如下所示:

    //5. have a quote list of the same size as the input parameter" have a quote list of the same size as the input parameter" in {val quotes = List("Moderation is for cowards","Anything worth doing is worth overdoing","The trouble is you think you have time","You never gonna know if you never even try")val teacherRef = TestActorRef(new TeacherLogParameterActor(quotes))//val teacherRef = TestActorRef(Props(new TeacherLogParameterActor(quotes)))teacherRef.underlyingActor.quoteList must have size (4)EventFilter.info(pattern = "QuoteResponse*", occurrences = 1) intercept {teacherRef ! QuoteRequest}}

    關閉ActorSystem

    最后, afterAll生命周期方法:

    override def afterAll() { super.afterAll()system.shutdown()}

    • 與往常一樣,可以從github這里下載整個項目。

    翻譯自: https://www.javacodegeeks.com/2014/10/akka-notes-actor-logging-and-testing.html

    總結

    以上是生活随笔為你收集整理的Akka Notes –演员记录和测试的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。