Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/clojure/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Clojure 如何使中间件仅在“:swagger{:deprecated true}”时放置响应头?_Clojure_Compojure_Ring_Compojure Api - Fatal编程技术网

Clojure 如何使中间件仅在“:swagger{:deprecated true}”时放置响应头?

Clojure 如何使中间件仅在“:swagger{:deprecated true}”时放置响应头?,clojure,compojure,ring,compojure-api,Clojure,Compojure,Ring,Compojure Api,我们使用compojure api在我们的戒指应用程序中实现了一些不错的虚张声势的集成。:swagger{:deprecated true}元像champ一样工作以获得正确的swagger页面,但是我有一个要求,当路由为:swagger{:deprecated true}时,我在响应上放置一个特定的头。我正在努力弄清楚如何使用中间件模式来实现这一点,我一直在使用中间件模式进行类似的响应头操作 (ns bob.routes (:require [clojure.tools.logging :a

我们使用compojure api在我们的戒指应用程序中实现了一些不错的虚张声势的集成。
:swagger{:deprecated true}
元像champ一样工作以获得正确的swagger页面,但是我有一个要求,当路由为
:swagger{:deprecated true}
时,我在响应上放置一个特定的头。我正在努力弄清楚如何使用中间件模式来实现这一点,我一直在使用中间件模式进行类似的响应头操作

(ns bob.routes
  (:require [clojure.tools.logging :as log]
            [compojure.api.sweet :refer :all]
            [ring.util.http-response :as status]
            [schema.core :as s]
            [ring.swagger.schema :as rs]))

(s/defschema BobResponse {:message (rs/describe String "Message")})

(defn wrap-bob-response-header [handler]
  (fn [request]
    (let [response (handler request)]
      ;; can I reach into the request or the response to see what
      ;; route served this and if it has the :swagger {:deprecated true}
      ;; meta on it and NOT emit the x-bob header if it does?
      (assoc-in response [:headers "x-bob"] "Robert"))))

(defroutes bob-routes
  (context "" []
    :middleware [wrap-bob-response-header]
    :tags ["bob"]
    :description ["Tease out how to do swagger driven response header"]
    (GET "/notdeprectated" [:as request]
      :swagger {:deprecated false}
      :new-relic-name "GET_notdeprecated"
      :return BobResponse
      (status/ok {:message "All is well"}))
    (GET "/isdeprecated" [:as request]
      :swagger {:deprecated true}
      :new-relic-name "GET_isdeprecated"
      :return BobResponse
      (status/ok {:message "You came to the wrong neighborhood."}))))

如何修改
wrap-bob响应头
以仅在具有
的路由上发出
x-bob
:swagger{:deprecated true}

使用Compojure API,中间件在其定义的路径上下文中被就地调用。在您的示例中,
wrap-bob响应头
还不知道请求将去哪里(或者它是否匹配任何内容)。如果它知道,您可以使用来自请求的注入路由信息(请参阅)来确定端点是否设置了招摇过市信息

您可以做的是,仅将标头设置中间件装载到需要它的路由

有一个名为(也被Metosin称为)的库,它通过应用route first架构来解决这个问题:首先完成完整路径查找,然后应用中间件链。因此,所有中间件都知道它们所挂载到的端点。中间件只需查询端点数据(在请求时或编译时)并相应地执行操作。他们甚至可以决定不走那条特殊的路线

REITT的功能与compojure api相当,只是语法不同,例如完全数据驱动

博客中的好例子:

另外,我是两本LIB的合著者

编辑 匹配后将数据注入响应的解决方案:

1) 创建向响应添加数据(或元数据)的中间件

2) 添加或修改重组处理程序,以使用给定数据(在处理程序中可用)将中间件从1装载到端点

3) 读取响应管道中的数据并采取相应的行动

(defn wrap添加响应数据[处理程序数据]
(让[带数据#(assoc%::数据)]
(fn
([请求]
(带有数据(处理程序请求)))
([请求-响应-提高]
(handler#(回应(含数据%))提出(()()))
(defmethod compojure.api.meta/restructure-param:swagger[uugger acc]
(->acc
(在[:info:public:swagger]swagger中关联)
(在[:middleware]中更新为“[[wrap add response data~swagger]]))
(def应用程序
(api)
(上下文“/api”[]
(获取“/:kikka”[]
:招摇过市{:已弃用?正确}
(好"耶"())("耶")
(app{:请求方法:get,:uri”/api/kukka})
; {:status 200,:headers{},:body“jeah”,::data{:deprecated?true}

我不认为在包装器中有什么可以做到这一点,因为环处理程序是一个
请求->响应
映射,所以在传递给处理程序之前,关于匹配的路由的任何信息都是未知的,在到达结果时就会丢失。然后,解决方案是修改/替换compojure.core/routing(),将匹配的请求关联到响应上,我想问题是:嵌套路由呢。“仅将头设置中间件装载到需要它的路由上。”这是我试图克服的问题;复制代码以支持
:swagger{:弃用的false}
。但这很奇怪。在我的中间件中,路由已经“发生”,为了pete的缘故,我正在修改响应,似乎没有地方可以查看刚刚执行的路由。我找错地方了吗?响应中是否有我可以用来查找路由元的内容?我想添加的是,在不推荐的路由响应上添加一个警告标题,它的值太低,无法通过编辑来更改框架。我已经开始考虑将
(defmethod compojure.api.meta/restructure-param…
作为实现这一目标的一种手段。我的障碍是,我没有完全理解
(在[:middleware]中更新为
[[wrap add response data~swagger]])`。我会在有机会的时候尝试一下。我很确定我能做到这一点。它基本上是一个代码生成器。请在
(get…
表单上尝试
macroexpand
,看看它发出了什么。