Fork me on GitHub
#clojure
<
2015-08-03
>
aengelberg01:08:18

Weird behavior in a Clojure 1.7 repl:

=> #=(list list)
()
Is this by design?

aengelberg01:08:48

I would expect to get back '(list)

nberger01:08:15

just checked and it's the same in a Clojure 1.6 repl

aengelberg02:08:09

clojure.tools.reader has the behavior I'd expect, but read-eval has significantly more functionality there anyway (resolving all sub-arguments instead of expecting symbols, etc.)

> (clojure.tools.reader/read-string "#=(list list)")
(#<[email protected]>)

nberger02:08:52

I don't know much about this area, but is it the same as the following?

user=> (eval (list 'list))
()

nberger02:08:31

I mean, is => #=(list list) roughly equivalent to => (eval (list 'list))?

aengelberg05:08:15

@nberger, I'm not an expert on the read-eval construct either, but I would interpret #=(...) to generally be equivalent to (eval '(...))

blueberry07:08:13

in my repl (emacs cider with clojure 1.7), it behaves as expected (list list) gives a list with one element

malabarba12:08:53

@aengelberg The two behaviors you describe are perfectly consistent

malabarba12:08:22

(read-string "#=(list list)") reads the string and returns (list)

malabarba12:08:48

Whereas typing #=(list list) on the rEpl will cause it to read and then *E*val the string. So the reader returns (list) and the repl evaluates that (which returns an empty list)

athos13:08:13

well… CLJ-1319 doesn’t seem to be fixed although it’s listed in changes.md

alexmiller13:08:02

hmm, you seem to be correct. it's possible other changes have foiled that change or something. will re-open.

ragge13:08:33

can't see that that patched was ever merged

alexmiller13:08:16

ragge: yeah, agreed

alexmiller13:08:43

I went through the rest of the list and I believe all other reported tickets for 1.8 were applied (I did find one jira number typo though)

athos13:08:52

Thank you, Alex!!

alexmiller13:08:08

@athos thank you for catching it!

aengelberg14:08:00

You're right @malabarba! I totally forgot that the REPL would be doing TWO passes, evalling the inner #= form and then evalling the whole form as usual simple_smile

bcobb16:08:20

👋 — any advice for debugging clojure.tools.namespace.repl/refresh throwing an error because it cannot find a namespace in my project? the project compiles normally, and the namespace definitely exists in a non-weird location

bcobb16:08:00

calling refresh from dev/user.clj in a component-y workflow

damien16:08:47

Hi, all. Can anyone recommend a performant Clojure > CUDA/OpenCL library?

trptcolin16:08:13

@bcobb: does that ns have any gen-class stuff going on? my advice is to (require '[ns.name.goes.here :reload true]) in the repl to see if you can rule tools.namespace out

trptcolin16:08:34

any user.clj on the classpath always gets loaded before anything else due to RT.java's static initializer - so if your user.clj needs some clojure stuff to run before it loads, you might need to restructure a bit

bcobb16:08:12

@trptcolin oh, good idea. grabbing food but will try that out after. thanks!

pmooser17:08:24

Is this ticket even possible to fix? It's been years ... http://dev.clojure.org/jira/browse/ASYNC-27

pmooser17:08:56

It would be so great if all of the line number info from the original code wasn't lost.

bcobb18:08:35

@trptcolin: tentatively saying that gen-class was the culprit. had system-building code in a gen-class ns, and extracting it to its own namespace so that the gen-class ns is not a dependency of anything seems to have fixed my problems

bcobb18:08:02

i wish i could say i understand exactly what’s going on, but i now have something concrete to learn more about simple_smile

trptcolin18:08:22

@bcobb: yeah i've hit this before, had a hell of a time debugging, and ultimately now i don't name my repl-init ns user.clj anymore

trptcolin18:08:39

because otherwise my user.clj might require my gen-class ns, which requires some clj compilation, which requires RT.java to be loaded, which hits https://github.com/clojure/clojure/blob/d534894c3006474068e46b67e4b838bf3727722d/src/jvm/clojure/lang/RT.java#L460-L480, which loads user.clj

trptcolin18:08:29

maybe i should blog this - i end up re-telling the sad story a lot simple_smile

stuartsierra18:08:44

@bcobb 9/10 of the problems I hear about with tools.namespace are caused by AOT-compilation

stuartsierra18:08:30

I also use dev.clj instead of user.clj now as @trptcolin suggests.

benbailey18:08:33

quick question: say I have something like a “player” which needs to be referenced across the game; is it idiomatic to have something like

(def player (atom {:name "Joe" :health 100 :denarii 10 :loc "here" :inv []}))

(defn get-player [key]
  (@player key))

(defn update-player [key val]
  (swap! player assoc key val))

bcobb18:08:39

@stuartsierra: ah, good to know, thanks for chiming in simple_smile

bcobb18:08:05

thanks for your help @trptcolin!

stuartsierra18:08:52

@benbailey: That's a global singleton, which is often convenient for small apps but quickly gets cumbersome when you have lots of them scattered across your app.

benbailey18:08:05

Yeah, I would imagine so. I guess I’m struggling of finding a functional way t o represent “actors” in the game.

benbailey18:08:59

I could always have one global state with actors as children, but that doesn’t seem right

stuartsierra18:08:42

@benbailey: usually there is some data structure representing the "state" of your entire application. This state can be created and managed by the entry point (`main`) of your app. Individual functions are passed that state or pieces of that state as arguments.

stuartsierra18:08:30

You can still have mutable references (`ref`, atom, agent) — at whatever level you need in the structure for efficient updates.

benbailey18:08:13

Okay, thanks! I was just concerned that the large structure might get unwieldy

stuartsierra18:08:13

update-in / assoc-in are your friends there simple_smile

benbailey18:08:22

awesome, thanks simple_smile

stuartsierra18:08:03

You're welcome!

lazy-lambda19:08:36

I am looking for clojure hosting solutions other than Digital Ocean

noisesmith20:08:52

@lazy-lambda: hosting clojure on aws and heroku are pretty straightforward (especially aws elasticbeanstalk for webapps)

lazy-lambda20:08:11

@noisesmith: Okay, I will check out AWS.

noisesmith20:08:55

lazy-lambda: with a webapp you can use lein uberjar, and simply upload the result as your jar (with a few pretty simple gotchas)

blueberry20:08:26

@damien ClojureCL supports OpenCL 2.0 and earlier.

podviaznikov21:08:23

@lazy-lambda: I started using http://tutum.co recently for clojure apps.

lazy-lambda21:08:07

@podviaznikov: Are you using tutum in production ?

podviaznikov21:08:07

I’m using it now while building new app. Started using it few months ago (have approximately 20 containers deployed to 4 nodes). If I don’t see any problems - I’ll use it in production

jeffmk22:08:48

@noisesmith: Example of the few pretty simple gotchas?

noisesmith22:08:34

jeffmk: you can't count on a persistent disk, or customizable system - the beanstalk boxes are cookie-cutter and you'll be moved to a new one with no warning basically

noisesmith22:08:02

good part - scaling is a cinch, hard part - developing an app that works within those constraints

noisesmith22:08:29

so eg. all resources need to use io/resource and not io/file, no creating files that are not in /tmp/ basically

pupeno22:08:57

Is there any better way of structuring a project regarding which directories contain clj and cljs and cljx?

nberger22:08:02

@pupeno: what's your pain with the directories structure? I guess you are using src/ and test/, but perhaps there's something specific to cljx? Is cljc an option?

sjol22:08:21

Hello, this is a more of beginner question but I'm trying to understand how I should go about iterating over a sorted map and it's content, so for a given list of maps I perform a group-by with the intent of sorting over each group's key values to display the content my code so far:

(let [sorted-by-url (sort-by :uri [{:user-id 1 :uri "/"} 
                    {:user-id 2 :uri "/foo"} 
                    {:user-id 1 :uri "/7"}
                    {:user-id 1 :uri "/3"}
                    {:user-id 4 :uri "/2"}
                    {:user-id 1 :uri "/0"}
                    {:user-id 4 :uri "/3"}
                    {:user-id 5 :uri "/account"}
                    {:user-id 5 :uri "/1"}]
                    )]
                    (let [sorted-map-of-users (into (sorted-map) (group-by :user-id sorted-by-url))]
                    	(println sorted-map-of-users)
                    	(doseq [[user content] sorted-map-of-users ]
                    		(println (str "----- " user "-------\n"  content)))
                    		(for [elem (seq content)] (println (str "--- " elem))) ;; this never seems to print
                    )
                    )
doesn't print the output I'd expect

sjol22:08:48

and can I sort the keys of the group-by hash map to go through them in order?

pupeno22:08:25

nberger: no particular pain, I’m looking at reframe and luminus templates and one has src and src-cljs and the other one has src/clj and src/cljs. Neither has a solution for test. I was wondering if there’s an advantage of one over the other.

nberger22:08:49

I guess src/clj & src/cljs is preferred: you can be sure you are looking to the entire codebase if you look into src. I think that, and having a cleaner root dir are the factors in favor of that layout

nberger22:08:21

I've seen some projects using src/main/{clojure,cljs} and src/test/{clojure,cljs}, I suspect for a similar reason

nberger22:08:50

But I'm no expert in directory layout simple_smile

danielcompton23:08:24

Is there a guide for setting up clojure.tools.logging in a library that will be consumed by other projects? I know how to set it up in my own apps, but I’m not 100% sure what to do about which logging dependencies go where?

potetm23:08:15

@sjol for is lazy. Use doseq

jeffmk23:08:43

@noisesmith: Thanks for the hints