Fork me on GitHub
#clojure
<
2016-12-15
>
ccann00:12:43

lein clean saved the day!?!

tbaldridge00:12:31

a lein....why you gotta be so dirty

tbaldridge00:12:06

no sure what it is with that tool, but about 2-3 times a week I hear a client, co-worker or someone here on this list have a problem fixed by lein clean

bfabry00:12:23

@ccann do you have any aot in your project?

ccann00:12:45

none that I’m doing

bfabry00:12:58

interesting. that's usually when I see lein clean fix things

talexxx01:12:52

This package’s function is failing when included in a defmacro and called from CLJ or CLJS, but works up to the last to-hiccup step: https://github.com/theJohnnyBrown/endophile/issues/11

talexxx01:12:03

Is there something I’m doing wrong or is it really a bug?

lyndsysimon01:12:31

I need some architecture assistance. I'm using yogthos' clj-log in a ring app, but need to be able to specify a function to create the log's data structure. The method that library uses to do that is here: https://github.com/yogthos/clj-log/blob/master/src/clj_log/core.clj#L25-L30

lyndsysimon01:12:48

I'm wanting to either fork and expand on this library or write my own. In Python (my "native" language), I'd create a Logger class with a default implementation of the make-message method, then subclass it to implement custom functionality. I'm confused about how to do it in Clojure. Obviously, subclassing it isn't correct.

lyndsysimon01:12:33

I want to be able to define the make-message function once, and have it applied everywhere in my application. The only way I know to do that would be to create a namespace for my logging tool - say, myapp.logging - implement the log function there, then import from that namespace everywhere in my app. Is there a better way?

gfredericks02:12:51

@lyndsysimon what don't you like about that method?

yogthos03:12:17

@lyndsysimon incidentally, I'm not really using or really maintaining clj-log aside from taking prs, I'd be happy to transfer it over if you plan on using it/working on it

peterromfeld04:12:06

hi, someone online who can help a bit with java interop? Java:

Settings settings = Settings.builder()
        .put("cluster.name", "myClusterName").build();
TransportClient client = new PreBuiltTransportClient(settings);
i tried quite a few things with -> or doto, but in the end i always get No matching ctor
(def client
  (-> (Settings/builder) 
      (.put "cluster.name" "elasticsearch_pair") 
      (.build)
      (PreBuiltTransportClient.)))

hiredman04:12:07

last time I looked at the es java api (this was several years ago) it changed pretty often

hiredman04:12:56

maybe check to see if whatever docs / example code you are following matches the version you are using

seancorfield04:12:04

@peterromfeld Perhaps a type hint is required?

seancorfield04:12:19

(def client
  (let [^Settings s (-> (Settings/builder) (.put ...) (.build))] (PreBuiltTransportClient. s)))

peterromfeld04:12:32

thanks, ive lunch break now.. will try when i get back to office and let you know

lyndsysimon04:12:53

@yogthos Good to know. I'll let you know if I decide to head that direction.

lyndsysimon04:12:03

@gfredericks I don't like that it doesn't seem very reusable.

peterromfeld05:12:28

