Clojure Noir WAR/Servlet(CloudFoundry)的初始化挂钩



我正在构建一个Clojure Noir web应用程序,以便在CloudFoundry中作为WAR文件运行。

在我的项目.clj中,我有:

:ring {:handler appname.server/handler}

在server.clj中,我使用Noir创建了一个处理程序:

(def handler (noir.server/gen-handler {:ns 'appname}))

我使用lein-ring插件构建了WAR文件:

lein ring uberwar

然后使用推送到CloudFoundry

vmc push appname

请求处理程序运行良好,我可以很好地浏览到应用程序的URL。

所以问题是:启动应用程序时,正确的初始化方法是什么

我可以在server.clj中执行以下操作:

(when (System/getenv "VCAP_APPLICATION")
  (init-func))

但这也有几个问题。首先,这似乎是在错误的时间进行初始化(当代码被读取/eval'd而不是在应用程序启动时)。其次,保护程序是特定于CloudFoundry的,我确信有一种合适的通用WAR方法可以做到这一点。

我认为这就是ServletContextListener上contextInitialized方法的目的,但我如何将其与Noir/ring挂钩?

通过查看WAR处理的环源来解决这个问题

project.clj:ring映射采用了一个:init关键字,如so:

:ring {:init appname.server/my-init
       :handler appname.server/handler}

myinit函数将在应用程序启动时调用。

Caveat:这显然增加了应用程序初始启动所需的内存量。128M在没有初始化的情况下就足够了。由于初始化代码,应用程序启动失败,所以我不得不将内存增加到256M。我怀疑使用init代码,JVM在编译/执行Clojure代码之前没有时间进行垃圾收集。

最新更新