clojure-spec

johanatan 2021-09-21T19:55:40.129800Z

is there ever a situation where the :ret value passed to a (failing) fdef :fn checker would diverge from the value you get when you run the function in question with the associated :args manually ?

johanatan 2021-09-21T19:55:50.130100Z

(I'm seeing this currently and it's a bit baffling)

johanatan 2021-09-21T19:56:23.130400Z

these are the reported values:

:cljs.spec.alpha/value
  {:args {:maps ({:A/A ""} {:A/A ""})}, :ret {:A/A " "}},

2021-09-22T04:29:41.134200Z

I think unless itโ€™s being conformed into that different value it will be the same. You could try doing:

(s/conform (:ret (s/get-spec `your-function)) {:A/A ""}) 
as a sanity check to make sure your spec isnโ€™t changing it during conforming.

johanatan 2021-09-22T18:14:22.134600Z

the :ret spec here is simply map?

johanatan 2021-09-22T18:15:18.134800Z

but for completeness:

johanatan 2021-09-22T18:15:21.135Z

utils.utils=> (s/conform (:ret (s/get-spec `-merge-attribs)) {:A/A ""})
{:A/A ""}

johanatan 2021-09-22T18:15:44.135200Z

could this be a bug in clojure spec ? it is in alpha after all. @alexmiller ?

Alex Miller (Clojure team) 2021-09-22T18:17:40.135400Z

sorry, can you re-explain?

johanatan 2021-09-22T18:17:59.135600Z

is there ever a situation where the :ret value passed to a (failing) fdef :fn checker would diverge from the value you get when you run the function in question with the associated :args manually ?

johanatan 2021-09-22T18:18:11.135800Z

these are the reported values:

:cljs.spec.alpha/value
  {:args {:maps ({:A/A ""} {:A/A ""})}, :ret {:A/A " "}},

johanatan 2021-09-22T18:18:31.136Z

this is the manual repl invocation of the function in question:

utils.utils=> (-merge-attribs '({:A/A ""} {:A/A ""}))
{:A/A ""}
the manual repl invocation is the "correct" one

johanatan 2021-09-22T18:19:57.136200Z

Notice that the one reported by spec includes a \space and the one returned from the manual invocation is merely the empty string.

johanatan 2021-09-22T18:20:08.136400Z

(the :ret that is)

Alex Miller (Clojure team) 2021-09-22T18:25:08.136600Z

it seems like you're asking me a question about your function, not spec

Alex Miller (Clojure team) 2021-09-22T18:26:05.136800Z

maybe there is more here than you can "see" - that "empty" string could have a Unicode non-breaking space or something in it

Alex Miller (Clojure team) 2021-09-22T18:26:36.137Z

or zero-width space, whatever that weird unicode thing is

Alex Miller (Clojure team) 2021-09-22T18:28:33.137200Z

in general, my answer to your original question is no (unless you're using spec :stub instrumentation or something)

johanatan 2021-09-22T18:45:17.137400Z

i think you misunderstood.

johanatan 2021-09-22T18:46:05.137600Z

spec says that for some input a specific return value is returned. when i run that function manually in the repl with the exact same input a different value is returned.

johanatan 2021-09-22T18:46:24.137800Z

i.e., "" != " "

johanatan 2021-09-22T18:46:30.138Z

regardless what that character is

johanatan 2021-09-22T18:46:38.138200Z

empty string is empty string

johanatan 2021-09-22T18:46:45.138400Z

" " is not empty string

Alex Miller (Clojure team) 2021-09-22T18:47:00.138600Z

a 1-character string with a Unicode zero-width space character looks like an empty string

johanatan 2021-09-22T18:47:08.138800Z

ah gotcha

johanatan 2021-09-22T18:47:23.139Z

is there any way to get the raw characters to be printed ?

johanatan 2021-09-22T18:47:34.139200Z

from what i've seen spec seem to report escape sequences for those

johanatan 2021-09-22T18:47:40.139400Z

like \b, \f etc etc

Alex Miller (Clojure team) 2021-09-22T18:47:49.139600Z

not those

Alex Miller (Clojure team) 2021-09-22T18:48:07.139800Z

U+200B

johanatan 2021-09-22T18:48:21.140Z

ah, ok. thanks. any other characters like that i should know about ?

Alex Miller (Clojure team) 2021-09-22T18:48:36.140200Z

well, that's one I've had this problem with. there are probably others

johanatan 2021-09-22T18:49:24.140400Z

hehe ๐Ÿ™‚ too bad https://clojuredocs.org/clojure.core/char-escape-string doesn't exist in cljs (although seems that wouldn't cover all of these anyway)

Alex Miller (Clojure team) 2021-09-22T18:49:28.140600Z

you add a debug in your :fn function to print the count of the input strings or map char etc

johanatan 2021-09-22T18:49:43.140800Z

๐Ÿ‘ thx

Alex Miller (Clojure team) 2021-09-22T18:50:09.141Z

I'm just guessing here - this is a possible answer that matches what I see, but you should validate

johanatan 2021-09-22T18:50:17.141200Z

yes of course

Alex Miller (Clojure team) 2021-09-22T18:51:15.141400Z

these kinds of things happen with generative tests :)

johanatan 2021-09-22T18:55:26.141600Z

unfortunately i think it might be something else:

johanatan 2021-09-22T18:55:30.141800Z

comparing v: '1 1', and: '1 1', count v: 5, count joined: 5 false

johanatan 2021-09-22T18:56:35.142Z

ooh, there's two non-printable chars in there

johanatan 2021-09-22T18:56:44.142200Z

and they're probably in opposing positions

johanatan 2021-09-22T18:58:36.142400Z

found it. silly mistake.

johanatan 2021-09-22T18:58:53.142600Z

i added a spurious reverse on the array of values i was comparing against

johanatan 2021-09-22T18:59:54.142800Z

might be worth thinking about how to better report string values (adding perhaps unicode escapes for these as well as the platform default escapes)

johanatan 2021-09-22T19:00:07.143Z

thanks for your help!

johanatan 2021-09-22T19:07:24.143200Z

fyi... i had used simple-type-equatable as my inner-type for a recursive map gen. if i had used instead simple-type-printable-equatable, this probably wouldn't have happened

johanatan 2021-09-21T19:56:40.130700Z

this is the manual repl invocation of the function in question:

johanatan 2021-09-21T19:56:48.131Z

utils.utils=> (-merge-attribs '({:A/A ""} {:A/A ""}))
{:A/A ""}

johanatan 2021-09-21T19:56:56.131200Z

the manual repl invocation is the "correct" one

johanatan 2021-09-21T19:58:39.131700Z

(i have deleted the target/ directory and restarted the repl so it should not be a stale code issue)