@seancorfield no luck 😞 i tried again also with doto and also with (def ^TransportClient client ... but still only get No matching ctor

seancorfield05:12:16

Do you have the code up on GitHub somewhere that we can play with to try to help fix it?

seancorfield06:12:49

'k ... cloning ..

seancorfield06:12:23

Well, I can repro your problem 🙂

seancorfield06:12:44

Trying to find better documentation of that PreBuiltTransportClient class...

seancorfield06:12:22

OK, it's because it's a variadic Java method and takes an optional array of plugins as the second argument.

peterromfeld06:12:27

i remember last time i struggled with java interop i had to pass an empty array

seancorfield06:12:46

(-> (Settings/builder)
    (.put "cluster.name" "elasticsearch_pair")
    (.build)
    (PreBuiltTransportClient. (into-array Class [])))

peterromfeld06:12:46

awesome thanks!

seancorfield06:12:12

I couldn't resist a puzzle like that 🙂

peterromfeld06:12:38

i have no java knowledge and always struggle if i have to dive into this world 😕

seancorfield06:12:07

Actually you can just use an empty vector -- don't need (into-array Class []), just [] will do

seancorfield06:12:37

Oh, just noticed you linked to the JavaDocs... it was below the fold on my laptop... I should have scrolled down 😐

peterromfeld06:12:14

btw the rest was also not perfect documented but i figured it out 😉 works like a charm, i can just pass normal maps without any json encoding 😄

noprompt07:12:26

((fn [{:as m}]
   m)
 [1 2 3])
;; => [1 2 3]

noprompt07:12:27

not sure if that’s a bug or intended behavior.

noprompt07:12:40

discovered this via

(spec/conform :clojure.core.specs/binding-form '{:as m})
;; => [:seq {:elems [[:seq {:as {:as :as, :sym m}}]]}]

lxsameer07:12:19

is there any schema lib for transit ?

pesterhazy09:12:44

@noprompt that's expected. What did you assume the output to be?

m3nthal10:12:08

Hi, everyone. I have a small question. I have a vector of functions [f1 f2 f3] and I have a vector of arguments [a1 a2 a3], which function would produce [(f1 a1) (f2 a2) (f3 a3)] ? I guessed (map apply [f1 f2 f3] [a1 a2 a3]) but it doesn't work: Don't know how to create ISeq from: java.lang.Long

Prakash10:12:59

I think an interleave followed by partition will work

fellshard10:12:26

You actually need your function to be (partial apply apply)

m3nthal10:12:49

@pcbalodi I meant how do I apply f1 to a1, f2 to a2, f3 to a3

rauh11:12:08

(map #(%1 %2) fns params)

fellshard11:12:10

Alternatively, you could write that as (map #(%1 %2) ...)

m3nthal11:12:31

@rauh @fellshard thanks, it worked:)

sickill11:12:22

do I understand it correctly that (shutdown-agents) shuts down the thread pool backing agents and futures but it actually doesn't wait for the future threads to complete?

xificurC13:12:07

I'm looking at mongo's profiling output, which seems to be different for different operations. It outputs a JSON that is of nested and always different structure. Thanks to monger I have the profile output ready in clojure's data structures - a list of these weird nested maps. Is there some simple way to find the common structure of these maps? Like (common-structure '({:foo {:bar 1 :baz 2} :one {:two 2 :three 3}} {:foo {} :one {:two 2}}) --> [:foo [] :one [:two]]

hbprince13:12:46

is there way to precompile or configuring project.clj file to do so, hiccup clj files ?

sickill13:12:29

xifi: look at clojure.data/diff

xificurC13:12:25

sickill that's a close one, unfortunately it diffs the values as well, I'm only interested in the strucuture, i.e. the keys

xificurC13:12:53

I guess this will remain as an exercise for me 🙂

xificurC14:12:33

is first deterministic on a map?

dominicm14:12:23

@xifi that depends on what you expect to happen?

dominicm14:12:33

It will always return a key.

dominicm14:12:59

But maps aren't ordered, so the key you get will vary.

xificurC14:12:56

by deterministic I mean I get the same results. Your answer says - no. Thanks

agile_geek14:12:54

@xifi No on a hash-map, I'm guessing yes on a sorted-map or an array-map

lyndsysimon14:12:41

I'm dealing with deploying a ring app, and need to address credentials management. Elsewhere, we're using credstash, but I'm not seeing anyone talking about using it with Clojure. Does anyone have experience using credstash in Clojure?

dominicm14:12:39

@lyndsysimon I've seen KMS used directly from Clojure, and reading the encrypted form from a config file. What kind of integration would you expect from credstash? It doesn't expose an API that I can see, and is a CLI application?

lyndsysimon14:12:16

My first thought was just to shell out to it to get the creds I need. Not elegant, but would work.

lyndsysimon14:12:48

Thanks @dominicm. I'll look into amazonica; it's already in the project for something else anyhow.

lyndsysimon14:12:12

As usual, it looks like Clojure just does it, simply, instead of dealing with integrating some other technology.

dominicm14:12:40

@lyndsysimon Yep. That's pretty much it 🙂

karol.adamiec15:12:11

when i hava a function (defn refresh-address [id & {:keys [line1 line2 city postcode country]}] it expects to be called like (refresh-address 234435 :line1 “ASdf”) which is fine, but sometimes i would like to call it (refresh-address 12323 myObject) and have it pick out keys from inside. how can i have that?

lyndsysimon15:12:02

@karol.adamiec - I think you could use a multimethod. I'm still a fair green Clojurian, so take my advice for what it is.

lyndsysimon15:12:14

By "object", i assume you mean a hashmap?

dominicm15:12:19

@karol.adamiec You need to use apply

dominicm15:12:49

(apply refresh-address 234435 {:line "ASdf"}) should do what you want.

dominicm15:12:01

Hmm, not quite, you need to flatten the k/v thing one level.

dominicm15:12:14

@karol.adamiec ^^ That's what you want I believe.

lyndsysimon15:12:23

@dominic I think @karol.adamiec is asking how to write a method that will take arguments in either form, not how to call the method using its existing signature.

dominicm15:12:27

To my knowledge, this isn't possible with Clojure's arity detection, as it isn't typed. You would need to do an if inside the body of the function.

dominicm15:12:21

Generally, I don't find that I need this though, when I want to use the hashmap form, it's because I've built it programatically, and not because of requiring that abstraction.

karol.adamiec15:12:08

@dominicm you are right i want to call a fn with a map because that is what i get from other place

tosh15:12:34

anyone knows if there is a rainbow parens plugin for atom? couldn't find one so far

karol.adamiec15:12:40

(refresh-address 234 (apply concat {:line1 "asdf"})) throws ;/ @dominicm

karol.adamiec15:12:53

IllegalArgumentException No value supplied for key: clojure.lang.LazySeq@d04b25e7 clojure.lang.PersistentHashMap.create (PersistentHashMap.java:77)

karol.adamiec15:12:57

(apply refresh-address 234 (apply concat {:line1 "SDf"}))

karol.adamiec15:12:09

that works 🙂, cheers!

saeidscorp16:12:18

hey, is clojurebot accessible to anyone? or it's restricted?

agile_geek16:12:37

@saeidscorp just prefix any clojure expression with /clj

noprompt16:12:54

@pesterhazy so my expectation is (= true (let [{:as m} [1 2 3]] (map? m))).

noprompt16:12:47

the semantics are just confusing. there’s effectively no difference between {:as m} and [:as m].

noprompt16:12:48

of course, i’ve looked at how various destructuring notations are “expanded” but i’m not sure these are good semantics.

noprompt16:12:32

and i’ve known about this for a while. it wasn’t until last night when working a macro when began wanting to know why these are the semantics in the first place.

fabrao16:12:50

hello all, is there any library that we can execute functions in concurrency and call a handler after all execution be called?

noprompt17:12:14

@fabrao clojure.core/future?

noprompt17:12:16

(let [c1 (future (do ,,, 1))
      c2 (future (do ,,, 3))
      c3 (future (do ,,, 3))]
  (+ @c1 @c2 @c3))
;; => 7

fabrao17:12:43

hummmmmm, I´ll try it

noprompt17:12:51

@fabrao here’s an example which does a better job of illustrating the semantics.

noprompt17:12:53

(let [c1 (future (do (Thread/sleep 3000)
                     (System/currentTimeMillis)))
      c2 (future (do (Thread/sleep 1000)
                     (System/currentTimeMillis)))
      c3 (future (do (Thread/sleep 2000)
                     (System/currentTimeMillis)))]
  [@c1 @c2 @c3])
;; => [1481822280122 1481822278122 1481822279123]

fabrao17:12:46

How can I use it in a reduce? Is there any way?

fabrao17:12:08

(reduce #(conj %1 (future (do (func %2)))) [] [1 2 3 4]) ?

noprompt17:12:58

@fabrao you might want to look at using transduce in a case like that.

fabrao17:12:47

but can I use future inside?

noprompt17:12:55

@fabrao you shouldn't need to.

noprompt17:12:07

@fabrao i’d recommend reading up on transducers.

fabrao17:12:37

ok, thanks

cdine18:12:10

Given a valid form, what would be the approach to find all atoms used in the form . Any pointers please?

jrheard18:12:17

@cdine - what do you mean by a “valid form”?

jrheard18:12:11

are you using a particular library? are forms a particular kind of custom datastructure that your program uses? (apologies if your question is regarding something discussed earlier and i’m missing context)

jrheard18:12:07

http://stackoverflow.com/a/11782628/7293650 seems like a reasonable way of checking if something’s an atom, if that’s helpful

jrheard18:12:46

or perhaps you mean a valid clojure s-expression?

noprompt18:12:25

also by “atom” do you mean an atomic expression? e.g. ‘x 1 :foo “bar”

cdine18:12:40

I meant a valid sexp, yes.. read a user input string (a clj expression) as a data structure and find the atoms used in the expression

noprompt18:12:02

clarify “atom"

cdine19:12:00

a clojure atom.. concurrency ref type.. not an atomic expression...

jrheard19:12:51

gotcha - off the top of my head, i see two approaches: 1) figure out how to get a list of all of the symbols foo, bar, baz, etc used in the expression and then check their values in the way described in that stackoverflow post (simple but not 100% thorough - if the expression includes a call to a function like use-hidden-atom that uses some atom not mentioned in the expression itself, you won’t find that atom) 2) reagent solves a similar problem by having a custom record that behaves just like an atom, but which sort of “registers” itself as having been used whenever it’s dereferenced

jrheard19:12:05

option 2 is more thorough but a lot more complicated

jrheard19:12:22

perhaps there are other, better options too, those are just the main ones that come to my mind 🙂

jrheard19:12:13

just sorta depends on what you want to do / why you want to do it

mpenet19:12:00

map is lazy

josh_tackett19:12:18

Anyone know a way to measure the size of a ref? or atom?

mpenet19:12:28

You can swap it with mapv for instance

noprompt19:12:03

`
(def a (atom []))
(def b (atom {}))

(let [form '(f [a b c])]
  (reduce
   (fn [m x]
     (or (when-let [var (and (symbol? x)
                             (resolve x))]
           (when (instance? clojure.lang.Atom @var)
             (assoc m var x)))
         m))
   {}
   (tree-seq coll? seq form)))

noprompt19:12:15

# => {#'scratch/a a, #'scratch/b b}

noprompt19:12:40

@cdine this would work if you’re working with a raw, unevaluated, s-expression.

Pishty19:12:52

thank u so much @mpenet, but why was it working from the repl but not through async

jrheard19:12:06

the value of an expression entered into the REPL is printed

jrheard19:12:12

which forces it to be realized

jrheard19:12:49

that doesn’t happen in the async case, so because of laziness, your side effect doesn’t go off

jrheard19:12:34

this is why entering (range) into a REPL will lock it up, whereas you can do (def foo (range)) in your code just fine, etc

noprompt19:12:09

@cdine the use of tree-seq will produce a sequence of all branches and their children. we can then use reduce to filter out symbols that can be resolved to a var which currently points to an atom.

jrheard19:12:18

@pishty maybe this will be a helpful illustration:

cljs.user=> (defn foo [a-number] (println a-number))
#'cljs.user/foo
cljs.user=> (map foo [1 2 3])
1
2
3
(nil nil nil)
cljs.user=> (let [bar (map foo 123)]
       #_=>   nil)
nil

noprompt19:12:55

@cdine you can extended this technique in several interesting ways like locating free variables, etc.

jrheard19:12:47

when i write (map foo [1 2 3]) into the REPL, it prints out the value of that expression (that’s P in REPL), which causes the lazy map expression’s value to be fully realized

jrheard19:12:11

but when i eg define a variable named bar and don’t cause the REPL to print it, it stays lazy / unrealized

Pishty19:12:42

thank u so much for the explanation @jrheard , i think i understand. does this mean whenever we want to insert a list into a db we have to make sure that the list is fully realized

jrheard19:12:40

it sorta depends - i think the issue here is that you’ve got this function:

(defn upsert-into-db [reddits]                                                                                                                                                                                                      
   (map #(upsert-record %) reddits))   
and its purpose is to cause side effects to happen, but it’s implemented using map, which is lazy

jrheard19:12:08

so the issue isn’t whether or not reddits is a lazy sequence/list/whatever, it’s that your function is supposed to run side effects over its inputs but the function itself is lazy so it doesn’t always do that

jrheard19:12:42

i think the solution is to make sure that your side-effecting functions aren’t implemented that way - eg switching the map to a mapv like mpenet suggests will accomplish that here

jrheard19:12:48

if your side-effecting function is “eager” (the opposite of lazy), it shouldn’t matter whether or not its inputs are lazy, it’ll force them all to be realized

Pishty19:12:01

thank u again @jrheard i think i understand what i was doing wrong in this instance but i think i need to read more on lazy and eager functions in clojure and when to use one over the other

jrheard19:12:20

np! yeah, it can be a bit confusing

jrheard19:12:39

it’s almost like a whole extra separate implicit type system

jrheard19:12:06

my function takes a list of foos and returns a bar but it’s lazy, my other function has the exact same inputs and outputs but it’s eager, etc

Pishty19:12:30

🙂 yes exactly

jrheard19:12:51

laziness is primarily useful if you want to write a program that operates on a huge or even infinite amount of data and doesn’t immediately fall over

jrheard19:12:01

that’s my understanding of it, anyway

jrheard19:12:25

which is handy but you don’t always need it! anyway good luck 🙂

Pishty19:12:42

thanks man

cdine19:12:47

@jrheard and @noprompt , thanks for the overwhelming responses.. I will give this a shot when I get back to work.. But thanks again..

genec20:12:38

any suggestions on a good "learning clojure" book for an experienced delphi / python / F# developer? would like to use clojure to build some dashboard style UI's to visualize financial simulation results at work, most likely with D3. But need to walk before trying to run. 😉

genec20:12:59

I liked the looks of Living Clojure, but it may be a bit out of date as it's using enfocus for the UI chapter

shaun-mahood20:12:07

@genec: I don't think Living Clojure is out of date - I would try using it to learn, then move on to the tools that make the most sense for your use case.

genec20:12:16

@shaun-mahood thanks, do you think it's a good book to start out with? any other suggestions?

shaun-mahood20:12:29

@genec: Lots of good resources at http://clojure.org/community/resources - it seems like Living Clojure and Clojure for the Brave and True both receive quite a few recommendations as a first Clojure book

genec20:12:40

@shaun-mahood great, thanks. that's pretty much the 2 books that looked good to me too. I'll take a look at the resources too.

danielcompton21:12:48

Does anyone know if you can do this: https://blog.heroku.com/postgres-essentials#track-the-source-of-your-queries with clojure.java.jdbc or other Clojure DB libs?

juhoteperi22:12:45

@danielcompton The mentioned libs just append a sql comment with location to each query

juhoteperi22:12:25

E.g. Hugsql could do this, but I don't think there is a way for java.jdbc to get file & location of the function call

danielcompton22:12:07

probably not without macros AFAIK

juhoteperi22:12:56

Yeah with macros it would be possible

juhoteperi22:12:12

(defn query' [db sqlvec file {:keys [line column]}]
  (let [sqlvec (update sqlvec 0 str (format " -- %s on line %s, column %s" file line column))]
    sqlvec))

(defmacro query [db sqlvec]
  `(query' ~db ~sqlvec ~*file* ~(meta &form)))

(comment
  (query nil ["SELECT * FROM foo"])
  ;; => ["SELECT * FROM foo -- /tmp/boot.user7194000466341961541.clj on line 53, column 3"]
  )

juhoteperi22:12:47

Oh, fireplace repl messes up file in that example

jrheard22:12:29

@genec i liked “clojure programming” fwiw, haven’t read brave-and-true though