|
200 | 200 | (defn explain-data* [spec path via in x]
|
201 | 201 | (when-let [probs (explain* (specize spec) path via in x)]
|
202 | 202 | (when-not (empty? probs)
|
203 |
| - {::problems probs}))) |
| 203 | + {::problems probs |
| 204 | + ::spec spec |
| 205 | + ::value x}))) |
204 | 206 |
|
205 | 207 | (defn explain-data
|
206 | 208 | "Given a spec and a value x which ought to conform, returns nil if x
|
|
215 | 217 | "Default printer for explain-data. nil indicates a successful validation."
|
216 | 218 | [ed]
|
217 | 219 | (if ed
|
218 |
| - (print |
219 |
| - (with-out-str |
220 |
| - ;;(prn {:ed ed}) |
221 |
| - (doseq [{:keys [path pred val reason via in] :as prob} (::problems ed)] |
222 |
| - (when-not (empty? in) |
223 |
| - (print "In:" (pr-str in) "")) |
224 |
| - (print "val: ") |
225 |
| - (pr val) |
226 |
| - (print " fails") |
227 |
| - (when-not (empty? via) |
228 |
| - (print " spec:" (pr-str (last via)))) |
229 |
| - (when-not (empty? path) |
230 |
| - (print " at:" (pr-str path))) |
231 |
| - (print " predicate: ") |
232 |
| - (pr (abbrev pred)) |
233 |
| - (when reason (print ", " reason)) |
234 |
| - (doseq [[k v] prob] |
235 |
| - (when-not (#{:path :pred :val :reason :via :in} k) |
236 |
| - (print "\n\t" (pr-str k) " ") |
237 |
| - (pr v))) |
238 |
| - (newline)) |
239 |
| - (doseq [[k v] ed] |
240 |
| - (when-not (#{::problems} k) |
241 |
| - (print (pr-str k) " ") |
242 |
| - (pr v) |
243 |
| - (newline))))) |
| 220 | + (let [problems (sort-by #(- (count (:path %))) (::problems ed))] |
| 221 | + (print |
| 222 | + (with-out-str |
| 223 | + ;;(prn {:ed ed}) |
| 224 | + (doseq [{:keys [path pred val reason via in] :as prob} problems] |
| 225 | + (when-not (empty? in) |
| 226 | + (print "In:" (pr-str in) "")) |
| 227 | + (print "val: ") |
| 228 | + (pr val) |
| 229 | + (print " fails") |
| 230 | + (when-not (empty? via) |
| 231 | + (print " spec:" (pr-str (last via)))) |
| 232 | + (when-not (empty? path) |
| 233 | + (print " at:" (pr-str path))) |
| 234 | + (print " predicate: ") |
| 235 | + (pr (abbrev pred)) |
| 236 | + (when reason (print ", " reason)) |
| 237 | + (doseq [[k v] prob] |
| 238 | + (when-not (#{:path :pred :val :reason :via :in} k) |
| 239 | + (print "\n\t" (pr-str k) " ") |
| 240 | + (pr v))) |
| 241 | + (newline)) |
| 242 | + (doseq [[k v] ed] |
| 243 | + (when-not (#{::problems} k) |
| 244 | + (print (pr-str k) " ") |
| 245 | + (pr v) |
| 246 | + (newline)))))) |
244 | 247 | (println "Success!")))
|
245 | 248 |
|
246 | 249 | (def ^:dynamic *explain-out* explain-printer)
|
|
371 | 374 | (let [pred (maybe-spec pred)]
|
372 | 375 | (if (spec? pred)
|
373 | 376 | (explain* pred path (if-let [name (spec-name pred)] (conj via name) via) in v)
|
374 |
| - [{:path path :pred (abbrev form) :val v :via via :in in}]))) |
| 377 | + [{:path path :pred form :val v :via via :in in}]))) |
375 | 378 |
|
376 | 379 | (defn ^:skip-wiki map-spec-impl
|
377 | 380 | "Do not call this directly, use 'spec' with a map argument"
|
|
417 | 420 | [{:path path :pred 'map? :val x :via via :in in}]
|
418 | 421 | (let [reg (registry)]
|
419 | 422 | (apply concat
|
420 |
| - (when-let [probs (->> (map (fn [pred form] (when-not (pred x) (abbrev form))) |
| 423 | + (when-let [probs (->> (map (fn [pred form] (when-not (pred x) form)) |
421 | 424 | pred-exprs pred-forms)
|
422 | 425 | (keep identity)
|
423 | 426 | seq)]
|
|
482 | 485 | x))
|
483 | 486 | (explain* [_ path via in x]
|
484 | 487 | (when (invalid? (dt pred x form cpred?))
|
485 |
| - [{:path path :pred (abbrev form) :val x :via via :in in}])) |
| 488 | + [{:path path :pred form :val x :via via :in in}])) |
486 | 489 | (gen* [_ _ _ _] (if gfn
|
487 | 490 | (gfn)
|
488 | 491 | (gen/gen-for-pred pred)))
|
|
518 | 521 | path (conj path dv)]
|
519 | 522 | (if-let [pred (predx x)]
|
520 | 523 | (explain-1 form pred path via in x)
|
521 |
| - [{:path path :pred (abbrev form) :val x :reason "no method" :via via :in in}]))) |
| 524 | + [{:path path :pred form :val x :reason "no method" :via via :in in}]))) |
522 | 525 | (gen* [_ overrides path rmap]
|
523 | 526 | (if gfn
|
524 | 527 | (gfn)
|
|
863 | 866 | (c/or (nil? vseq) (= i limit)) x
|
864 | 867 | (valid? spec v) (recur (inc i) vs)
|
865 | 868 | :else ::invalid)))))))
|
866 |
| - (unform* [_ x] x) |
| 869 | + (unform* [_ x] |
| 870 | + (if conform-all |
| 871 | + (let [spec @spec |
| 872 | + [init add complete] (cfns x)] |
| 873 | + (loop [ret (init x), i 0, [v & vs :as vseq] (seq x)] |
| 874 | + (if (>= i (c/count x)) |
| 875 | + (complete ret) |
| 876 | + (recur (add ret i v (unform* spec v)) (inc i) vs)))) |
| 877 | + x)) |
867 | 878 | (explain* [_ path via in x]
|
868 | 879 | (c/or (coll-prob x kind kind-form distinct count min-count max-count
|
869 | 880 | path via in)
|
|
1089 | 1100 | (case op
|
1090 | 1101 | ::accept nil
|
1091 | 1102 | nil p
|
1092 |
| - ::amp (list* 'clojure.spec/& (op-describe p1) forms) |
| 1103 | + ::amp (list* 'clojure.spec.alpha/& (op-describe p1) forms) |
1093 | 1104 | ::pcat (if rep+
|
1094 | 1105 | (list `+ rep+)
|
1095 | 1106 | (cons `cat (mapcat vector (c/or (seq ks) (repeat :_)) forms)))
|
|
1106 | 1117 | insufficient (fn [path form]
|
1107 | 1118 | [{:path path
|
1108 | 1119 | :reason "Insufficient input"
|
1109 |
| - :pred (abbrev form) |
| 1120 | + :pred form |
1110 | 1121 | :val ()
|
1111 | 1122 | :via via
|
1112 | 1123 | :in in}])]
|
|
1218 | 1229 | (op-explain (op-describe p) p path via (conj in i) (seq data))
|
1219 | 1230 | [{:path path
|
1220 | 1231 | :reason "Extra input"
|
1221 |
| - :pred (abbrev (op-describe re)) |
| 1232 | + :pred (op-describe re) |
1222 | 1233 | :val data
|
1223 | 1234 | :via via
|
1224 | 1235 | :in (conj in i)}])
|
1225 | 1236 | (c/or (op-explain (op-describe p) p path via (conj in i) (seq data))
|
1226 | 1237 | [{:path path
|
1227 | 1238 | :reason "Extra input"
|
1228 |
| - :pred (abbrev (op-describe p)) |
| 1239 | + :pred (op-describe p) |
1229 | 1240 | :val data
|
1230 | 1241 | :via via
|
1231 | 1242 | :in (conj in i)}]))))))
|
|
1247 | 1258 | (explain* [_ path via in x]
|
1248 | 1259 | (if (c/or (nil? x) (coll? x))
|
1249 | 1260 | (re-explain path via in re (seq x))
|
1250 |
| - [{:path path :pred (abbrev (op-describe re)) :val x :via via :in in}])) |
| 1261 | + [{:path path :pred (op-describe re) :val x :via via :in in}])) |
1251 | 1262 | (gen* [_ overrides path rmap]
|
1252 | 1263 | (if gfn
|
1253 | 1264 | (gfn)
|
|
1389 | 1400 | (c/and (<= (inst-ms start) t) (< t (inst-ms end))))))
|
1390 | 1401 |
|
1391 | 1402 | (defn int-in-range?
|
1392 |
| - "Return true if start <= val and val < end" |
| 1403 | + "Return true if start <= val, val < end and val is a fixed |
| 1404 | + precision integer." |
1393 | 1405 | [start end val]
|
1394 | 1406 | (cond
|
1395 | 1407 | (integer? val) (c/and (<= start val) (< val end))
|
|
0 commit comments