         spec))))
 
 
-(def make-method-matcher
-  "Given a route spec map containing :method key with method keyword (or keyword set) as value, return a matcher fn to
-  match the method. If the route spec does not contain :method key then it is left intact."
+(def ^{:arglists '([route-spec method-finder])} make-method-matcher
+  "Given a route spec not containing the :matcher key and containing HTTP-method keyword (or keyword set) as value
+  (found by method-finder), create a method matcher and add it under the :matcher key. If the route spec already
+  contains the :matcher key or if it does not contain HTTP-method keyword/set then the route spec is left intact. When
+  adding matcher also add matchex unless the :matchex key already exists."
   (make-ensurer :matcher
     (fn [spec method-finder]
       (when-not (map? spec)
         (i/expected "route spec to be a map" spec))
       (if-let [method (method-finder spec)]  ; assoc matcher only if method matcher is intended
-        (let [ensure-matchex (make-ensurer :matchex (fn [spec x]
-                                                      (assoc spec :matchex x)))]
+        (do
           (when-not (or (keyword? method)
                       (and (set? method)
                         (every? keyword? method)))

                                                  `(when (~method (:request-method ~request))
                                                     {}))))))
        spec))))


;; ----- manipulate nested routes -----


(defn cons-matcher
  "Given a bunch of routes, nest all of them under a specified matcher."
  [matcher routes]
  [{:matcher matcher :nested routes}])


(defn cons-uri-prefix-matcher
  "Given a bunch of routes, nest all of them under a URI-prefix matcher."
  [^String prefix routes {:keys [strip? replace? original-key]
                          :as options}]
  (cons-matcher
    (let [plen (.length prefix)]
      (cond
        (and strip? replace?)       (fn [request]
                                      (let [^String uri (:uri request)]
                                        (when (and (.startsWith uri prefix)
                                                (> (.length uri) plen))
                                          {:request (assoc request
                                                      :uri         (.substring uri plen)
                                                      original-key uri)})))
        (and strip? (not replace?)) (fn [request]
                                      (let [^String uri (:uri request)]
                                        (when (and (.startsWith uri prefix)
                                                (> (.length uri) plen))
                                          {:request (assoc request
                                                      :uri (.substring uri plen))})))
        (and (not strip?) replace?) (fn [request]
                                      (let [^String uri (:uri request)]
                                        (when (and (.startsWith uri prefix)
                                                (> (.length uri) plen))
                                          {:request (assoc request
                                                      original-key uri)})))
        :otherwise                  (fn [request]
                                      (let [^String uri (:uri request)]
                                        (when (and (.startsWith uri prefix)
                                                (> (.length uri) plen))
                                          {})))))
    routes))

      (if-let [uri-pattern (uri-finder spec)]  ; assoc matcher only if URI matcher is intended
        (do
          (when-not (string? uri-pattern)
            (i/expected "URI pattern to be a string" spec))
          (let [uri-template (i/parse-uri-template i/default-separator uri-pattern)]
            (-> spec
              (assoc :matcher (fn [request]
                                (when-let [params (Util/matchURI ^String (:uri request) uri-template)]
