5

Boot.scala で ssh デーモンを起動するリフト アプリ。問題は次のとおりです。sbtcontainer:restart /セッションで実行すると、 Address already in use という例外が発生します。今2つの質問:

  1. Boot.scala で依存サービスを開始するのは正しい方法ですか?
  2. とにかく、container:stop イベントをどのように処理できますか?
4

2 に答える 2

10

それを行うLift-yの方法はLiftRules.unloadHooks.

十分に文書化されているわけではありませんが (AFAIK)、Lift のソース コードを見ると、LiftServletdestroy()ed のときに で定義された関数LiftRules.unloadHooksが実行されることがわかります。

関数を実行する順序に応じてunloadHooks RulesSeqappendまたはメソッドを使用して関数を追加できます。そのため、メソッドでは、次のようにすることができます。prependbootstrap.liftweb.Boot.boot

sshDaemon.start()
LiftRules.unloadHooks.append( () => sshDaemon.stop() )

(それが SSH デーモンを開始および停止した方法であると仮定します。)

LiftServlet.destroy()sbt web-plugin のコマンドが実行されたときにメソッドが呼び出されるとは 100% 確信が持てcontainer:restartませんが、それはプラグインと、Lift ではなく Jetty との相互作用によって決定されますが、container:stopコマンドは確実に機能するはずです。

于 2012-01-31T02:24:06.540 に答える
4

私は Lift に詳しくありませんが、このアドバイスは、サーブレット ベースの Web アプリケーションならどれでも当てはまるはずです。

に を登録し、メソッド内のすべてのリソースを解放ServletContextListenerします。(起動はメソッド内で行う必要があります。)web.xmlcontextDestroyedcontextCreated

setAttribute/を使用getAttributeして、サーバーを格納し、後で取得できます。

これをすべてまとめると:

import javax.servlet.{ServletContextEvent, ServletContextListener}


final class SshListener extends ServletContextListener{
  val attributeKey = "sshServer"

  def contextInitialized(sce: ServletContextEvent) {
    val server = new Server()
    server.start()
    sce.getServletContext.setAttribute(attributeKey, server)
  }

  def contextDestroyed(sce: ServletContextEvent) {
    Option(sce.getServletContext.getAttribute(attributeKey)).foreach(_.asInstanceOf[Server].stop())
  }
}

class Server {
  def start()
  def stop()
}
于 2012-01-29T20:03:57.597 に答える