mirror of
https://github.com/metosin/reitit.git
synced 2025-12-16 16:01:11 +00:00
Ensure extra query-string params aren't removed by coercion
This commit is contained in:
parent
5f10465533
commit
21e5840f13
4 changed files with 70 additions and 19 deletions
|
|
@ -178,6 +178,12 @@
|
|||
(-response-coercer [_ schema]
|
||||
(-coercer schema :response transformers :encode opts))
|
||||
(-query-string-coercer [_ schema]
|
||||
(-coercer schema :string transformers :encode opts))))))
|
||||
;; TODO: Create encoding function that only does encode, no decoding and validation?
|
||||
(-coercer (mu/open-schema schema)
|
||||
:string
|
||||
;; Tune transformer to not strip extra keys
|
||||
{:string {:default (-transformer string-transformer-provider (assoc opts :strip-extra-keys false))}}
|
||||
:encode
|
||||
opts))))))
|
||||
|
||||
(def coercion (create default-options))
|
||||
|
|
|
|||
|
|
@ -160,7 +160,13 @@
|
|||
(is (= "/olipa/kerran?x=a&x=b"
|
||||
(-> router
|
||||
(r/match-by-name! ::route {:a "olipa", :b "kerran"})
|
||||
(r/match->path {:x [:a :b]}))))))
|
||||
(r/match->path {:x [:a :b]}))))
|
||||
|
||||
(is (= "/olipa/kerran?x=a&x=b&extra=extra-param"
|
||||
(-> router
|
||||
(r/match-by-name! ::route {:a "olipa", :b "kerran"})
|
||||
(r/match->path {:x [:a :b]
|
||||
:extra "extra-param"}))))))
|
||||
|
||||
(testing "custom encode/string for a collection"
|
||||
(let [router (r/router ["/:a/:b"
|
||||
|
|
@ -183,6 +189,13 @@
|
|||
(r/match-by-name! ::route {:a "olipa", :b "kerran"})
|
||||
(r/match->path {:x [:a :b]}))))
|
||||
|
||||
(testing "extra query-string parameters aren't removed by coercion"
|
||||
(is (= "/olipa/kerran?x=a%2Cb&extra=extra-param"
|
||||
(-> router
|
||||
(r/match-by-name! ::route {:a "olipa", :b "kerran"})
|
||||
(r/match->path {:x [:a :b]
|
||||
:extra "extra-param"})))))
|
||||
|
||||
(is (= {:query {:x [:a :b]}}
|
||||
(-> (r/match-by-path router "/olipa/kerran")
|
||||
(assoc :query-params {:x "a,b"})
|
||||
|
|
|
|||
|
|
@ -1,16 +1,30 @@
|
|||
(ns reitit.frontend.easy-test
|
||||
(:require [clojure.test :refer [deftest testing is are async]]
|
||||
(:require [clojure.string :as str]
|
||||
[clojure.test :refer [are async deftest is testing]]
|
||||
[goog.events :as gevents]
|
||||
[reitit.coercion.malli :as rcm]
|
||||
[reitit.core :as r]
|
||||
[reitit.frontend.easy :as rfe]
|
||||
[reitit.frontend.history :as rfh]
|
||||
[goog.events :as gevents]))
|
||||
[reitit.frontend.history :as rfh]))
|
||||
|
||||
(def browser (exists? js/window))
|
||||
|
||||
(def router (r/router ["/"
|
||||
["" ::frontpage]
|
||||
["foo" ::foo]
|
||||
["bar/:id" ::bar]]))
|
||||
["bar/:id"
|
||||
{:name ::bar
|
||||
:coercion rcm/coercion
|
||||
:parameters {:query [:map
|
||||
[:q {:optional true}
|
||||
[:keyword
|
||||
{:decode/string (fn [s]
|
||||
(if (string? s)
|
||||
(keyword (if (str/starts-with? s "__")
|
||||
(subs s 2)
|
||||
s))
|
||||
s))
|
||||
:encode/string (fn [k] (str "__" (name k)))}]]]}}]]))
|
||||
|
||||
;; TODO: Only tests fragment history, also test HTML5?
|
||||
|
||||
|
|
@ -38,10 +52,11 @@
|
|||
;; 0. /
|
||||
3 (do (is (= "/" url)
|
||||
"go back")
|
||||
(rfe/navigate ::bar {:path-params {:id 1}}))
|
||||
(rfe/navigate ::bar {:path-params {:id 1}
|
||||
:query-params {:q "x"}}))
|
||||
;; 0. /
|
||||
;; 1. /bar/1
|
||||
4 (do (is (= "/bar/1" url)
|
||||
4 (do (is (= "/bar/1?q=__x" url)
|
||||
"push-state 2")
|
||||
(rfe/replace-state ::bar {:id 2}))
|
||||
;; 0. /
|
||||
|
|
|
|||
|
|
@ -3,14 +3,28 @@
|
|||
[reitit.core :as r]
|
||||
[reitit.frontend.history :as rfh]
|
||||
[reitit.frontend.test-utils :refer [capture-console]]
|
||||
[goog.events :as gevents]))
|
||||
[goog.events :as gevents]
|
||||
[reitit.coercion.malli :as rcm]
|
||||
[clojure.string :as str]))
|
||||
|
||||
(def browser (exists? js/window))
|
||||
|
||||
(def router (r/router ["/"
|
||||
["" ::frontpage]
|
||||
["foo" ::foo]
|
||||
["bar/:id" ::bar]]))
|
||||
["bar/:id"
|
||||
{:name ::bar
|
||||
:coercion rcm/coercion
|
||||
:parameters {:query [:map
|
||||
[:q {:optional true}
|
||||
[:keyword
|
||||
{:decode/string (fn [s]
|
||||
(if (string? s)
|
||||
(keyword (if (str/starts-with? s "__")
|
||||
(subs s 2)
|
||||
s))
|
||||
s))
|
||||
:encode/string (fn [k] (str "__" (name k)))}]]]}}]]))
|
||||
|
||||
(deftest fragment-history-test
|
||||
(when browser
|
||||
|
|
@ -24,9 +38,12 @@
|
|||
(rfh/href history ::foo)))
|
||||
(is (= "#/bar/5"
|
||||
(rfh/href history ::bar {:id 5})))
|
||||
(is (= "#/bar/5?q=x"
|
||||
(testing "query string coercion doesn't strip extra keys"
|
||||
(is (= "#/bar/5?extra=a"
|
||||
(rfh/href history ::bar {:id 5} {:extra "a"}))))
|
||||
(is (= "#/bar/5?q=__x"
|
||||
(rfh/href history ::bar {:id 5} {:q "x"})))
|
||||
(is (= "#/bar/5?q=x#foo"
|
||||
(is (= "#/bar/5?q=__x#foo"
|
||||
(rfh/href history ::bar {:id 5} {:q "x"} "foo")))
|
||||
(let [{:keys [value messages]} (capture-console
|
||||
(fn []
|
||||
|
|
@ -58,11 +75,11 @@
|
|||
(.back js/window.history))
|
||||
4 (do (is (= "/" url)
|
||||
"go back")
|
||||
(rfh/push-state history ::bar {:id 1}))
|
||||
5 (do (is (= "/bar/1" url)
|
||||
(rfh/push-state history ::bar {:id 1} {:extra "a"}))
|
||||
5 (do (is (= "/bar/1?extra=a" url)
|
||||
"push-state 2")
|
||||
(rfh/replace-state history ::bar {:id 2}))
|
||||
6 (do (is (= "/bar/2" url)
|
||||
(rfh/replace-state history ::bar {:id 2} {:q "x"}))
|
||||
6 (do (is (= "/bar/2?q=__x" url)
|
||||
"replace-state")
|
||||
(.back js/window.history))
|
||||
7 (do (is (= "/" url)
|
||||
|
|
@ -84,7 +101,7 @@
|
|||
(rfh/href history ::foo)))
|
||||
(is (= "/bar/5"
|
||||
(rfh/href history ::bar {:id 5})))
|
||||
(is (= "/bar/5?q=x"
|
||||
(is (= "/bar/5?q=__x"
|
||||
(rfh/href history ::bar {:id 5} {:q "x"})))
|
||||
(let [{:keys [value messages]} (capture-console
|
||||
(fn []
|
||||
|
|
@ -119,8 +136,8 @@
|
|||
(rfh/push-state history ::bar {:id 1}))
|
||||
5 (do (is (= "/bar/1" url)
|
||||
"push-state 2")
|
||||
(rfh/replace-state history ::bar {:id 2}))
|
||||
6 (do (is (= "/bar/2" url)
|
||||
(rfh/replace-state history ::bar {:id 2} {:q "x"}))
|
||||
6 (do (is (= "/bar/2?q=__x" url)
|
||||
"replace-state")
|
||||
(.back js/window.history))
|
||||
7 (do (is (= "/" url)
|
||||
|
|
|
|||
Loading…
Reference in a new issue