我正在为event collector in Clojure构建Snowplow(使用Ring / Compojure),并且在使用Ring提供透明像素时遇到一些问题。这是我发送像素的代码:
(ns snowplow.clojure-collector.responses
(:import (org.apache.commons.codec.binary Base64)
(java.io ByteArrayInputStream)))
(def pixel-bytes (Base64/decodeBase64 (.getBytes "R0lGODlhAQABAPAAAAAAAAAAACH5BAEAAAAALAAAAAABAAEAAAICRAEAOw==")))
(def pixel (ByteArrayInputStream. pixel-bytes))
(defn send-pixel
[]
{:status 200
:headers {"Content-Type" "image/gif"}
:body pixel})
当我启动服务器时,第一次点击send-pixel
的路径时,像素已成功传送到我的浏览器。但是第二次 - 以及每次之后 - Ring都没有发送正文(内容长度为0)。重启服务器,它的模式相同。
有些事情不是:
wget
复制了此内容,以确认间歇性不是浏览器缓存问题"R01GOD..."
)生成了cat original.gif | base64
base64字符串,所以知道那里没有问题diff original.gif received-pixel.gif
)我是Clojure的新手 - 我猜我的代码中有一些令人尴尬的动态gremlin,但我需要帮助发现它!
答案 0 :(得分:6)
我在发布后不久发现了REPL中的问题:
user=> (import (org.apache.commons.codec.binary Base64) (java.io ByteArrayInputStream))
java.io.ByteArrayInputStream
user=> (def pixel-bytes (Base64/decodeBase64 (.getBytes "R0lGODlhAQABAAAAACH5BAEKAAEALAAAAAABAAEAAAICTAEAOw==")))
#'user/pixel-bytes
user=> (def pixel (ByteArrayInputStream. pixel-bytes))
#'user/pixel
user=> (slurp pixel-bytes)
"GIF89a!�\n,L;"
user=> (slurp pixel-bytes)
"GIF89a!�\n,L;"
user=> (slurp pixel)
"GIF89a!�\n,L;"
user=> (slurp pixel)
""
所以基本上问题是ByteArrayInputStream
在第一次通话后被清空了。可变数据结构!
我通过为每个响应生成一个新的ByteArrayInputStream
来修复错误,其中包含:
:body (ByteArrayInputStream. pixel-bytes)}))
答案 1 :(得分:0)
问题是您的pixel
变量包含一个流。一旦读完,就不可能再次重读。
此外,您不需要处理编码问题。 Ring也提供静态文件。回来:
(file-response "/path/to/pixel.gif")
它也处理不存在的文件。 See the docs也是。