如何确定正确的文件系统路径

发布于 2024-10-04 17:02:29 字数 1191 浏览 9 评论 0原文

我正在开发一个应用程序,该应用程序必须下载一些外部资源并通过 Ring 中的 public/static 目录访问它们。

但是..我在将资源保存到应用程序中的静态目录中时遇到问题,在开发时我使用ring-jetty-adapter;测试与生产服务器正在运行 Tomcat。

我将 :web-content "public" 添加到我的 leiningen 项目中,并在项目根目录中添加了 public 目录,然后我就有了使用 http-agent 的下载功能和duck-streams:

(defn download
  [file-name url]
  (h/http-agent url
                :handler (fn [agnt]
                           (let [fname file-name]
                             (with-open [w (d/writer fname)]
                               (d/copy (h/stream agnt) w))))))

如果我从 REPL 启动 Jetty 并使用 savepath: "public/my.file" ,下载的文件将正确放置在 public 目录中。 但是,当我使用 .war 文件将其部署到 Tomcat 时,它会在 Tomcat 根目录中查找 public 目录,而不是在应用程序上下文路径下。

我尝试添加一个中间件包装器来确定上下文路径,并从那里构建正确的保存路径,但我找不到任何方法来访问 HttpServlet 或确定应用程序是否在适配器或者它是否部署在特定上下文下。

这里的包装器:

(defn wrap-context-info [handler]
  (fn [req]
    (let [resp (handler req)]
      (assoc resp :servlet (:servlet req) :req (:servlet-request  req)))))

:servlet:req 都是 nil

I am working on an application that has to download some external resources and make them accessible through a public/static directory in Ring.

But.. I have a problem saving the resources into a static directory in my application, when developing I use the ring-jetty-adapter; the test & production servers are running Tomcat.

I added :web-content "public" to my leiningen project and added the public directory in the root of the project, then I have a download function using http-agent and duck-streams:

(defn download
  [file-name url]
  (h/http-agent url
                :handler (fn [agnt]
                           (let [fname file-name]
                             (with-open [w (d/writer fname)]
                               (d/copy (h/stream agnt) w))))))

If I am booting Jetty from the REPL and use savepath: "public/my.file", the downloaded file is placed correctly in the public directory.
But when I deploy it using a .war file to Tomcat, it looks for a public directory in the Tomcat root directory, and not under the application context path.

I tried to add a middleware wrapper to determine the context path and from there build the correct save path, but I cannot find any way to access the HttpServlet or a way to determine if the application is running in the adapter or if it is deployed under a specific context.

Here the wrapper:

(defn wrap-context-info [handler]
  (fn [req]
    (let [resp (handler req)]
      (assoc resp :servlet (:servlet req) :req (:servlet-request  req)))))

both :servlet and :req are nil.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

倦话 2024-10-11 17:02:30

查看 ring-servlet 源代码,看来ring servlet 适配器将HttpServletHttpServletRequestHttpServletResponse 对象与ring 请求关联起来相应地映射到 :servlet:servlet-request:servlet-response 键下。

为了方便起见,它还会向请求映射添加一个 :servlet-context 条目,其值为 (.getServletContext servlet)

在处理程序中,您可能需要检查请求映射中是否存在这些键,然后从关联的对象中提取所需的更多信息。

Looking at the ring-servlet source, it appears that the ring servlet adapter associates the HttpServlet, HttpServletRequest, and HttpServletResponse objects with the ring request map under :servlet, :servlet-request, and :servlet-response keys, accordingly.

It also adds a :servlet-context entry to the request map with the value of (.getServletContext servlet) for convenience.

Inside your handler, you might want to check for the presence of these keys in the request map, and then pull further information that you need from the associated objects.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文