Fork me on GitHub
#clojure-spec
<
2020-10-13
>
johnjelinek00:10:15

oh, hmm:

; (#:scratch{:keys [scratch/total prices]}) - failed: Extra input at: [:fn-tail :arity-1 :params] spec: :clojure.core.specs.alpha/param-list
#:scratch{:keys [scratch/total prices]} - failed: vector? at: [:fn-tail :arity-n :params] spec: :clojure.core.specs.alpha/param-list

Michael Stokley03:10:46

is there an fdef that works for multi-methods?

Alex Miller (Clojure team)03:10:25

no, but you can pull the dispatch function out and spec that

johnjelinek03:10:20

ya, dunno what was up with that destructuring, but this works:

(s/def ::m (s/and (s/keys :req [::total ::prices])
                    #(= (::total %) (reduce + (::prices %)))))

johnjelinek03:10:57

ah-ha! I think I got it! thx @alexmiller!

johnjelinek03:10:50

I did something like this:

(s/def ::m (s/and ::total=prices (s/schema [::prices ::total])))

Alex Miller (Clojure team)03:10:18

just as a heads up, I do not consider spec 2 to be ready for use and the api may change before release

👍 3
vlaaad21:10:18

I have the following spec:

(s/def ::grid
  (-> (s/keys :opt-un [::grid])
      (s/coll-of :kind vector? :min-count 1)
      (s/coll-of :kind vector? :min-count 1)))
How do I do generative testing with this kind of spec? any attempt to generate an example of ::grid makes my OS super laggy until I kill the JVM process...

Alex Miller (Clojure team)21:10:17

that's not a valid spec? what are you expecting -> to do there?

vlaaad05:10:35

Oh, sorry, I added threading in the message for readability, actual spec doesn't have it

Alex Miller (Clojure team)21:10:03

I guess maybe it would work in the spec 1 macrology, but I find that very confusing to parse (and it won't in spec 2 I think)

Alex Miller (Clojure team)21:10:41

in general, setting :gen-max is useful for coll specs though to bound nested coll size

vlaaad05:10:19

Thanks, I'll try that

vlaaad07:10:40

It did help, thank you!

kenny22:10:56

We often build our own spec "types" by doing something like this.

(defmacro my-custom-map
  [kpred vpred]
  (let [form `(s/map-of ~kpred ~vpred)]
    `(s/with-gen ~form #(gen/fmap identity (s/gen ~form)))))

(s/def ::k string?)
(s/def ::v string?)

(s/def ::my-custom-map (my-custom-map ::k ::v))
This, however, does not play nice with :gen overrides.
(gen/generate (s/gen ::my-custom-map {::k #(s/gen #{"a" "b"})}))
=>
{"3" "b4tq9FeW6Gt",
 "8h" "o47F763P0v5B63sA52c4xu1FN",
...}
Is there a better way of doing this that works with :gen overrides?

kenny22:10:45

Oh, duh - I think this is a perfect case for s/conformer

kenny23:10:13

It's like with-gen needs to take an argument with :gen overrides or implicitly use a dynamic variable.

kenny23:10:43

Can't figure out any way around this other than to override the top level spec (in my example ::my-custom-map). That can be quite painful with complex specs.