This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2016-06-07
Channels
- # admin-announcements (4)
- # beginners (63)
- # boot (67)
- # clara (29)
- # cljs-dev (38)
- # cljsjs (10)
- # clojars (7)
- # clojure (336)
- # clojure-belgium (3)
- # clojure-dev (22)
- # clojure-greece (30)
- # clojure-nl (1)
- # clojure-russia (9)
- # clojure-spain (3)
- # clojure-spec (169)
- # clojure-uk (12)
- # clojurescript (45)
- # clojurex (4)
- # core-matrix (3)
- # cursive (58)
- # datascript (3)
- # datomic (18)
- # events (38)
- # hoplon (228)
- # immutant (5)
- # lambdaisland (6)
- # leiningen (3)
- # luminus (8)
- # off-topic (11)
- # om (113)
- # om-next (2)
- # onyx (10)
- # parinfer (7)
- # planck (22)
- # re-frame (11)
- # reagent (25)
- # robots (7)
- # spacemacs (3)
- # specter (10)
- # yada (3)
@wilkerlucio: in addition to the new namespaced support in CLJ-1910 and CLJ-1919 we are considering changes related to aliasing of non-existent namespaces too
@alexmiller: cool, that would be nice, specially for cljs where I can't do the trick mentioned by @hiredman
I did some recon on it a few weeks ago and we talked about it briefly again today
I'm happy to hear that this is being considered, I think with clojure.spec the usage of fully namespaced keywords is going to have a great increase in usage
Found some clojure.spec benchmarks over on Reddit: http://muhuk.github.io/validation-benchmark/ N.B. I haven't independently verified any of the work.
Hi, could you help me understand clojure.spec Here is the little snippet:
(s/def ::name string?)
(s/def ::specific-name #{"John" "Jack"})
(s/def ::age (s/and integer? #(<= 0 % 100)))
(s/def ::person (s/keys :req-un [::name ::age]))
(s/explain ::person {:name "John" :age 10})
Is there a way to validate that map contains specific key like :name
, but value should be matched against another spec, ::specific-name
?(s/def ::person (s/and (s/keys :req-un [::name ::age]) #(#{“John” “Jack”} (:name %))))
yes, but would be good to use already defined spec ::specific-name
instead of copying its implementation
Don't know your code, but you could (def specific-names #{...}) and use that var in the specs
you can do (s/def ::name ::specific-name)
to just alias an existing one
spec will "chase" registered names like that
or you could define a predicate that is reused for multiple specs
looks like spec might need some performance tuning http://muhuk.github.io/validation-benchmark/
I don't think that test is very good, but that may also be true. will be looking at it today
The use case for clojure.spec
is different to Schema tho', right?
You might have conform
in several places for destructuring and some calls to valid?
but you're not going to have everything instrumented in production code.
Whereas folks do have Schema enabled in production don't they? Hence the focus on performance there.
schema aims to be used similarly though
Ah, so not in production code then?
when you decorate functions with schemas they don't run by default
and similar to spec you can turn them all on
for testing
and you can call them explicitly to validate in/out in production
so maybe they focus on performance primarily for that last case?
we still want spec to have good performance, even when not used in production :)
@seancorfield: we disable schema in prod, performance hit is way too much
@mishadoff: like alexmiller said, you can create a new one, if you still need that key on the current namespace, make up a new namespace, eg: (s/def :other-ns.anything/name ::specific-name)
and then (s/keys :req-un [:other-ns.anything/name])
@wilkerlucio: thanks, for now I’ve decided to use same names for keys and specs
@mishadoff: cool, that is the preferred way I believe 🙂
@wilkerlucio: yes, but sometimes you have maps with unqualified keys from third-party libs
that's true, maybe with the clojure.spec people will start using more fully qualified keywords from now one, and possibly with specs already coming from the library itself, will be awesome 🙂
is :opt
in s/keys
just for documentation purposes?
I can't figure out how else it affects anything
@gfredericks: does it work with generators?
oh that's probably true
yes indeed
cool.
yes, those reasons :)
bunch of new predicates (most with gen support) just landed in master https://github.com/clojure/clojure/commit/58227c5de080110cb2ce5bc9f987d995a911b13e
also, the long-awaited seqable?
:)
And Alpha 5 is coming… when? 😸
alexmiller: oh boy this inst generator
@seancorfield: winding its way through the tubes
TIL that java.util.Date does weird things with negative years
probably better to use something like inst-in
with that :)
coming up with reasonable generators in a lot of cases is difficult :/
reasonable defaults I mean
strings are my best example of that
here's a bunch of stuff that in no way resembles reality
a uniform distribution over unicode characters would give you 99% unprintable things
1.9.0-alpha5 https://groups.google.com/d/msg/clojure/D_s9Drua6D4/CTWk12cXDQAJ
notably for spec is the new unform
which lets you conform ... backwards
also in addition to the vast quantity of new predicates in core, there are now specs for long, double, and instant ranges in spec
and everything gens yay
That’s an awesome new release! Thank you (to everyone involved)!
yessssss
if I use s/or
in the value spec in a map-of
, I lose the qualifier I get when I use it on its own
eg. as per docs (s/def ::thing (s/or :name string? :id integer?))
conforms eg. (s/conform ::thing "bob")
to [:name "bob"]
but... (s/def ::map-of-kw-to-thing (s/map-of keyword? ::thing))
doesn't behave the same was under conform
(s/conform ::map-of-kw-to-thing {:foo "bob"})
gives {:foo "bob"}
, not {:foo [:name "bob"]}
as I was expecting
Am I missing something? I expected ::thing
to behave the same way regardless of where it was used
oh sorry I see a message in the history that I missed from @alexmiller: Rich said above "currently conform doesn't flow into coll-of, so the value is never conformed, only checked" which I think is likely related to this - sorry!
queue the warnings from all your favorite libraries that clojure.core/boolean? is being replaced by their local copy
hopefully all benign if the work we did in 1.7 was successful :)
what sort of work?
isn't http://dev.clojure.org/jira/browse/CLJ-1591 still open? I didn't accidentally re-open it did I?
it's open but it's very narrow in scope iirc - only when defining a new fn of the same name in terms of the old function of the same name, right?
the general case of just overlapping the name was resolved afaik
prior issues came up when we added "update"
we have since added other things that were in general use without issue (although I can't remember an example now)
the fact that def
declares the var at analysis time is the only way to write recursive functions with defn
mmm, I guess I am note sure what version of clojure the guy was running when I w as helping him debug this
@hiredman: I'm not sure if your final example in the comments is actually the same thing or not, not sure?
should it be possible to write a function that verifies that none of the keyword-references used in any specs have typos?
using keywords instead of vars makes the whole thing feel a lot more typo-sensitive
yeah, I didn't look at the history to see the current state of the bug, just spent a while trying to figure out why this guys defmulti was resulting in an unbound var, and after way too long I remember that bug, and he said changing the name of his function fixed it, but that is kind of loose, who knows what is happening on the other end of irc
by "typos" I mean a keyword that is supposed to refer to a spec but no spec has been registered
that's not a typo
necessarily
as long as it's registered by the time you use it, it's fine
right, so I mean "never registered"
well never is a long time
I could have a test in a codebase that looks at this for example
so it would have the responsibility to ensure that all pertinent code is loaded already
So I’m trying to play around with the new clojure.spec generators, and I keep getting this error: Var clojure.test.check.generators/large-integer is not on the classpath
. I definitely have test.check
as a dep and i can access various vars under the clojure.test.check.generators
namespace, but large-integer
isn’t one of them.
pheuter: did you add test.check magically later?
that's when I get that error
pheuter: is it an older version? large-integer
is new
are you using test.check 0.9.0 ?
do you have an older version also on the classpath?
lein deps :tree
yeah do tree ↑ and look for conflicts
(at the top of the output)
@brabster: I asked Rich, he said the point of that was that conform samples (does not check every value) for perf reasons and that is unlikely to change. we might make the docs better around it though
@alexmiller: thanks for the info, would suggest mentioning it with an example in the docs as that's not the behaviour I'd expect from map-of - working around it at the moment but would have been a nice multi-method dispatch off the conformed inputs, looks ugly in comparison now. Will share when pushed up to github, maybe I'm just misusing the functionality!
I making some updates to the guide for alpha5 right now - I'll try to add a note about that
btw spec is great imho - really neat and well thought through after a few hours of using it
alexmiller: the thing that makes me uneasy is when I have to type a fully qualified keyword referencing a spec
but where it's actually defined elsewhere using ::
or regardless actually
with var namespaces the compiler will catch renamings that were only partially done
with specs it just looks like something isn't defined yet
any ideas on how to use generators, possibly custom, to generate Datomic facts? More specifically, I’d like to generate legitimate temp ids, but it’s not clear to me how to express that as a predicate.
temp ids are a custom datomic type aren't they?
so the predicate would be #(instance? ThatType %)
what's the API to create a tmp id? it's a 0-arg function and it returns a unique object each time?
even simpler, they can be verified as longs! the problem is being able to actually transact them against a test db
long?
longs?
that can't be right...
(tempid part) returns a long?
well not exactly, it returns a :db/id reader value, but you can pull out an :idx
long from it
sequential?
why does that matter?
perhaps that part doesn’t matter, that’s just my interpretation of the error I get: db.error/not-a-partition Entity id -1000441 is not in a valid partition
are you passing a valid partition to tempid when you call it?
oh um
you just generate a random long and construct the thing that way rather than calling tempid?
but -1000441 is out of range, does that mean you're accidentally generating out of range numbers?
still out of range
feeling silly is what programming is all about
ah, it may be how i’m transacting that value, since it expects it in a #db/id reader value
For anyone following along, the approach we're gonna try is using clojure.test.check.generators/fmap
in conjunction with datomic.api/tempid
and clojure.test.check.generators/choose
.
zane: I assume you are also pheuter; now that I think about it I suspect you'll have to be careful about uniqueness?
you can use gen/vector-distinct to get a collection of distinct things
Hm, looks like gen/vector-distinct
is not one of the lazy combinators in clojure.spec.gen
you can use it directly from clojure.test.check.generators/vector-distinct
wrap it in a function if you have to