Fork me on GitHub
#clojure-spec
<
2016-12-12
>
gowder01:12:30

Oh whoops. Instrument just for args, duh. Lazy speed reading of slack posts is never a good idea :-(

thomas08:12:04

cheers... I'll investigate it some more.

alexisvincent10:12:45

Any patterns to avoid things like this

alexisvincent10:12:51

(s/def ::dimensions/seq (s/cat ::dimensions/x ::dimensions/x ::dimensions/y ::dimensions/y ::dimensions/z ::dimensions/z))

dergutemoritz10:12:36

@alexisvincent You could use s/tuple instead - or are you interested in the conforming behavior of s/cat?

dergutemoritz10:12:00

Then I think your only option to avoid the redundancy is to write a macro around s/cat

alexisvincent10:12:18

->

(defn make-dimensions [& d]
  (s/conform ::dimensions/seq d))

alexisvincent10:12:34

hmm. was wondering if there was something like the destructureing {:keys []}

dergutemoritz10:12:01

So you want to conform your sequential input into a map, right?

dergutemoritz10:12:24

Ah, how about s/keys*

dergutemoritz10:12:35

I think that's what you're looking for

dergutemoritz10:12:50

Well no, it's not, sorry 😄

dergutemoritz10:12:05

That would require the keys themselves to be present in the input sequence, too

dergutemoritz10:12:17

So yeah, you'll have to roll your own wrapper macro

alexisvincent10:12:46

@dergutemoritz Thanks 🙂 I wonder though if tuple is not what I want actually

dergutemoritz10:12:15

@alexisvincent YW! Yeah, s/tuple would get rid of the redundancy but it wouldn't conform into a map

dergutemoritz10:12:23

But perhaps you can live with that

alexisvincent10:12:57

I wonder if s/keys maintains order?

alexisvincent10:12:44

Because then I could write a function that first accepts req keys and then optional keys

dergutemoritz10:12:10

FWIW, here's a wrapper macro of the kind I'm talking about:

(defmacro keys-cat [& keys] `(s/cat [email protected](interleave keys keys)))

(s/conform (keys-cat ::foo ::bar) [1 2]) => #:user{:foo 1, :bar 2}

dergutemoritz10:12:31

Or maybe keys-tuple would be a more fitting name

alexisvincent10:12:58

maybe cat-keys

alexisvincent11:12:50

is the general consensus to prefer namespaced keys in maps?

dm312:12:47

it seems so, for best synergy with spec

alexisvincent13:12:37

Are people generally using :: as a helper

alexisvincent13:12:30

Its a pain when wanting to use the spec in another ns… You have to specify the full mylonglongname.namespace.thing/name

alexisvincent13:12:11

becomes so long winded…

alexisvincent13:12:35

Or are people just registering thing/name

alexisvincent13:12:30

OH 🙂 :: can also be used for aliasing

dm313:12:27

also (require [some.ns :as n]) (is (= ::n/kw :some.ns/kw))

dm313:12:45

I guess that's what you meant

alqvist13:12:01

What is the best way of namespacing an existing map? Using a function, not the reader

Alex Miller (Clojure team)15:12:52

@alqvist what do you mean? adding a namespace to the keys of a map?

Alex Miller (Clojure team)15:12:14

there is no function to do that right now

alqvist15:12:36

@alexmiller exactly that - I made a small function for it. Posted it in #clojure

sparkofreason17:12:25

Is there some preferred way of writing simulation-testable specs for functions with constraints between parameters? I have a function that takes a map and a key. The key must exist in the map for both the input and output. I can make it work by writing a custom generator for :args using bind, was wondering if there was a preferred method.

Alex Miller (Clojure team)18:12:47

that is the preferred method

sparkofreason18:12:03

Thanks, that's basically how I handled it.

sparkofreason18:12:13

I notice in the video that the generator override was specified directly in the test, rather than in the spec. Don't know that it makes much difference, though giving it in the spec would allow you to reuse the override if that spec was composed with others.

bbloom18:12:18

is there a spec or predicate for objects that have strict value equality? looking for something like a clojure.core/edn? or something like that

bbloom18:12:03

edn? isn’t quite right, since that’s about serializability, but would be close enough for my needs

hiredman18:12:33

that would be nice

hiredman18:12:56

any? is so close, but fails with NaNs

bbloom18:12:18

no, any? isn’t close - it includes functions

bbloom18:12:57

i have a procedure that will go in to an infinite loop if the function isn’t pure & i’ve been bitten a few times by including a function in it

bbloom18:12:07

so i’m doing like add-watch! does, which is force key values

hiredman18:12:32

I am pretty sure the generator for any? doesn't generate functions

bbloom18:12:52

generation aside, the spec is wrong if i allow functions 🙂

bfabry18:12:14

the generator for any? was way simpler than preferred last time I checked, there was a bug on test.check about it

bbloom18:12:54

i need a predicate like value-equality?

bbloom18:12:10

which i guess i could make, but it seemed like it might have been something that existed or should exist

bbloom18:12:21

i didn’t feel like exhaustively listing what’s in edn in a spec

Alex Miller (Clojure team)18:12:30

I think there are some things in test-check with "printable" in their name?

Alex Miller (Clojure team)18:12:02

I know we spent a lot of time building up stuff like that in the old data.generative

Alex Miller (Clojure team)18:12:09

Certainly open to ideas

bbloom18:12:23

hmm “printable” is a good hint, i’ll look - thanks

hiredman18:12:33

the problem with the printable stuff is it generates NaNs

hiredman18:12:43

and those are generators, not predicates

bbloom18:12:51

alexmiller: this looks more or less like what i need. would be cool to have a predicate for it

Alex Miller (Clojure team)19:12:58

Seems like we could also fix test.check re NaN (which is not currently printable)

bbloom19:12:39

i think clojure.core/edn? would be the least objectionable formulation of this request

bbloom19:12:36

well, actually - may not

bbloom19:12:41

b/c that would be a “deep” predicate

bbloom19:12:59

i don’t think any such deep predicates exist - it would have O(N) runtime 😕

Alex Miller (Clojure team)19:12:57

I think it's probably unlikely we would make that predicate

bbloom19:12:26

yeah - after realizing it was O(N), i realized that - but a spec makes more sense, right?

Alex Miller (Clojure team)19:12:20

Well, definitely a generator, maybe a spec

bbloom19:12:58

besides the stuff in clojure.core.specs, are there any “standard” specs anywhere? i don’t think so, right? just predicates...

jeremyraines21:12:43

In this example from the spec guide, is the ability to key into the arguments with :start and :end created by the s/cat above the anon function? Does the destructuring happen such that the first expression given to s/and has an effect on what’s passed to the other?

(s/fdef ranged-rand
  :args (s/and (s/cat :start int? :end int?)
               #(< (:start %) (:end %)))
…

bfabry21:12:16

@jeremyraines yes, the s/cat conforms the data. s/and threads the conformed data

zane21:12:55

Super useful for conformers that coerce between types.