我有一个名为index.html
的静态文件,我想在有人请求/
时提供。通常web服务器do this by default,但Compojure没有。当有人要求/
时,如何让Compojure服务index.html
?在Compojure中默认使用index.html
下面是我使用的静态目录代码:
; match anything in the static dir at resources/public
(route/resources "/")
我有一个名为index.html
的静态文件,我想在有人请求/
时提供。通常web服务器do this by default,但Compojure没有。当有人要求/
时,如何让Compojure服务index.html
?在Compojure中默认使用index.html
下面是我使用的静态目录代码:
; match anything in the static dir at resources/public
(route/resources "/")
这将是一个非常简单的环中间件:
(defn wrap-dir-index [handler]
(fn [req]
(handler
(update-in req [:uri]
#(if (= "/" %) "/index.html" %)))))
就具有这种功能包装你的路线,并请求/
在您的其他代码看到它们之前转化为请求/index.html
。
(def app (-> (routes (your-dynamic-routes)
(resources "/"))
(...other wrappers...)
(wrap-dir-index)))
另一种方法是在附加路由中创建重定向或直接响应。像这样:
(ns compj-test.core
(:use [compojure.core])
(:require [compojure.route :as route]
[ring.util.response :as resp]))
(defroutes main-routes
(GET "/" [] (resp/file-response "index.html" {:root "public"}))
(GET "/a" [] (resp/resource-response "index.html" {:root "public"}))
(route/resources "/")
(route/not-found "Page not found"))
“/”路径返回公用文件夹中存在的“index.html”文件响应。 “/ a”路径直接通过“内联”文件index.html进行响应。
更多关于环响应:https://github.com/mmcgrana/ring/wiki/Creating-responses
编辑:去除不需要[ring.adapter.jetty]
导入。
最近我发现,当Clojure/Compojure应用程序在Jetty或Tomcat下作为.war运行时,@ amalloy的答案不起作用。在这种情况下,需要更新:path-info
。另外,我认为这个版本可以处理任何路线,而不仅仅是“根”路线。
(defn- wrap-dir-index [handler]
(fn [request]
(handler
(let [k (if (contains? request :path-info) :path-info :uri) v (get request k)]
(if (re-find #"/$" v)
(assoc request k (format "%sindex.html" v))
request)))))
参见:https://groups.google.com/forum/#!msg/compojure/yzvpQVeQS3w/RNFkFJaAaYIJ
更新:替换,例如与工作的版本。
这工作得很好。无需编写一个环形中间件。
(:require [clojure.java.io :as io])
(defroutes app-routes
(GET "/" [] (io/resource "public/index.html")))
不知道它是否回答了这个问题,但它帮助我获得了我需要的东西! Upvoted!谢谢! – leontalbot
小心不要提供您想要的内容类型。另一个中间件如'wrap-content-type'可能会破坏你的代码。我发布了[答案](http://stackoverflow.com/a/32491623/1707589)解决这个问题。 – fasfsfgs
只是一个考虑Binita,一直困扰我一直在经历。尽管我无法找到有关订单定义的Compojure路线我发现这行不通
(GET "/*" [] r/static)
(GET "/" [] (clojure.java.io/resource "public/index.html"))
,而这确实工作
(GET "/" [] (clojure.java.io/resource "public/index.html"))
(GET "/*" [] r/static)
显然*
配衬也为空字符串的重要性,任何文件但我认为这个命令根本不重要。
小心不要提供你想要的内容类型。另一个中间件如'wrap-content-type'可能会破坏你的代码。我发布了[答案](http://stackoverflow.com/a/32491623/1707589)解决这个问题。 – fasfsfgs
当其他代码不起作用时, 请尝试此代码。
(GET "/about/" [] (ring.util.response/content-type
(ring.util.response/resource-response "about/index.html" {:root "public"}) "text/html"))
请为您的答案添加一些解释,以使其对其他读者更有用。 –
很好的答案。它使用环提供的解决方案提供指定其内容类型的资源。 – fasfsfgs
在这里观看了很多的答案后,我用下面的代码:
(ns app.routes
(:require [compojure.core :refer [defroutes GET]]
[ring.util.response :as resp]))
(defroutes appRoutes
;; ...
;; your routes
;; ...
(GET "/" []
(resp/content-type (resp/resource-response "index.html" {:root "public"}) "text/html"))))
检查ring-defaults。它具有您应该在您的项目中使用的最佳实践中间件。
我想我的观点是:Compojure没有这样做,因为用Ring来代替它很容易。您的Clojure Web堆栈不是一个全面的平台,而是一系列可插拔和专用的工具。用专为它设计的工具解决问题X. – amalloy