首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >带有Clojure Compojure应用程序的Tomcat 7上的流关闭错误

带有Clojure Compojure应用程序的Tomcat 7上的流关闭错误
EN

Stack Overflow用户
提问于 2013-08-10 01:21:13
回答 2查看 702关注 0票数 2

我正在使用compojure、ring-json和lein-ring在clojure中开发一个应用程序,并使用lein- ring在开发时进行测试(使用"lein ring server“命令),并将应用程序打包到war文件中以部署到Tomcat 7.0.42上。我有一个页面,它使用jQuery向url发出ajax post请求,该url响应来自更新的数据库记录的数据。在"lein ring server“命令下进行开发和运行时,javascript工作得很好。它收集输入,发送post数据,服务器用我正在寻找的数据进行响应。

当我打包应用程序并将其部署到Tomcat的"webapps“目录中时,我的应用程序运行正常,让我登录,从数据库中提取数据,并正确处理表单post请求(例如,登录通过登录表单将数据发送到服务器,一切都正常)。但是,当我使用javascript ajax请求导航到页面时,我得到了以下错误:

代码语言:javascript
运行
复制
SEVERE: Servlet.service() for servlet [performancecenter.routes/app servlet] in context with path [/performance] threw exception
java.io.IOException: Stream closed
    at org.apache.catalina.connector.InputBuffer.read(InputBuffer.java:312)
    at org.apache.catalina.connector.CoyoteInputStream.read(CoyoteInputStream.java:200)
    at sun.nio.cs.StreamDecoder.readBytes(Unknown Source)
    at sun.nio.cs.StreamDecoder.implRead(Unknown Source)
    at sun.nio.cs.StreamDecoder.read(Unknown Source)
    at java.io.InputStreamReader.read(Unknown Source)
    at java.io.BufferedReader.fill(Unknown Source)
    at java.io.BufferedReader.read(Unknown Source)
    at clojure.core$slurp.doInvoke(core.clj:6279)
    at clojure.lang.RestFn.invoke(RestFn.java:410)
    at ring.middleware.json$read_json.doInvoke(json.clj:12)
    at clojure.lang.RestFn.invoke(RestFn.java:423)
    at ring.middleware.json$wrap_json_body$fn__3427.invoke(json.clj:19)
    at ring.middleware.json$wrap_json_params$fn__3431.invoke(json.clj:31)
    at ring.middleware.json$wrap_json_response$fn__3438.invoke(json.clj:42)
    at performancecenter.servlet$_service$fn__706.invoke(servlet.clj:1)
    at ring.util.servlet$make_service_method$fn__50.invoke(servlet.clj:126)
    at performancecenter.servlet$_service.invoke(servlet.clj:1)
    at performancecenter.servlet.service(Unknown Source)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:305)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:222)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:123)
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:502)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:171)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:99)
    at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:953)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:408)
    at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1023)
    at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:589)
    at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:312)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
    at java.lang.Thread.run(Unknown Source)

下面是post请求url的compojure route函数和用ring-json函数包装请求的app函数:

代码语言:javascript
运行
复制
(defroutes page-routes
  (POST "/log/performance/api" {session :session params :params} 
        (enter-production-record (:user session) params)))

(def app
  (-> (routes login-routes main-routes)
      (auth/with-user)
      (handler/site :session)
      (middleware/wrap-json-body)
      (middleware/wrap-json-params)
      (middleware/wrap-json-response)))

下面是返回json数据的函数(在开发中有效):

代码语言:javascript
运行
复制
(defn enter-production-record [user params]
  (let [m (data/insert-producer-metric (:id user))
        r (data/get-productivity m)]
    {:body {:productivity (float (:productivity_factor r))}}))

诚然,我对Tomcat知之甚少,但通过阅读,我发现了此错误的示例,它通常与应用程序中的函数提前关闭流或其他什么有关。我不知道这里到底发生了什么,或者我的函数是如何做到这一点的。如有任何帮助,将不胜感激,谢谢!

EN

回答 2

Stack Overflow用户

发布于 2013-08-10 09:34:53

我经常遇到这样的情况,当对DB的调用返回一个懒惰的记录序列时,某些东西在开发中有效,而在生产系统中失败,这些记录在开发中被打印到repl或logger,但在生产系统上没有实现。可能是对get-productivity的调用中缺少对返回行周围的doall的调用。

另一种情况是,异常处理程序包装了对with-connection的调用,因此当异常发生时,db连接不再可用,尽管根据我对get-productivity中可能存在的内容的猜测,这似乎比缺少doall的可能性要小。

如果你包含了get-productivity并记录了它在失败期间的返回值的例子,我们将能够做出更好的猜测。

票数 1
EN

Stack Overflow用户

发布于 2016-08-03 00:24:44

如果您没有放入正确的内容类型,json包装器可能无法正常工作,因此,它们可能会导致IO错误(在我的例子中,我没有使用中间件,但我直接使用了{request :body},这导致了IO错误)。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/18152248

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档