#clojure log - Jul 15 2014

The Joy of Clojure
Main Clojure site
Google Group
List of all logged dates

0:00 elben: I meant “do”, but I also use corea.sync and go blocks, so still useful

0:01 kristof: elben: In go, if you've got 10000 go procs running on a 4 core machine and just 4 of those goroutines have no function-calls and no channel ops (just tight loops), they will starve every other proc on the system until they're done.

0:01 elben: ok, that’s what i would expect

0:02 right, because in clojure go uses some small number of threads i I’m correct

0:02 My question was in the context of clojurescript, which does not use threading

0:03 so a tight loop would indeed starve everyone else

0:04 kristof: Yes. But if it's a tight loop, why is it in a go block? :P

0:06 elben: you’re the one who first mentioned a tight loop :)

0:06 kristof: elben: Anyway I would think no. Your do block would hold up everyone else until somewhere in the do block you put or take.

0:06 elben: i was trying to understand how clojurescript, om and core.async function in a non-threaded, async, single-process world i.e. a browser :)

0:06 nathan7: elben: JS has an event loop

0:07 well, it's not part of the JS spec presently, but every JS runtime has an event loop

0:07 only once things hit the event loop, events are dispatched

0:08 so no, your code won't ever be interrupted in the middle

0:08 kristof: ^

0:08 elben: thank you, that’s the original question :)

0:08 kristof: Erlang does some interesting pre-emption

0:09 elben: yes, i recall taht. they have some kind of counter for actiosn per threadlet?

0:09 kristof: But minimizing latency through pre-emption throttles throughput!

0:09 elben: Yeah, like a running total of "ops" fired. I can't remember if BIFs count.

0:09 nathan7: I'm still getting used to thinking with threads around

0:10 I'm mostly a JS programmer, I can read you the ES5 spec backwards from memory and all, so I normally just get to assume everything just runs to completion without interruption

0:10 elben: kristof, makes sense. there’s always context switch overhead, even for “green” threads.

0:10 nathan7: unless I'm firing off something async

0:11 technomancy: kristof: it's considered a bug if any call gets missed by those counts IIUC

0:11 elben: “unless”?

0:11 nathan7 ^ in what circumstances would the event loop “take over” control?

0:11 nathan7: elben: well, if I hand something a callback, that'll of course run in a future turn of the event loop

0:11 elben: i assume the user program must give up contorl to the event loop

0:11 nathan7: yes

0:11 the event loop lives at the bottom of the stack

0:12 kristof: technomancy: I know that there's something related to BIFs... or perhaps it was calling C routines... that one has to be careful of.

0:12 nathan7: well, right below the JS stack

0:12 elben: I see, just making srue

0:12 nathan7: in any real program you'll do stuff async

0:13 because blocking the event loop is highly undesirable

0:13 well, any program doing I/O

0:14 kristof: elben: The cost of context switching would mostly come from stuff like cache misses, actually

0:14 elben: Want to know what an erlang actor is? (lambda () (;; loop and match message with dispatch function))

0:14 elben: hmm i remember a go lang paper talking about that. basically the “secret sauce” of the go scheduler is dealing w/ cache misses

0:15 kristof: Actually, just ignore the "loop" part. At the end of a single receive it'll get scheduled!

0:15 elben: ^ don’t take my word for it though, was just skimming

0:15 kristof: *scheduled out

0:30 technomancy: kristof: oh yeah, there was a bug where NIFs weren't tracked correctly in R14 or something.

0:34 kristof: elben: Secret sauce? They do avoid cache misses by trying to keep the same goroutines on the same processor.

1:08 _1_angga: australia

1:19 benkay: indochina?

1:24 i've got :uberjar {:aot [van.main]} (the ns with my the main function for my app) in the :profiles map in project.clj and yet when I run lein uberjar and then java -jar van_standalone.jar, java complains that it cannot find or load class van.main. thoughts?

1:25 :gen-class in the main ns?

1:26 spammers in #clojure again...

1:26 kasmoin, for the record.

1:29 kegund: I made the switch to ERC on day 4 of clojure (from freenode HTML). It feels great!

1:33 benkay: how much of your life have you poured into your .emacs so far?

1:33 kegund?

1:35 kegund: yeash... 13 years

1:36 benkay: erc is really what made me serious about honing my .emacs. i haven't lost much time to it...yet.

1:37 kegund: I've hardly been serious... though a dozen years of emacs kind of adds up.

1:37 I just cleared my .emacs last Friday when clojure wasn't working right in emacs.

1:38 hellofunk: benkay what kind of erc stuff do you have in your .emacs?

1:38 kegund: about ""

1:38 exactly ""

1:39 hellofunk: sorry... I'm new

1:46 deadghost: my emacs is 800 lines

1:46 ~8 months in

1:46 clojurebot: excusez-moi

1:47 deadghost: still haven't put in erc because it seems like a pain to get it to xchat functionality

1:50 hellofunk: if you live inside emacs and have a large monitor, it is quite useful to have your irc as a window inside emacs

1:51 deadghost: hellofunk, when you say useful

1:51 you mean distracting right

1:51 hellofunk: no, i consider those two words to have different meanings

2:52 Frozenlock: Especially for Clojure, because the official doc is #clojure

3:05 razum2um: i'd like to use foundation library (in my foss) inside of https://github.com/JetBrains/intellij-community/blob/master/platform/util/src/com/intellij/ui/mac/foundation/Foundation.java is there any way to pack it apart as a lib? why isn't it separeted already?

3:06 is it permitted by Apache License?

3:08 johnwalker: technomancy: do you sign the books in your dotfiles?

3:08 ;)

3:18 jack_rabbit: razum2um, you might try reading the Apache 2.0 license. It's not too long or difficult to understand.

3:18 razum2um, in short, you can probably use it for whatever you want. There are certain conditions laid out in the license that you should read and be aware of.

3:19 razum2um: jack_rabbit: btw is there any another lib to invoke objc methods?

3:21 jack_rabbit: razum2um, not sure, but objective-C has C interoperability. Once it's object code, you should be able to call into it with JNI. That said, I've never done it, so there might be complications I'm not aware of.

4:46 daGrevis: ,(map #(* % %) range(2))

4:46 clojurebot: #<ClassCastException java.lang.ClassCastException: java.lang.Long cannot be cast to clojure.lang.IFn>

4:46 daGrevis: whoops

4:46 ,(map #(* % %) (range 2))

4:46 clojurebot: (0 1)

5:09 hellofunk: in Om I can log a vector that contains both clojure as well as js numerals, such as [12 #<455>] however if I attempt to place the second of these in a dom/td cell, it prints onscreen as 4550. is this some sort of js->cljs issue?

5:09 like adding a 0 to the end of things, why would that happen?

5:13 boxed: have you looked at the DOM? is it just one text node for “4550”?

5:15 hellofunk: boxed ahh good catch.

5:15 boxed: no problem :P

5:16 hellofunk: are you happy with Om otherwise? I had a lot of trouble with getting it to do what I wanted, so I gave up and went to Reagent instead which I am very happy with

5:16 hellofunk: boxed: yes, Om is quite amazing.

5:16 not having any problems at all

5:17 boxed: I could never figure out when you had to add #js and when not to… and I got annoyed at the sprinkling of “nil” all over the place

5:18 hellofunk: boxed you could have removed both of those concerns if using Om with Sablano (which I'm not doing)

5:18 boxed: ah, did not know that

5:18 * nathan7 is enjoying Reagent a lot

5:19 boxed: Reagent is pretty damn nice I must say… I think it deserves as much hype as Om

5:19 nathan7: it's everything I was hoping Om would be

5:19 just Clojure data types and pure functions

5:20 hellofunk: nathan7 well that's what Om is as well, no?

5:20 boxed: yea, I still don’t get the whole cursors thing, and I’ve read the docs several times :(

5:20 nathan7: hellofunk: with Sablono it's close to what I'd like

5:21 with Reagent's reactive atoms it's 100% there

5:21 boxed: hellofunk: I’ve never written a single #js or nil in Reagent, without adding another lib :P

5:21 hellofunk: boxed the #js is there because sometimes you do want to pass a pure javascript notation for any number of things, but you don't have to if you don't want to.

5:21 boxed: plus reagent worked first time… had loads of trouble getting Om to do anything

5:22 hellofunk: Om is a bit complicated but it worked out of the box for me

5:22 nathan7: it means binding your every component quite strongly to it

5:22 with all the om/blah

5:23 well, dom/blah

5:23 hellofunk: I guess I'd have to see Reagent in action to understand the distinction

5:24 nathan7: [:h1 "this is how we do it in Reagent"]

5:24 and just @blah

5:24 hellofunk: nathan7 that's not reagent, that's sablono, no?

5:24 nathan7: well

5:25 hellofunk: well, yes, I just realised I picked the wrong difference

5:25 hellofunk: You can get that same syntax with Om just fine if you use Sablono there too

5:25 nathan7: it's been over 24 hours since I awoke

5:25 my brain is slightly off

5:25 boxed: hellofunk: good defaults count though…

5:26 nathan7: hellofunk: when you dereference an atom while rendering, it remembers that

5:26 hellofunk: and it knows to rerender that when the atom changes

5:26 hellofunk: Om seems pretty well thought out and very highly performance so I'd have to see better examples to agree that there was a better alternative right now

5:27 nathan7 and what gives you the impression that Om's engine is not watching state changes as well? Because of course that is the entire point behind Om and React

5:27 nathan7: hellofunk: I can have as many atoms as I want

5:28 mi6x3m: clojure

5:28 why is the doc comment not included in the meta

5:28 the-kenny: nathan7: You can have as many different states in Om too. Either nested, or via different om/roots.

5:28 mi6x3m: if I specify custom stuff with ^{...}

5:28 nathan7: the-kenny: I don't have to have extra roots for Reagent, however

5:28 the-kenny: Why do you need multiple atoms then anyway?

5:29 hellofunk: I'm still waiting to here a good example of what Reagent does that Om does not.

5:29 the-kenny: One root, one "application", one single consistent state over the whole application

5:29 boxed: hellofunk: It’s not about what features Reagent has that Om does not imo, it’s about the ease of use of the features either has

5:29 nathan7: I have a homebaked DB that has live-updating documents

5:30 boxed: perl has all the features, it sucks :P

5:30 nathan7: I wrap my JS-land DB documents in an atom that gets reset when the DB document gets updated

5:30 I don't have to tell Reagent shit

5:31 and the set of documents that is displayed varies of course

5:31 the-kenny: nathan7: Om works the same.

5:31 nathan7: I don't have to maintain a set of Om roots or whatever

5:31 or have a global map that everything lives in

5:31 the-kenny: What's wrong about a map containing multiple DBs?

5:31 nathan7: I can just read from an atom and everything automagically updates

5:32 and I intend to extend the atoms a little more so my DB stuff can see what atoms are actually being watched

5:32 so unused documents are dropped

5:32 and I can use my DB as if it's entirely local

5:32 the-kenny: *shrug* I don't really want to discuss the differences in detail. I'm a pretty happy Om user in multiple projects :)

5:33 nathan7: the-kenny: basically, I get to write reactive UI as if it's not

5:33 the-kenny: nathan7: It's the same in Om...

5:34 hellofunk: The only thing nathan7 has mentioned that I don't understand is the "atom getting reset when DB document gets updated" -- in Om, I have a separate core.async go block that investigates outside changes and then delivers anything necessary to the Om atom on a channel.

5:34 and then of course Om automatically reacts to whatever new state is has

5:34 the-kenny: hellofunk: That's the preferred way iirc. You can also just modify the atom outside om. Works fine too.

5:34 What brings me to my question: Anyone got an idea to selectively *disable* a portion of code (in my case weasel-repl) when I build the application with :optimization :advanced? I need Closure to fully *strip* the code, as our security policies won't allow eval() in the generated JS.

5:35 hellofunk: the-kenny it is not advised that you modify the Om atom outside Om. For high performance, you should let Om schedule all updates only inside an Om render cycle

5:35 the-kenny: I know

5:35 nathan7: hellofunk: This means my UI stuff has to handle it differently from regular code though

5:36 hellofunk: Om is very much a strong MVC reactive system, so I can only suspect that you weren't using it as designed if you felt it wasn't doing these things.

5:36 the-kenny: nathan7: Well. The performance is quite good even when modifying the atom from the outside.

5:36 nathan7: derefing an atom handles all — even if that's inside some function that's entirely unaware of that

5:36 hellofunk: It's important to note that while React is a very fast JS library, Om has been benchmarked to be another 2 - 3X faster than React because of how it schedules state updates. I'd be very surprised if Reagent has that sort of implementation going on, but maybe it does (which I doubt).

5:37 nathan7: hellofunk: It re-renders if atom values aren't identical?

5:37 hellofunk: what?

5:37 clojurebot: what is a better one i think: https://github.com/michaelklishin/neocons

5:37 nathan7: hellofunk: so Om might be doing something faster there, yes

5:37 hellofunk: Nathan7 the entire point of React is to re-render things that have changed, so both Om and Reagent would be doing this

5:38 nathan7: hellofunk: mhm

5:38 boxed: hellofunk: pretty sure the whole “immutable data structure” thing gives a lot of speed advantages to Om and Reagent equally, compared to normal React

5:38 the-kenny: boxed: Yup, that sounds right.

5:38 locks: isn't Reagent basically bindinds to ReacT?

5:39 nathan7: hellofunk: But Om might be doing something smarter than just identity comparison

5:39 hellofunk: by using cursors and all

5:39 the-kenny: On the plus side for Om: It might know *which* subtree(s) changed without even comparing them to the last state, so it can optimize even further by telling React only those differences

5:39 That's a big plus, brought by the cursors.

5:39 hellofunk: nathan7 Om has some quite sophisticated source code worth looking at, it is doing some very interesting things

5:41 boxed: the-kenny: you’d have to have a pretty huge tree of state for that to make much difference though right? I mean, if a subpart has changed it should be at worst binary search type time complexity to find that subtree?

5:41 michihuber: could somebody help me out with a silly java issue (never did java stuff before)?

5:41 $ jar tf ./some.jar | grep ragtime/main

5:41 ragtime/main$_main.class


5:41 ragtime/main$migrate.class


5:41 ragtime/main__init.class

5:41 ragtime/main.clj

5:41 $ java -cp ./some.jar ragtime.main migrate

5:41 Error: Could not find or load main class ragtime.main

5:41 the-kenny: michihuber: Aww don't paste code here please.

5:42 michihuber: sorry

5:44 mi6x3m: how does clojure abbreviate clojure.string?

5:44 strng?

5:44 the-kenny: boxed: Yes, that's right. Still I find it more pleasant to have constant-time diffing in case of transact! or update!

5:45 mi6x3m: I usually use [clojure.string :as s] or just :refer [...], if that's what you're asking

5:45 mi6x3m: the-kenny: i also only refer usually

5:45 but recently thought i might start to abbreviate

5:45 tnx

5:46 nathan7: mi6x3m: :as str perhaps?

5:46 (str/join …) reads nicely

5:46 mi6x3m: nathan7: shadows str

5:46 nathan7: mi6x3m: that doesn't really matter

5:46 mi6x3m: namespaces don't shadow vars

5:47 mi6x3m: nathan7: ah, then str is indeed better :)

5:47 didn't know that

5:47 nathan7: I do it all the time

5:47 I have a type called Metric, vars containing it usually called metric

6:06 Glenjamin: they make it sound simple, but there's some serious work gone into efficient tree diffs and IE8 support

6:06 mtrimpe: The big advantage of a Clojure version would be that it wouldn't need to do tree diffs of course...

6:06 kerneis: Om more or less directly translates React's idea of a single global state flowing through

6:07 Glenjamin: mtrimpe: you still need tree diffs to decide what to do to the DOM

6:07 kerneis: but while it is important in javascript to ease design and immutability, I'm not sure it's necessary to keep it in cljs

6:07 Glenjamin: and if you have any derived data being passed to child components, identity checks aren't particularly useful anymore

6:08 eg (map func coll) will never pass an identity check

6:08 mtrimpe: Glenjamin: An idiomatic Clojure clone would be closer to what e.g. Hoplon does...

6:09 Glenjamin: ah, hoplon seems neat

6:09 mtrimpe: Glenjamin: Track changes in the data and then figure out the optimal way to reflect how that affects the DOM

6:11 Yeah; except Hoplon doesn't really buy into the React philosophy of only keeping visible elements in the DOM

6:12 A Clojure react clone could be something like a source atom with a function that builds a UI from that data…

6:12 and then have a macro that memoizes that function graph and applies changes only when needed...

6:15 the-kenny: I don't really see the point in rewriting React in Clojure(Script). Way too much work, and (as far as I can see) it already integrates quite fine

6:17 mtrimpe: Yeah that's the thing… React gets you 80% of the way there with 20% of the effort.

6:18 Would still love a pure Clojure version though… I'm pretty sure you would end up with something simpler…

6:20 the-kenny: likely. Still I would never even want to think about re-implementing the event system in a *correct* way over all the browser implementations ;)

6:22 mtrimpe: Yeah; that's the biggie React handles under the hood...

6:23 Still; even a version that doesn't paper over those problems (yet) could already be valuable…

6:31 nathan7: the-kenny: It's mostly "hey that seems fun and interesting to do"

6:57 martinklepsch: when using projectile in emacs it somehow uses my src/projectname directory as root rather tan the one that contains project.clj

6:57 anyone had that problem as well?

6:59 hellofunk: the-kenny i'm curious how Om handles the situation where you write over an entire vector but only one of the items in the vector changes; is it smart enough (or perhaps this is on the React side) to not update other items that did not change?

7:00 the-kenny: hellofunk: I think so. build-all uses the index as :react-key, iirc.

7:00 hellofunk: You can also provide your own react-key.

7:01 hellofunk: the-kenny okay so if I completely replace [1 2 3] with [1 5 3], there would be the advantage of the persistent data structure not change the 1 and 3 and then the additional advantage of React not seeing any changes on the 1 and 3 even if they were actually recreated?

7:01 the-kenny: I think so

7:02 I'm not sure if Om will trigger the component-function for each val in the vector though.

7:03 hellofunk: the key-stuff also makes sure that components don't get destroyed and recreated if their index changes.

7:03 hellofunk: I wonder if it makes a difference for performance if you use om/update! on a deep cursor passed as an arg to a component, or if you use a path of korks in an update to the main parent app-state, each of these should be equally as fast?

7:04 the-kenny: Not sure, but the API would allow to optimize both

8:01 sharps: Need help: working with File i/o, but I want my clojure CLI to open current user's $EDITOR the same way Git opens it for messages. How would i go about doing that?

8:05 luxbock: https://github.com/hhutch/om-bootstrap/blob/master/src/om_bootstrap/dom.clj

8:05 I'm trying to figure out why `(gen-react-dom-inline-fns)` is needed at all in this code but I can't wrap my head around it

8:06 I know it's needed as if I comment it out then the thing stops working

8:06 but I just don't see where the macros that get created from that call are ever used

8:07 kerneis: sharps: copy the file to a temporary location, exec $EDITOR temp-file, wait for editor to return, copy modified file back

8:07 (or exec editor directly on the original file)

8:08 sharps: http://clojure.github.io/clojure/clojure.java.shell-api.html should be useful

8:09 Glenjamin: luxbock: https://github.com/hhutch/om-bootstrap/blob/master/src/om_bootstrap/dom.cljs#L2

8:09 it makes more sense in the real om source

8:15 luxbock: Glenjamin: sorry what do you mean in the real Om source?

8:17 xavierriley: What's the best option for jumping between tests and code in emacs?

8:18 bob2: clojure-test-mode

8:18 luxbock: my trouble in understanding this is that I don't see how the call to `gen-react-dom-fns` in dom.cljs invokes any of the macros created by `(gen-react-dom-inline-fns)`

8:18 bob2: unless technomancy 's fancy thing is working now

8:19 xavierriley: thanks - I think I'm setting up at a point where I fall between the cracks of fancy thing working and test-mode being deprecated

8:21 twiceaday: can i paste

8:21 here really short example of the source code in clojure that i am trying to understand ?

8:21 it is solution to this

8:21 http://www.4clojure.com/problem/28

8:27 vyorkin: hi everyone! i'm trying to solve a very simple task in clojure, its http nested parameters parsing, here is my solution http://pastebin.com/xNHG3ha0

8:28 it almost works, but i'm doing smth wrong because if i have a nested array it'll be overriden by the next hashmap

8:29 e.g. a need to get a "d" ["1" "2"] not just "d" ["2"]

8:29 what am i doing wrong?

8:30 kerneis: twiceaday: if its a one-liner it's fine, otherwise use a pastebin service

8:30 vyorkin: (by overriden i mean overwritten, sorry)

8:31 bob2: do you mean "I'm trying to parse php-style GET parameters"?

8:31 vyorkin: it's a rails-style also as far as i know

8:31 rack-style, excuse me

8:38 kerneis: vyorkin: notwithstanding your bug, you miss a "w" in your expected result

8:38 (or I don't understand what you are trying to do)

8:40 vyorkin: kerneis: oh, sorry, i right, but unfortunately thats not the main problem(

8:40 kerneis: i expect to get {"x" ["1" "2" "3"], "a" {"b" {"w" {"y" "3"}}, "c" "2", "d" ["1" "2"]}}

8:41 kerneis: but i've got {"x" ["1" "2" "3"], "a" {"b" {"w" {"y" "3"}}, "c" "2", "d" ["2"]}}

8:42 kerneis: i right = you are right

8:45 kerneis: vyorkin: your problem is that:

8:45 ,(into {"d" ["1"]} {"d" ["2"]})

8:45 clojurebot: {"d" ["2"]}

8:46 kerneis: because:

8:47 ,(conj {"d" ["1"]} {"d" ["2"]})

8:47 clojurebot: {"d" ["2"]}

8:47 kerneis: namely, conj does not do what you have in mind

8:48 (and into uses conj implicitly)

8:48 vyorkin: omg, thanks, didn't know about this

8:48 i can see now this (reduce conj to from)

8:49 now i wonder how to implement this correcty (%

8:49 mercwithamouth: o_O;

8:49 kerneis: well you should try and write a function to use instead of into

8:50 when you are done, maybe you'll notice this is an already existing function (but I don't think so at first sight)

8:50 vyorkin: when to you think about my solution? i've just started to learn clojure

8:51 so may be there is a better way to solve this? how bad my code is? (%

8:53 kerneis: I don't have much clue about the whole problem, because I don't know what the original specification is exactly

8:53 the format since very crappy to be honnest

8:53 but in any case, you might be interested in this function:

8:54 ,(update-in {"d" ["1"]} ["d"] conj "2")

8:54 clojurebot: {"d" ["1" "2"]}

8:54 vyorkin: kerneis: thanks!

8:54 kerneis: ,(update-in {"a" {"d" ["1"]}} ["a" "d"] conj "2")

8:54 clojurebot: {"a" {"d" ["1" "2"]}}

8:57 kerneis: if you are smart enough, I believe you can get rid of transform, and directly (reduce #(update-in ...) {})

8:58 vyorkin: kerneis: thanks for your feedback

8:58 xavierriley: I'm just trying a code kata and leiningen seems to be holding onto some previous version. I run `lein test` and it says 1 test containing 0 assertions when I have 4 assertions and I've definitely saved the file. Any suggestions as to how I sort this out?

8:59 vyorkin: kerneis: i'll try to do this by myself, cuz i need to learn

8:59 kerneis: (I have an almost solution, don't hesitate to ask if you need more details)

8:59 (but you are right, it's better if you dig it by yourself)

9:00 Glenjamin: xavierriley: try lein clean

9:01 xavierriley: no difference with lein clean

9:17 `lein clean` thing turns out to be PEBCAK - I didn't use (is ..) in the tests

9:28 imperman: Hi, does anybody know any Clojure HDL DSL (for digital design FPGA/ASIC)? I found PIplin (https://github.com/dgrnbrg/piplin) but it's not longer in development.

9:29 mr-foobar: seangrove: is there a protocol for undo/redo/state ?

9:31 imperman: mr-foobar: maybe try to add a watcher function. http://stackoverflow.com/questions/9847245/pattern-for-implementing-undo-redo-in-clojure

9:33 gfredericks: ,(def a (doto (atom nil) (add-watch :x (fn [_ a old new] (alter-meta! a update-in [:history] (fnil conj []) old)))))

9:33 clojurebot: #'sandbox/a

9:33 gfredericks: ,(swap! a (constantly 12))

9:33 clojurebot: 12

9:33 gfredericks: ,(swap! a inc)

9:33 clojurebot: 13

9:33 gfredericks: ,(swap! a inc)

9:33 clojurebot: 14

9:33 gfredericks: ,(swap! a + 5)

9:33 clojurebot: 19

9:34 gfredericks: ,(:history (meta a))

9:34 clojurebot: [nil 12 13 14]

9:36 mr-foobar: neat, thx gfredericks, imperman !

9:46 https://i.imgur.com/1ZuiGic.jpg :)

9:48 imperman: mr-foobar: http://aphyr.com/data/posts/314/monads.jpg ;)

9:52 razum2um: I'm trying to release to clojars but signing fails like this https://gist.github.com/razum2um/87ec980408ad1c77a55b (using mac 10.9) why i'm not asked for gpg passphrase?

9:52 mr-foobar: imperman: that's it, if I ever have a pet I will call it state and put it in a box :)

9:54 Fare: mr-foobar: with all those monadic combinators starting with m- I read your name as m-foobar and was wondering what kind of combinator you were.

9:55 Anyone going to the International Lisp Conference 2014 in Montreal (Aug 15-17) ?

9:55 mr-foobar: Fare: i am the unrepairable kind :)

9:57 jdkealy: i have been using om to build a tab component, onclick it sets the state of the tab component as some key, and then calls om/build function on the appropriate passed in component, however i'm finding that if i click on tab, then another, then go back to the first, IDidMount appears to never be called the second time I build it. I tried passing in a new react key every time, but still.

9:58 ambrosebs: Fare: yes

10:00 mr-foobar: jdkealy: if tab-component is rendered once, the IDidMount is also called once.

10:00 Glenjamin: if the key is different it should cause a did-mount

10:02 imperman: Fare: hm... to far away from Ukraine :(

10:03 nathan7: razum2um: do you have a gpg agent configured at all?

10:03 jdkealy: yeah it's strange, i'll debug some more try try to figure out what's going on

10:03 Fare: imperman, it's a small world. $ not km is the distance that matter.

10:05 imperman: Fare: course, it's far away in $ at now ))

10:06 jdkealy: so hypothetically, if you don't pass in a react key, it should call IDidUpdate when you om/build the component again ?

10:07 Glenjamin: jdkealy: if shouldUpdate was true, yeah

10:07 jdkealy: i thought in the docs, it basically said "never use shouldUpdate"

10:08 Glenjamin: in om you probably don't need to touch it, this is true

10:22 michaelr525: Hi

10:22 I'd like to do the basic Om tutorial here: https://github.com/swannodette/om/wiki/Basic-Tutorial

10:23 Using Emacs and cider instead of lighttable

10:23 How should I go about it?

10:24 nullptr`: michaelr525: the easy way is to skip the live brower repl and just hit refresh

10:24 michaelr525: nullptr`: i see

10:39 boxed: am I missing something? I can’t find how to do named groups in regexes…

10:40 michaelr525: nullptr`: why go the easy way when we can go the hard way :)

10:41 nullptr: what's the shortest route for adding a brepl?

10:42 nullptr: once upon a time it was https://github.com/cemerick/austin

10:43 michaelr525: nullptr: 10x

10:43 cbp: michaelr525: use weasel

10:43 michaelr525: weasel?!

10:43 cbp: it's faster and easier than austin

10:44 and not as buggy

10:44 $google clojure weasel

10:44 lazybot: [tomjakubowski/weasel · GitHub] https://github.com/tomjakubowski/weasel

10:45 michaelr525: cbp: i'll check it thanks!

10:47 it's readme is definitely shorter

10:47 hhenkel: Hi all, is there a way to use mapcat in a way that I can give one collection that is applied and a second collection is given as one whole thing?

10:48 Glenjamin: hhenkel: can you give an example input/output please?

10:49 hhenkel: Glenjamin: I'll try, omething like (mapcat my-func [ 1 2 3 ] [ a b c]) where the [a b c] should handed over completly.

10:49 borkdude: what is up with Uncaught ReferenceError: goog is not defined app.js:1 (anonymous function) in a compiled clojurescript js file?

10:51 Glenjamin: hhenkel: so (my-func 1 [ a b c ]) ?

10:52 hhenkel: Glenjamin: yes, and so on for the other values

10:52 Glenjamin: (mapcat #(apply my-func % others) [ 1 2 3])

10:54 nullptr: alt: (mapcat my-func [1 2 3] (repeat [a b c]))

10:55 hhenkel: Glenjamin: nullptr: I think I'll go with the alternative version as % is allready in use in my code.

10:55 kerneis: borkdude: <script src="out/goog/base.js" type="text/javascript"></script>

10:55 or something like that?

10:56 at least that's what Om tutorial does

10:56 borkdude: kerneis Thanks. I wonder why this html doesn't have it: https://github.com/ckirkendall/kioo/blob/master/example/om/index.html

10:57 verma: borkdude, it depends on the optimization level you use

10:57 You need those explicit includes for :optimizations :none

10:57 but can avoid those for :whitespace and :advanced

10:58 borkdude: verma ah, thank you

10:59 hhenkel: nullptr: Glenjamin: Thanks a lot, seems to work just fine!

11:00 kerneis: ,(into #clojurescript #clojure)

11:00 clojurebot: #<RuntimeException java.lang.RuntimeException: Unmatched delimiter: )>

11:03 ambrosebs: arrdem: nice work with grimoire.

11:03 verma: inside a clojure macro, is there a way to request a random variable name? I know about hello#, but I need to ask clojure for a random variable the same way hello# does

11:04 ssideris: verma: gensym

11:04 Glenjamin: ,(doc gen-sym)

11:04 clojurebot: excusez-moi

11:04 Glenjamin: ,(doc gensym)

11:04 clojurebot: "([] [prefix-string]); Returns a new symbol with a unique name. If a prefix string is supplied, the name is prefix# where # is some unique number. If prefix is not supplied, the prefix is 'G__'."

11:04 verma: thanks ssideris, Glenjamin :)

11:07 jdkealy: i'm stuck on an issue in om. i built tabs, where onClick they call om/build on the appropriate component. i click one tab, and fine, i go back, and it does not render correctly. I wanted to be sure that the component mounts before I make call to a function in the render state, so I call (om/set-state! owner :mounted true) inside the DidMount call, however even though (did-mount) does get called, IRenderState never renders

11:07 with the state :mounted true...

11:09 verma: jdkealy, some code would be nice

11:09 clojurebot: excusez-moi

11:09 jdkealy: ok making a gist

11:09 bteuber: jdkealy: not so familiar with om, but why do you render from the on-click?

11:09 hhenkel: nullptr: Glenjamin: Do you know if the return values may change when using mapcat with repeat?

11:09 bteuber: when I build tabs without om, I just toggle display:none

11:10 so if I would build them with, I would do the same and render on the outside of that

11:10 I guess

11:10 jdkealy: i'm debating doing just that :)... I just thought it will make unnecessary http calls

11:11 bteuber: true probably better let om take care of which one is visible

11:11 verma: I just try to keep my renders just about rendering and nothing else

11:12 hhenkel: I'm expecting something like "portal1, portal2" but instead I get a lazy seq that looks like this: ( \p \o \r \t \a \l \1\p \o \r \t \a \l \2)

11:12 From within my code I see with trace that I get strings

11:13 cbp: that happens when you concat 2 strings

11:13 just add (apply str ..) to that

11:14 or use clojure.string/join

11:15 hhenkel: cbp: I don't use concat (I would say). I'll give the line of code.

11:15 bteuber: mapcat calls concat

11:16 hhenkel: cbp: (mapcat get-replacements (distinct (re-seq #"\$\{.+?\}" %)) (repeat collection))

11:16 bteuber: hhenkel: (clojure.string/join (map get-replacements ...)) should do the job

11:16 or (apply str (map ...)

11:18 hhenkel: bteuber: okay, I'll try. Thought I tested it and got stuff I was expecting though...

11:20 quangquach: Is there anyway to use update-in to update a value in a map w/o passing an anonymous function? (as I am a Clojure beginner)

11:20 kerneis: this is the main issue with dynamically-typed languages

11:20 quangquach: for example: (update-in {:a 3} [:a] (fn [_] 4))

11:20 cbp: quangquach: assoc-in

11:20 quangquach: ah, just checked that, thanks

11:21 rkneufeld: quangquach: (fn [_] 4) is also equivalent to (constantly 4), but cbp's suggestion is most appropriate

11:22 bteuber: note that (assoc-in m [x y z] 42) == (update-in m [x y] assoc z 42)

11:23 quangquach: they're really helpful, thanks.

11:23 arrdem: which is really (update m x update y update z assoc 42)...

11:24 hhenkel: bteuber: Okay, my mistake I tested it in a short example before I implented it within my code and there I was returning a vector not a plain string...

11:24 quangquach: While trying Clojure, I see many ways to do one task at a time.

11:25 jdkealy: verma: here's my gist https://gist.github.com/jdkealy/217f56e10349642c3996

11:25 you could see the first component mounts the first time, but the second time, it fails the if clause, and the state never updates appropriately

11:29 verma: jdkealy, taking a look

11:30 gfredericks: how do I convince leiningen to not try to sign git tags?

11:31 * gfredericks remembers he can read the leiningen source

11:33 gfredericks: apparently leiningen does not want to be convinced of this

11:34 verma: jdkealy, I don't think you need to explicitly call om/get-state in IRenderState since the state is being passed to you already

11:34 jdkealy: ok, but all the same, the state object doesn't have the :mounted property either

11:34 verma: jdkealy, don't think that'd fix the issue, but just a thought

11:34 gfredericks: time for lein-shell

11:35 wait nevermind

11:37 jdkealy: verma, so om/set-state :mounted true does get called, but iRenderState never picks it up

11:37 cbp: :-o

11:46 angusiguess: Does anyone have a link to something containing the <? macro?

11:48 arrdem: angusiguess: <? isn't a macro, it's a special symbol that the go macro looks for and compiles.

11:48 angusiguess: @arrdem I was under the impression it wasn't in core.async yet.

11:52 jdkealy: so in my gist, if you click "tab 1" twice, it will render appropriately, but one click will render it without that state property even though i can see the call to set-state! is indeed being made

11:52 seangrove: Of course <? is un-googleable. Does it take only non-nil values off of a channel?

11:53 angusiguess: I found this: http://martintrojer.github.io/clojure/2014/03/09/working-with-coreasync-exceptions-in-go-blocks/

11:53 Which describes <?

11:53 gfredericks: seangrove: you can't put nil values onto a channel in the first place

11:54 seangrove: gfredericks: Yeah, thought that immediately after writing that

11:54 angusiguess: It's a pattern for exception handling.

11:54 Frozenlo`: seangrove: sometimes this works http://symbolhound.com/

11:55 seangrove: angusiguess: Got it, thanks. Looks interesting

11:55 angusiguess: seangrove np!

11:55 andyf_: /whois arrdem

11:55 arrdem: some random asshat

11:55 seangrove: ~arrdem

11:55 clojurebot: Titim gan éirí ort.

11:55 andyf_: Ugh. How did my client just send that to the channel

11:56 verma: jdkealy, sorry was away, I am going to try and run this

11:56 seangrove: clojurebot: arrdem is on the edge, and best left alone

11:56 clojurebot: Ack. Ack.

11:56 jdkealy: thanks verma!

11:57 arrdem: hum.. I used to have a couple clojurebot entries... I guess that's part of my hellban. *shrug*

11:58 jeremyheiler: andyf_: think you put a space before teh command

11:58 andyf_: Yeah, probably so.

12:02 Is there a story to who taught the bots Celtic curses, and why?

12:03 gfredericks: clojurebot: why?

12:03 clojurebot: why is the ram gone

12:05 verma: jdkealy, I am seeing what you're seeing I think

12:05 jdkealy: cool!

12:05 so i'm not crazy!

12:06 i mean... i could go the show/hide route, but that would mean me conceding that i have no idea how to control how om re-renders a component, which is sad

12:07 verma: no, I don't think you'd have to do that, may be some re-ordering is in order, what do you intend to do with the :mounter property

12:09 jdkealy: well... there's another call which is inside component one, which requires me to detect the width of component one, without the mounted property it's buggy, sometimes detects the width, sometimes doesn't

12:09 verma: jdkealy, I changed the call to (js/setTimeout #(om/set-state! owner :mounted true) 100)) and it seems to notice it

12:10 jdkealy: hmmmm... that's interesting, but is that really a fix ?

12:10 i mean... i could work with that

12:12 verma: yeah, with a timeout of 0 :) .. but I guess I would try to understand the exact semantics behind this and why state updates in did-mount don't work

12:12 either dig through om or have dnolen_ take a look

12:14 jdkealy: what's the best way to have him look? I see a lot of people putting crap issues on the issues list on github, i don't wanna get flagged as a chump :)

12:14 think this qualifies for github issues ?

12:21 well anyway, the timeout thing appears to work fine, i'll just chalk it up to too many updates at once and some asynchronicity issues

12:23 verma: jdkealy, I don't think I understand what you're trying to do with that prop, so may be once you have it worked out with this hack may be we can take a look at it, issue would be the best way, but do some research before you post it I would guess.

12:29 jdkealy, Om does some stuff here: https://github.com/swannodette/om/blob/master/src/om/core.cljs#L324

12:42 TimMc: ,(.next (.iterator (vec ())))

12:42 clojurebot: #<NullPointerException java.lang.NullPointerException>

12:42 TimMc: I think that's the wrong exception...

12:43 ,(.next (.iterator #{}))

12:43 clojurebot: #<NoSuchElementException java.util.NoSuchElementException>

12:45 andyf_: TimMc: vote for CLJ-1453, assuming it is the same issue

12:47 Full link: http://dev.clojure.org/jira/browse/CLJ-1453

12:49 tbaldridge: anyone here have some experience with test.check?

12:50 I'm trying to write a generator that creates values that are based on previous values generated.

12:50 reiddraper: tbaldridge: me me!

12:50 tbaldridge: hey, I was looking for you ;-)

12:51 got an example of that? I'm generating a list of commands to run against my API. the return values of some commands I need to use as parameters to other generated commands.

12:51 gfredericks: bind

12:51 reiddraper: indeed, bind is your friend there,

12:51 gfredericks: tbaldridge: allow me to plug this for macro I created

12:52 tbaldridge: https://github.com/gfredericks/test.chuck#for

12:52 reiddraper: https://github.com/clojure/test.check/blob/master/doc/intro.md#bind

12:52 i might recommend playing with bind before the macro, but that's just me

12:52 dnolen_: jdkealy: a minimal example w/ no extra context and I will take a look.

12:52 gfredericks: reid and I are competitors in the test.check business

12:55 tbaldridge: I'll think about bind a bit, this could get interesting....

12:55 Frozenlock: Google, stop sending me to clojuredocs for v1.2!!

12:55 arrdem: http://grimoire.arrdem.com/1.6.0/

12:56 yeah not sure what to do about clojuredocs unfortuate pagerank score...

12:56 bbloom: arrdem: needs a more "official" sounding domain & everybody has to link to that, so that google learns it's fucking lesson

12:56 Frozenlock: arrdem: Ah right

12:56 bbloom: its*

12:56 arrdem: bbloom: you saw my clojure@googlegroups post about an "official" domain, right?

12:56 andyf_: And give it more Google juice by whatever means works for that. Link to it somehow?

12:56 * Frozenlock wonders why he gets the hamburger button on his 27inches screen.

12:57 bbloom: arrdem: nope

12:57 reiddraper: tbaldridge: dunno if you'll find this helpful,but the type of bind is: bind :: Generator a -> (a -> Generator b) -> Generator b

12:57 arrdem: Frozenlock: hard coded HTML ftw. the sidebar never unhides itself

12:57 technomancy: Frozenlock: sponsored UI elements (mcdonalds)

12:57 cbp: im lovin it

12:58 Frozenlock: Wasn't there a search field?

12:58 tbaldridge: reiddraper: yeah, I understand how it works, but what I'm doing is a bit more complex. Imagine that "testing clojure collections" thing but while testing multiple types of collections at once.

12:58 cbp: Frozenlock: home page

12:58 arrdem: bbloom: https://groups.google.com/d/msg/clojure/ctNJUvhhkPg/rOpWO5UYrg0J

12:59 Frozenlock: cbp: Ah thansk

12:59 thanks even

12:59 reiddraper: tbaldridge: i'll be shocked if what you want to do can't be done with some combination of fmap and bind

12:59 bbloom: a more important question is how come your hamburger menu has different spacing between the top and bottom lines?

12:59 tbaldridge: reiddraper: right, I think it can be done, I just need to play around with it a bit

12:59 thanks for the help everyone.

12:59 reiddraper: tbaldridge: i've got a call in a couple of minutes, but will be around after and can try and help

13:00 TimMc: reiddraper: I wrote an Iterable tester using simple-check.

13:00 arrdem: bbloom: 5/5 would take github issue for your ocd

13:00 TimMc: Turns out myimpl is correct, but vector's is not. :-P

13:00 andyf_: Hamburger menu?

13:00 arrdem: andyf_: the hamburger button in the top left

13:00 TimMc: andyf_: Thanks!

13:00 cbp: andyf_: 3 horizontal lines make a hamburger

13:01 Frozenlock: andyf_: http://s.mlkshk.com/r/LOQQ

13:01 luxbock: I'm trying to get Weasel to work, but after I start the the CLJS-repl via cemerick.piggieback/cljs-repl and try connecting to ws://localhost:9001 nothing happens

13:01 bbloom: or in this case, an underlined equals sign?

13:01 luxbock: I'm using this: https://github.com/jacksonja/clj-cljs-weasel-template

13:01 TimMc: bbloom: I thought it was struck through!

13:01 luxbock: if I try to access localhost:9001 without the ws:// protocol then I get a message telling me to connect with web-socket

13:02 bbloom: TimMc: i haven't found the source yet, so i'll let you know what i discover, heh

13:02 cbp: luxbock: use the ws:// then?

13:02 jdkealy: Hi dnolen_! I stripped down my example a little bit. https://gist.github.com/jdkealy/f8b6db5829406fc2030d... Interestingly, if I skip "app-view" and set tabs to be the root, the issue does not occur. Basically the issue being that render-state (in component one) does not have the state changes made in DidMount https://gist.github.com/jdkealy/f8b6db5829406fc2030d

13:02 luxbock: cbp: nothing happens when I use that

13:03 jdkealy: (btw, dnolen_, i went to your kitchen table coders event 3 months ago... great stuff!)

13:04 andyf_: TimMc: Please do comment on that ticket, or provide a better patch, if you find any issues with it

13:05 cbp: luxbock: are you using (ws-repl/connect "ws://localhost:9001" :verbose true) ?

13:06 bbloom: TimMc: arrdem: it's magic

13:06 i have no idea where the hamburger is coming from

13:06 apparently i don't know how to use computers

13:06 arrdem: hamburgers |are| magic

13:07 luxbock: cbp: from the cljs-repl? I didn't try that but it doesn't appear to work either

13:07 I was trying to use my browser to connect to the address

13:07 bbloom: holy crap

13:07 it's made out of borders...

13:07 *cringe*

13:07 cbp: luxbock: thats the cljs that creates the js that connects to your repl

13:08 luxbock: as in you compile that and then load that from your browser

13:08 arrdem: bbloom: er... ew. okay. definitely issue worthy then.

13:08 * bbloom creates ocd branch

13:08 bbloom: boom: https://github.com/arrdem/grimoire/pull/47

13:09 css/html/js are all stupid

13:09 cbp: i know right

13:09 luxbock: cbp: yeah I've compiled it, and I've tried opening the index.html file that ships with the template, though now that I'm looking at the console it's telling me that goog is not defined

13:10 so maybe there's something wrong with the cljsbuild-settings of the project, hmm

13:10 cbp: luxbock: you need to do the <script> tags for goog.base.js or whatever

13:10 Frozenlock: http://grimoire.arrdem.com/1.6.0/clojure.core/ I can't search the page if I didn't click to expand. :-(

13:10 arrdem: Frozenlock: yeah known issue

13:11 cbp: I don't know if there's a decent clojurescript tutorial around

13:11 arrdem: Frozenlock: I don't have a good fix for that yet.

13:11 luxbock: yeah it doesn't appear that this project, generated via that clj-cljs-weasel template, has base.js at all

13:11 cbp: I know it was a pain to get it all to work the first time

13:11 arrdem: Frozenlock: pls can have gh issue for that? one doesn't exist yet.

13:11 Frozenlock: sure

13:11 arrdem: thanks

13:11 luxbock: I've had a working Austin repl before but I read somewhere that this is the new thing to use

13:11 Frozenlock: I like to criticize without doing any work :-p

13:12 Btw, why are those hidden away?

13:12 cbp: luxbock: it is a much better experience than austin

13:12 arrdem: well as bbloom is ample proof my real strategy is to commit only the set of errors sufficiently egregious to motivate someone else to fix them for me..

13:12 cbp: it's like fast and doesn't randomly break!

13:13 luxbock: good to hear, then it's worth figuring out why this template is not working :)

13:13 bbloom: arrdem: i only fixed it b/c i was incredulous that i couldn't find the source of the problem within 5 seconds in the inspector

13:13 have i mentioned that css/html/js are stupid?

13:14 took me 11 damn minutes

13:14 cbp: you also don't need a freaking server to use cljs on a local html file

13:14 arrdem: new build is deployed. enjoy bbloom's hamburger everyone.

13:14 Frozenlock: Oooooh

13:15 much nicer

13:15 bbloom: it's glorious

13:15 cbp: i want an actual hamburguer

13:15 Frozenlock: I still have to use the mouse to open the menu.

13:15 * arrdem checks that nothing exploded in the build

13:15 Glenjamin: an actual hamburger would be hilarious

13:15 * Frozenlock has lost a part of his soul

13:15 Glenjamin: Frozenlock: i intend to put a JS-based search on all the pages soon

13:16 probably with a shortcut key to focus it

13:16 cbp: oh?

13:16 arrdem: Glenjamin: if I had a way to map your user-agent string to your IRC handle I would totally support per-user customization

13:16 * cbp was also working on that

13:16 Glenjamin: cbp: i haven't started yet

13:16 beyond raising the issue on github for discussion

13:17 cbp: luxbock: https://github.com/tomjakubowski/weasel#usage That works for me

13:17 Glenjamin: arrdem: JS can set cookies, that's probably good enough

13:17 technomancy: weird that the hamburger isn't considered a click target by hit-a-hint

13:17 no idea what it uses as a heuristic

13:17 Glenjamin: oh wow, it's a label

13:18 Frozenlock: joys of webdev

13:18 arrdem: there's a reason I lurk in the compiler..

13:19 Glenjamin: but yeah, JS powered site search is vaugely on my "i should add that" list

13:19 basically the cheatsheet's search, but on every page

13:19 cbp: oh

13:19 i was gonna do an autocomplete thing where you type clojure.string/join and press enter and switch to the page

13:20 arrdem: one possible "real answer" is to flatten this thing into a single page webapp so that rather than linking to another page, clicking a cheathseet link or entering a fully qualified var replaces the cheatsheet body with the symbol documentation body

13:20 then you only have to have "search" in one place because the whole thing becomes flat

13:20 but idk how that'd play with my existing structure. probably badly.

13:20 Glenjamin: i was gonna do https://twitter.github.io/typeahead.js/ + JSON list of all symbols

13:21 or similar

13:21 arrdem: that'd work.

13:21 dnolen_: jdkealy: sorry by minimal I really mean nothing but Om - maybe core.async if there's a weird interaction happening

13:21 no domina, sablono, etc

13:22 jdkealy: gotcha

13:22 luxbock: cbp: at what point and with what address are you accessing the index.html file that has the goog.require script statements?

13:23 cbp: luxbock: i do lein repl. Type in the (require 'weasel..) and (cemerick.piggiback/..)

13:23 which turns it into a cljs repl

13:23 luxbock: then I make sure my cljs file has those 3 lines (ns my.cljs.core..) and (ws-repl/connect..)

13:24 luxbock: then I compile, make an html file with all the <scripts>, load that file in the browser and thats it

13:28 jdkealy: dnolen_ can i use gdom to set the om/root ?

13:31 luxbock: hmm yeah it appears that this template is a bit mungled up

13:34 puredanger: hey all, just a friendly reminder that the CFP for the Conj is open till Aug 1st http://clojure-conj.org/call-for-proposals

13:34 carry on with your awesomeness

13:34 luxbock: cbp: thank you for your patience

13:35 I got it working

13:40 jdkealy: sorry about that, dnolen_, now just using OM https://gist.github.com/jdkealy/14bc7181039ddef20367

13:48 cbp: luxbock: awesome

14:03 zanes: I’m trying to make a bunch of HTTP requests in parallel, process the results, and do an insertion into a database for each retrieved record. The tool I reached for for this was reducers, but the reducers documentation cautions against using reducers with operations that trigger I/O.

14:10 arrdem: well crud clojure/conj conflicts with SC14..

14:10 ludwig`: zanes: reducers aren't intended for your goal.

14:10 zanes: ludwig`: That’s the sense I’m getting.

14:11 ludwig`: core.async? I saw a thread on the Google Group about this.

14:11 ludwig`: zanes: it depends on whether you have synchronization constraints

14:11 zanes: No synchronization constraints.

14:11 But I’m kind of interested in both answers.

14:12 ludwig`: it depends on what exactly you want to parallelize

14:12 _alejandro: zanes: I've used core.async for similar things, but there's still some trouble around I/O esp if you want to parallelize say thousands of request

14:12 s

14:13 zanes: ludwig`: I mean, all of the operations can be done in parallel. There needn’t be any synchronization at all.

14:13 dnolen_: jdkealy: what am I supposed to be looking for again?

14:14 ludwig`: zanes: are the results of the operation necessary to respond to the request?

14:15 jdkealy: dnolen_: when you click on tab2 and go back to tab1, render-state does not pick up the (om/set-state) call in did-mount

14:15 zanes: ludwig`: Yes. I’m retrieving JSON via HTTP, transforming the JSON a bit and then doing a database insertion.

14:15 ludwig`: zanes: ah ok, I misunderstood you the first time and thought you were working on a request handler

14:16 zanes: I'd just start a bunch of Threads

14:17 or, if you have all the responses, you could run a pmap for the transformations

14:18 amalloy: if these requests are all against the same server, launching thousands of requests against it in parallel could reasonably be characterized as an attack. you want to regulate things more than opening all the threads at once

14:18 ludwig`: amalloy: agree

14:18 amalloy: even if they're different servers, thousands of requests at once will not be so great for your own machine

14:19 dnolen_: jdkealy: did you try implementing IUnmount to see if unmount is invoked?

14:20 jdkealy: no i did not. What would I do with that?

14:22 zanes: amalloy: Yes. I had imagined doing it in batches.

14:22 amalloy: zanes: you probably want a ThreadPoolExecutor

14:23 jdkealy: yes, i see unmount is called when you click on tab2

14:23 trptcolin: bbloom: do you have anything written up anywhere (or know of anyone else writing anything up) about why you don’t like the idea of doing something Rx-like on top of core.async, as you mention in https://github.com/brandonbloom/asyncx ?

14:24 bbloom: trptcolin: you're like the third person to ask me about that in the past week :-P

14:24 trptcolin: lol

14:24 bbloom: the summary of it is that i don't particularly think that linear async streams are that useful. most interesting async use cases involve multiplexing

14:24 trptcolin: i’ve heard dnolen_ say similar stuff but couldn’t find references. just looking for concrete reasons other than “do not want” :)

14:25 bbloom: it makes it too easy to do stuff that isn't worth doing

14:25 i just had an email thread w/ ztellman too, he's working on some new thing

14:25 dnolen_: jdkealy: just covering bases before actually spending time debugging this myself :)

14:26 jdkealy: does tab one get unmounted that's the real question

14:26 jdkealy: yes

14:26 trptcolin: bbloom: what distinguishes multiplexing from something like an Observable of Observables?

14:27 bbloom: trptcolin: as i told ztellman, my experience w/ async stuff falls in to one of 3 buckets: GUI, single-machine services, and big distributed systems

14:27 in the first case, i rather just have a global message pump instead of callbacks and/or pervasive async

14:27 in the second case, i rather just have a few top level queues and some state machines each on a thread

14:27 PigDude: ok is somebody here actually working with core.async

14:27 the lack of tracebacks is crippling

14:27 or even error line numbers

14:27 bbloom: in the last case, i haven't ever felt a need for intraprocess asynchronity and parallelization, etc

14:28 so i'm not the right guy to ask if you're interested in server use cases

14:28 amalloy: PigDude: you could fork core.async and remove the one line that's taking away your backtraces, until clojure/core gets around to fixing it for real

14:28 bbloom: or maybe i am, and the answer is "don't do that"

14:28 PigDude: a.malloy referred me to this as the source of the trouble https://github.com/clojure/core.async/commit/9fcae99576c0735a804bbd4cbec81307e2d34d90#diff-2193dd8597437d6454bb74edd2f15e00L26

14:28 dnolen_: jdkealy: you should also implement the will mount methods

14:28 PigDude: amalloy: it just feels like a joke, isn't this killing people?

14:28 (not literally)

14:28 dnolen_: jdkealy: this is how I would debug this

14:28 PigDude: i mean, is anybody using core.async, or do they just use a version before this was introduced?

14:29 bbloom: trptcolin: about the observable of observables thing

14:29 amalloy: maybe core.async users are all amazingly good programmers who don't write bugs, and therefore never get exceptions

14:29 bbloom: trptcolin: the stream abstraction is kinda insufficient for thinking about scheduling and resource consumption

14:29 PigDude: haha

14:30 bbloom: trptcolin: if you look at the .net rx stuff, you'll see tons of crazy shit about schedulers and things

14:30 ToxicFrog: PigDude: I'm using core.async and I don't recall seeing this issue at all

14:30 What version are you using? I'm on 0.1.301

14:30 bbloom: trptcolin: http://www.introtorx.com/content/v1.0.10621.0/15_SchedulingAndThreading.html

14:31 PigDude: ToxicFrog: any exception in a go block/loop just shows the error message, like #<NullPointerException java.lang.NullPointerException>

14:31 ToxicFrog: Wow, that's incredibly useless

14:31 PigDude: ToxicFrog: i'm on "0.1.303.0-886421-alpha"

14:31 bbloom: trptcolin: maybe i'm just an old crumudgen, but i prefer a few top level loops w/ queues and shared state

14:31 ToxicFrog: PigDude: but I'm also not using go-blocks, I'm using true threads.

14:31 PigDude: ToxicFrog: i've gotten pretty far, considering. async log store working :)

14:31 bbloom: trptcolin: also, talk to ztellman b/c he knows more about this shit than me :-P

14:31 PigDude: i'll try with your version maybe

14:31 ztellman: haha

14:31 PigDude: is that the full version in your dependency?

14:32 ToxicFrog: PigDude: so if there's a problem specific to go-blocks, then I wouldn't be seeing it regardless.

14:32 PigDude: hm ok

14:32 ToxicFrog: PigDude: [org.clojure/core.async "0.1.301.0-deb34a-alpha"]

14:32 ztellman: I agree with bbloom that multiplexing is a fundamental design consideration

14:32 as is the resource management that comes with it

14:33 trptcolin: this is probably because i’m not experienced enough with it, but i guess i’m just not getting what about the Rx model disallows multiplexing & resource management

14:33 ztellman: trptcolin: it doesn't disallow it, it just doesn't help much

14:33 PigDude: hey trptcolin it says on clojars you're the last guy to push core.async, do you know abotut his?

14:34 oh maybe this is just a bad search engine result that led to your fork

14:34 amalloy: PigDude: the official core.async release is not on clojars

14:34 PigDude: where would i find it?

14:34 trptcolin: ok, so on the flip side: what is it about core.async that makes these easy

14:34 amalloy: maven central

14:34 er

14:34 maybe? i forget. they probably put it there

14:34 PigDude: ah, got it

14:34 thanks amalloy

14:34 bbloom: trptcolin: ztellman: one of my favorite microsoftisms is the "pit of success" coined by Rico Mariani

14:35 the idea is that you design stuff that makes you kinda fall in to the right approach

14:35 a good design with respect to this principal is one that makes the path of least resistance the correct one

14:35 i feel that Rx doesn't meet that criteria

14:35 technomancy: I like that metaphor

14:35 bbloom: it makes it easy to do stuff that will be giant resource leaks and complexity bug farms

14:36 technomancy: compelled to correctness by gravity

14:36 bbloom: righto

14:36 Rx makes the wrong things easy

14:36 trptcolin: PigDude: uh weird i don’t remember doing anything to core.async. must have been some bug i had to patch real quick before the new version came out.

14:36 bbloom: and doesn't make the right things simple

14:36 but for that matter, i think core.async almost makes the right things too easy ;-)

14:37 PigDude: probably

14:37 bbloom: that is, people use a lot more core async than they probably should

14:37 PigDude: thanks to amalloy's sleuthing i've got real-life error line numbers tracebacks, by using, released dec 9 2013

14:37 bbloom: a giant graph of channels and goroutines is not much better than a big pile of callbacks

14:37 amalloy: haha, you rolled back to an older snapshot?

14:37 PigDude: haha yea

14:38 bbloom: best part of core.async is that you get 1) an emulation of threads and 2) multiplex-able channels

14:38 ztellman: bbloom: isn't that just because the graph's opaque, though?

14:38 PigDude: amalloy: professional: develop w/ this version, then make sure they pass w/ latest :)

14:38 bbloom: ztellman: that's a big part of it, but not the only part

14:38 that opaque graph also contains local state

14:39 ztellman: ok, granted

14:39 bbloom: and of course http://awelonblue.wordpress.com/2012/10/21/local-state-is-poison/

14:39 ztellman: ha, haven't seen that before

14:39 platz: problem comes when the "pit" is used beyond it's initial context. e.g. ActiveRecord/RoR

14:39 bbloom: and that includes the immutable values used as loop control variables too!

14:39 Glenjamin: i always assumed the idea was to use go-blocks + channels to make erlang style processes

14:39 platz: success can have disadvantages too

14:39 ztellman: Glenjamin: erlang-style processes aren't the easiest thing to reason about

14:39 Glenjamin: you send off a message to a little worker part of your app, and it sends you back some data later

14:40 ztellman: and that's with orders of magnitude more tooling to help you understand them, too

14:40 bbloom: a telling problem w/ actors is how hewett talks about "orgs" like human organizations, set up hierarchically

14:40 but actor orgs have the same problems as human orgs: lack of transparency, redundancy, competition for resources, etc

14:41 Glenjamin: makes sense

14:41 bbloom: that's not to say it's a useless model

14:41 platz: e.g. conway's law

14:41 Glenjamin: an efficient org has a few small teams that don't get in each other's way

14:41 bbloom: sometimes lots of stuff gets done despite large amounts of waste

14:41 Glenjamin: i can see how that metaphor holds

14:41 amalloy: PigDude: well, i recommended instead forking the latest version and making the one change you need. now, if anything important has happened in the last half a year, you don't get those changes

14:41 bbloom: conway's law is so fucking true it's crazy

14:42 hiredman: actors aren't closed under composition either, the lack of symmetry is sad

14:42 bbloom: hiredman: which properties are not closed under which composition operators?

14:42 hiredman: bbloom: I mean, if you build a system out of actors, what you get is not an actor

14:43 bbloom: hiredman: i mean, it *can* be

14:44 ztellman: bbloom: but that's fundamentally a more limited model, rigth?

14:44 right*

14:44 hiredman: bbloom: I think that distiction leads to the tarpit

14:44 bbloom: ztellman: which model is more limited?

14:44 ztellman: an actor model where all systems of actors are an actor

14:44 platz: this is part of the interest in the recent push of SOA (so-called microservices), actually it's more optimizing for the human factors rather than the technical ones

14:44 bbloom: ztellman: i mean, if you buy in to hewitt's crazy idea, everything is actors all the time and actors are the only thing that actually represent all of computation

14:44 PigDude: amalloy: yea, you're right, it's just another thing to do :\

14:44 bbloom: ztellman: but he's crazy

14:45 he's also right, but not in a useful way :-P

14:45 ztellman: ok, it's been a while since I've read the original paper, but there is some concept of ordering, right?

14:45 bbloom: no

14:46 ztellman: even messages from a single actor?

14:46 bbloom: the theoretical model only says that the message will get there in some unbounded finite time, where the probability of delivery follows some asymtotic probability or something like that

14:47 no promise of ordering

14:47 ztellman: oh, huh

14:47 platz: in akka we have 'or a given pair of actors, messages sent from the first to the second will not be received out-of-order'

14:47 bbloom: yeah, i think erlang promises order... (right?)

14:47 ztellman: right, which also holds true in Erlang

14:47 platz: but between any other two, no

14:47 ztellman: so if you have a system of actors 'acting' as a single actor, that guarantee goes out the window

14:47 which is where I figured the composition broke down

14:48 but I guess it depends on what definition of actor you use

14:48 bbloom: the problem is that hewitt needs a student to sit over his shoulder and copy edit for him when he posts on the internet

14:49 somehow he has managed to piss off every single respected poster on lambda the ultimate :-P

14:49 so if you try to read about the actual theoretical model, you just get angry at all the misinformation and confusion

14:49 anyway, the wikipedia is pretty good: https://en.wikipedia.org/wiki/Actor_model

14:49 also, it's totally pointless to talk about, b/c we don't program turing machines, why should we program theoretical actor models?

14:50 turns out promises, such as order, are useful

14:54 reiddraper: tbaldridge: back, you having any luck?

14:56 PigDude: amalloy: done, that stuff is just a pain ... setting up git submodule, install in checkouts ...

14:56 amalloy: PigDude: gross, why would you do any of that? just clone it, change the groupid in project.clj, and deploy to clojars. like trptcolin did

14:57 or maybe in pom.xml; i guess clojure/core stuff often has no project.clj

14:58 PigDude: amalloy: i'd do that if i were working alone

15:07 gfredericks: man clojure sucks at SQL: https://www.refheap.com/88196

15:07 wkelly: haha

15:08 this is where we need some reader macros

15:08 stuartsierra: PigDude: you can always find latest releases of org.clojure projects on http://search.maven.org/

15:08 gfredericks: reader macros that query your database

15:08 wkelly: exactly. what could possibly go wrong?

15:09 gfredericks: clojurebot: what |could| possibly go wrong

15:09 clojurebot: In Ordnung

15:10 MC-Escherichia: amalloy is that a courtesy thing...for example I use lein idefiles to hide clojure from my java colleagues

15:10 arrdem: clearly java.lang.String should be IFn and when applied execute as an SQL query against *connection*.

15:10 MC-Escherichia: and lein 2.4.0 broke it, the original author and technomancy haven't sorted it out yet, so I forked and patched in a different way than the author wants

15:11 so now I tell my colleagues clone my version of lein idefiles, lein install, and then we're good

15:11 gfredericks: arrdem: plz make a jira ticket

15:13 arrdem: gfredericks: naw man lets just hard fork clojure it'll be great

15:13 PigDude: thanks stuartsierra

15:14 amalloy: next april fools day joke: everyone in #clojure opens a new jira ticket asking for java.util.regex.Pattern to be IFn

15:14 stuartsierra: Oh please no.

15:14 trptcolin: put them in https://github.com/clojure/clojure/pulls

15:14 arrdem: stuartsierra: it's on the official todo list :P

15:15 trptcolin: ;)

15:15 stuartsierra: Do you have any idea how hard it is to search JIRA?

15:15 nobodyzzz: IFn all the things!!1

15:15 ivan: a few days ago I was tempted to fork Clojure for literal strings / pretty-printed byte arrays / \xNN in strings

15:16 stuartsierra: You could get pretty-printed byte arrays by overridding print-method, I think.

15:16 amalloy: ivan: that has got to be the second-worst reason for forking clojure i've ever heard of

15:16 PigDude: ivan: pp byte arrays would be nice

15:16 puredanger: stuartsierra: I just committed all of them to memory

15:16 ivan: stuartsierra: yeah, but what would you print them as? (.getBytes "awful string with \u escapes")?

15:17 amalloy: ivan: hex, of course. not strings

15:17 stuartsierra: ivan: I dunno, you're the one who wanted it. :)

15:17 ivan: amalloy: well, that would be spectacularly useless for humans

15:17 working at the REPL

15:17 PigDude: erlang does a good job w/ <<>>

15:17 stuartsierra: ,(seq (byte-array [1 2 3 4]))

15:17 PigDude: (soemtimes)

15:17 clojurebot: (1 2 3 4)

15:18 amalloy: uhhhh. i'm now convinced your idea is even worse, if you wanted to print as anything but hex, or possibly as a sequence of numbers from -128 to 127

15:18 PigDude: and sometimes it just spits numbers at you

15:18 amalloy: attempting to interpret byte[] as a string as the default behavior is awful

15:19 PigDude: it was a big problem w/ large binary data in erlang logs but i think lager fix this

15:19 stuartsierra: ,(apply str (map #(format "%z" %) (.getBytes "hello")))

15:19 clojurebot: #<UnknownFormatConversionException java.util.UnknownFormatConversionException: Conversion = 'z'>

15:19 stuartsierra: (apply str (map irc://chat.freenode.net:6667/#(format "%x" %) (.getBytes "hello")))

15:19 dammit!

15:20 amalloy: stuartsierra: i think that would print poorly for characters needing more than 7 bits

15:20 trptcolin: CLJ-1454: symbols starting with an HTTP protocol should implement IFn

15:21 dammit i ruined that one s/HTTP/some-kind-of/

15:21 oh also that 1454 is a real ticket

15:23 amalloy: oh, interesting. i assumed %x would upcast to integer, but i guess it doesn't. that's what i get for assuming java is c

15:26 stuartsierra: ,(clojure.string/join " " (map #(format "%x" %) (.getBytes "hello\uffff")))

15:26 clojurebot: "68 65 6c 6c 6f ef bf bf"

15:27 stuartsierra: Welcome to UTF-16.

15:27 arrdem: UTF-23 only please

15:28 gfredericks: 23 bits ought to be enough for anyone.

15:29 arrdem: 16 + 5 for tag + 2 for GC amirite?

15:29 * arrdem digs for a PDP-11 manual

15:29 andyf: Perl is pretty interesting with its strings - you can treat then as if they are arrays of Unicode chars, 1 index per Unicode char, but they store them as UTF8 to save memory (I think)

15:29 gfredericks: if your string encoding doesn't contain GC flags you're doing it wrong

15:30 andyf: Must make some of their implementation code interesting

15:34 TimMc: ztellman: Basic iterator testing: https://github.com/timmc/collection-check/compare/iterators?expand=1 -- already found a bug. :-P

15:34 I can't get it to do an informative fail for some reason, though.

15:34 tbaldridge: andyf: there was something I was reading the other day that showed that scanning a UTF-8 string on modern processors is actually very fast

15:35 gfredericks: "look I hit enter and it was done immediately"

15:38 tbaldridge: here we go, strlen utf8 optimization http://www.daemonology.net/blog/2008-06-05-faster-utf8-strlen.html

15:41 arrdem: nice!

15:43 augustl: sorta off topic.. Any graph processing libraries and/or databases around? Only one I know about is neo4j, but I don't need disk durability, in memory processing is enough

15:43 and I don't mind interop ;)

15:43 arrdem: augustl: loom is pretty good.. there are some others

15:43 augustl: arrdem: looking it up, tnx :)

15:44 arrdem: hmm, got a link? I get all sorts of hits on google

15:45 arrdem: https://github.com/aysylu/loom

15:46 it's the "obvious" DG implementation using Clojure maps that you'd build if you just sat down and started hacking. more than fast enough for everything I've thrown it at, some of which was pretty big.

15:46 puredanger: https://www.youtube.com/watch?v=wEEutxTYQQU

15:54 mthvedt: what’s the difference between coll-reduce and internal-reduce

15:55 augustl: arrdem: I need some very specific graph, uhm, "thingies" :)

15:56 such as finding everything that moves the same direction in a group of paths within the next 30 minutes, and what not

15:57 magopian: when doing some web development, if you need a database (say postgres, h2, ...), I see that you can use Korma, but how do you create the schemas? I mean, create the tables and all?

15:58 should you resort to using clojure.java.jdbc as I saw in the luminus example?

15:58 augustl: magopian: for schemas I've used liquibase for a long time, for clojure apps as well

15:58 I don't mind the xml, it's just pointy lisp after all

15:59 arrdem: tnx for the link btw :)

16:00 bbloom: augustl: with a weird attribute/element dichotomy and all sorts of strange rules about text nodes, but yeah, juuuust a pointy lisp :-/

16:00 augustl: difficult to google for graph processing libs, most of the results are about drawing graphs, not querying them :)

16:00 magopian: augustl: ok, i see

16:00 bbloom: such that you may trip and impale yourself

16:01 MC-Escherichia: magopian there's a library called lobos that I used once to write a simple SQL schema

16:02 magopian: MC-Escherichia: thanks, i'll read on that too

16:02 augustl: I should probably just suck it up and use neo4j

16:06 insamniac: Any of you nerds going to DEF CON?

16:07 arrdem: did last year, 5/5 would recommend but not going this year

16:07 kristian-: augustl: http://titanium.clojurewerkz.org

16:07 insamniac: arrdem: Did you stay at the Rio or wherever it was hosted last year?

16:08 arrdem: insamniac: rio or go home

16:08 insamniac: there is no room at the inn

16:08 xk05: aint that just the way? soon as i decide my rdf application wants to be in org i come across serious discussion and code examples for clojure

16:09 puredanger: mthvedt: their protocols are defined https://github.com/clojure/clojure/blob/master/src/clj/clojure/core/protocols.clj#L13 but I believe internal-reduce is not used anymore

16:10 cljbeginner: Hey, I'm having trouble getting the quoting/unquoting of a macro right. I've tried to reduce it to the simplest possible case

16:10 xk05: if Fredric Giasson lurks here, Thanks for the article, very instructive

16:10 cljbeginner: The form would be (test = (person "name") "bob"), where this macro returns a function that takes one argument

16:11 I want person to have the value of this argument

16:11 augustl: kristian-: :D tnx

16:13 cljbeginner: I tried something like this http://pastebin.com/nUK4NeM5 but obviously item gets namespace qualified

16:15 augustl: cljbeginner: so you want to rewrite (test = (person "name") "bob") to (= (person "name") "bob")?

16:16 if you want op and body as separate args, you have to make sure body (which is basically args to op?) is treated as such

16:16 cljbeginner: for example, `(apply ~test ~@body)

16:16 cljbeginner: @augustl: I removed a bunch of other stuff happening there, but i want to rewrite (test = (person "name") "bob") to (fn [person] (= (person "name") "bob"))

16:17 augustl: cljbeginner: so tat means the 2nd argument to test has to be a list, and the first item in that list should be what's passed into the fn?

16:17 cljbeginner: @augustl: so that person is actually the arguments passed to the function, and I could say ((test = (person "name") bob) (hash-map "name" "bob"))

16:17 augustl: this sounds like a job for #(= (% "name") "bob") to me :)

16:18 unless you want to do it for the exercise of writing a macro ofc

16:18 cljbeginner: @augustl: it is a little bit of an exercise, yeah - I want to use the syntax (person "name) to describe the attribute I'm accessing, but person isn't defined yet

16:19 @augustl: I agree that your solution makes sense :) I'm trying to go through an exercise of creating a DSL

16:19 augustl: the problem is the magic value "person" imo

16:19 the macro would either have to be very specific about its args, or hardcode 'person'

16:19 that's why the #() macro uses %

16:20 writing a macro for ((test = (% "name") "bob") {"name" "bob"}) probably makes more sense

16:20 hiredman: tbaldridge: "while giving a wonderful example of using a goto to jump from the middle of one loop into the middle of another:" lol

16:21 tbaldridge: ?

16:21 hiredman: tbaldridge: from the utf8 link

16:21 augustl: cljbeginner: or create a binding with something like (test [person] = (person "name") "bob")

16:21 tbaldridge: lol yeah

16:21 ucb: so apparently you can conj onto a map and get a map back: https://gist.github.com/ulises/ffb0895335ab04af1a1a

16:21 * ucb had no idea

16:21 augustl: cljbeginner: but then you're dangerously close to (#(= (% "name") "bob") {"name" "bob"}) ofc :)

16:22 cljbeginner: @augustl: correct

16:23 Frozenlock: ucb: It acts like 'merge'?

16:23 ucb: Frozenlock: apparently so

16:24 though I suspect there are differences I have not explored yet

16:24 Frozenlock: ucb: Yeah, I was suspecting the same, but I made some tests in my repl and they seem identical.

16:24 Which brings the question 'whyyyyyy?'

16:25 puredanger: conj = "add an element to a collection in whatever way is natural for the collection"

16:25 with maps, an "element" is a key-value pair

16:25 Frozenlock: puredanger: I understand that, but why do we have merge then?

16:26 hiredman: ,(conj {} {:a 1})

16:26 puredanger: merge is map-specific so handles a nil coll better

16:26 clojurebot: {:a 1}

16:27 puredanger: ,(merge nil {:a 1})

16:27 clojurebot: {:a 1}

16:27 puredanger: ,(conj nil {:a 1})

16:27 clojurebot: ({:a 1})

16:28 Frozenlock: Ah nil, always ruining my day.

16:30 puredanger: might be a perf difference too. merge uses reduce which may be faster than the loop/recur in conj. but I would not wager on that without a test.

16:31 augustl: ,(conj {} [:a 1])

16:31 clojurebot: {:a 1}

16:31 augustl: oh hey

16:32 Frozenlock: ,(merge {} [:a 1])

16:32 augustl: convenient in some cases :)

16:32 clojurebot: {:a 1}

16:32 augustl: ah, well there you go

16:35 gfredericks: ,(merge nil [:a 1])

16:35 clojurebot: {:a 1}

16:36 gfredericks: ,(merge [:a 1] nil)

16:36 clojurebot: [:a 1 nil]

16:36 gill_: arrdem: loom has an a* test, that's a cool library. maybe I can use that for AI pathfinding in a game :)

16:47 TimMc: reiddraper: simple-check is sneaky and mean. Thanks!

16:48 reiddraper: TimMc: ha, i might co-opt that tagline!

16:52 bars0: Hi all. I try to make use of lein-exec plugin on windows 7 but I encounter something strange. I have lein-exec plugin entry in my ~/.lein/profiles.clj. When I fire up command prompt and type `lein` I see `exec` entry. But when I change direcotry and repeat lein command, `exec` entry is missing. What is going on?

16:53 TEttinger: where were you running lein before, when you could see it?

16:53 bars0: TEttinger: My HOME directory

16:53 technomancy: bars0: what are you using lein-exec for?

16:54 TEttinger: is there a project.clj there?

16:54 amalloy: TimMc: :.hasNext? are you a monster?

16:54 technomancy: it's mostly-redundant afaik

16:54 bars0: TEttinger: no

16:54 technomancy: actually I wanted just try it :)

16:55 technomancy: bars0: you should be able to just use lein run

16:58 gfredericks: TimMc: it's mean?

16:58 technomancy: does it make fun of you when you make mistakes?

16:58 like that sudo hack where you can get it to call you names if you get the wrong password?

16:58 gfredericks: TimMc: also simple-check is old hat; all the cool kids have moved on to test.check, which has better beer

16:59 technomancy: gfredericks: whatever, test.check is too mainstream

16:59 bob2: or slay killing all your processes if you forget to run it as root

16:59 nullptr: pfft, i used quickcheck before it was cool

17:00 gfredericks: technomancy: it has its own package manager and a super active community and three different syntax highlighting plugins for light-table

17:00 bars0: TEttinger: yes, you were right I double check directory where I wanted run clj file and I found project.clj in there... Sorry, I'm a dummy and I am learning the tooling.

17:01 amalloy: also, TimMc, you should typehint this stuff to avoid reflection. not because of performance, but because of privacy and accessibility. for example, this should throw an IllegalAccessError if you try to test (.iterator (.entrySet (java.util.HashMap. {1 2})))

17:02 TimMc: amalloy: Just following orders^Wexisting code conventions.

17:03 amalloy: TimMc: huh?

17:03 TimMc: re: :.hasNext

17:03 amalloy: what existing convention is that?

17:04 TimMc: Stuff elsewhere in collection-check. :conj! and the like.

17:04 amalloy: there's no :. anywhere. i'd expect :hasNext

17:05 TimMc: *shrug* It's a keyword version of the symbol normally found at the head.

17:05 I think there are way bigger things to complain about in that code. :-P

17:06 amalloy: well, i did! reflection

17:07 TimMc: Yeah, can you expand on that a bit?

17:08 amalloy: TimMc: you can't use reflection to work with non-public classes, even to call their public methods

17:09 TimMc: Ah, OK.

17:09 amalloy: (.iterator (.entrySet (java.util.HashMap. {1 2}))) returns a java.util.HashMap$EntryIterator, which is a private class

17:09 so you have to hint it as ^Iterator in order to call things on it, via its public interface

17:09 TimMc: ,(.next (.iterator (.entrySet (java.util.HashMap. {1 2}))))

17:09 clojurebot: #<Entry 1=2>

17:09 TimMc: ,(.next (identity (.iterator (.entrySet (java.util.HashMap. {1 2})))))

17:09 clojurebot: #<Entry 1=2>

17:09 amalloy: hm

17:10 afaik that shouldn't work. i wonder why it does

17:10 zanes: https://github.com/halgari/clojure-conj-2013-core.async-examples/blob/master/src/clojure_conj_talk/core.clj#L361...L368

17:10 Is doall necessary there?

17:11 hiredman: amalloy: I think it is if the class the method comes from isn't public or something

17:12 zanes: it is complicated, but basically yes, if you want the http-gets to be run in parallel

17:12 zanes: Can you help me understand why?

17:13 hiredman: zanes: for is lazy, so the result is computed as needed, in this case the result happens to kick off some other computations

17:13 if you don't force it all, you end up forcing one at a time

17:13 zanes: I guess I kind of assumed merge had an implicit doall, but that doesn’t make sense.

17:14 tbaldridge: zanes: merge may force it, it may not I don't know, I just found it easier to put the doall in there and not worry about it

17:14 zanes: Cool.

17:15 tbaldridge: zanes: more correctly merge uses alts! and that would most likely force it. But I would hate for this code to break if the definition of merge changes

17:15 zanes: Right on. Better to be explicit!

17:15 hiredman: and technically, I think range produces a chunked seq, and for respects chunking, so you'll 32 at a time instead of one at a time, but it is best to try and pretend that train wreck doesn't exist

17:16 tbaldridge: (inc hiredman)

17:16 lazybot: ⇒ 50

17:16 gfredericks: clojurebot: chunked seqs |are| sunked cheeks

17:16 clojurebot: Ok.

17:19 amalloy: hiredman: right, but java.util.HashMap$EntryIterator is indeed private

17:20 hiredman: amalloy: but the iterator method is declared in some public class/interface no?

17:21 we could be talking about different things

17:21 amalloy: we might be. i'm thinking that what TimMc is doing should be roughly equivalent to http://stackoverflow.com/questions/5184284/illegalaccessexception-on-using-reflection, and not work

17:22 hiredman: something like http://dev.clojure.org/jira/browse/CLJ-1243

17:23 oh, you are talking about reflection in general then, not clojure's reflector

17:23 amalloy: so for example, https://www.refheap.com/6a4cdda1e4b3c5a927bb89d60 doesn't work, and i don't know what clojure's reflector does that seems to get around that

17:23 puredanger: hiredman: stuartsierra loves that ticket

17:24 hiredman: puredanger: like, he has a shrine too it in his locker and the cognocave?

17:24 puredanger: hiredman: exactly

17:25 hiredman: it is an odd one

17:25 amalloy: i guess it has a special case to avoid this issue. it checks to see if you're falling into exactly this case, and then looks around for public interfaces or superclasses it can use instead

17:25 puredanger: but the summary is that Java doesn't even tell you useful stuff in this case because generic bridge methods are blech

17:26 hiredman: :/

17:27 puredanger: generic bridge methods are the bucket under the leaking abstraction of generics

17:28 tbaldridge: generics, the one thing that .NET does so much better.

17:29 bob2: because it doesn't erase?

17:30 tbaldridge: bob2: yeah

17:31 Frozenlock: Is there an official way to take a spot in the :session ring request?

17:31 :my-lib-name ?

17:31 puredanger: Frozenlock: namespaced keyword?

17:31 tbaldridge: Frozenlock: perhaps even consider namespaced keywords

17:31 ,::foo

17:31 clojurebot: :sandbox/foo

17:31 amalloy: Frozenlock: assert your dominance by removing everything else in the :session

17:32 martinklepsch: are there any graph databases that are easy to understand coming from a sql/nosql background that are also great to use from clojure?

17:32 tbaldridge: amalloy: bad idea, instead replace it with randomly generated data

17:32 Frozenlock: puredanger, tbaldridge : Sounds perfect, thanks!

17:32 amalloy: Right? As an alpha male, I should just (assoc :session my-stuff) every time!

17:35 zanes: I don’t suppose there’s a core.async-based interface to java.jdbc?

17:35 tbaldridge: java.jdbc isn't async is it?

17:36 puredanger: no

17:36 except for the kind of weird case of reading blobs and clobs, stuff like that

17:37 nobodyzzz: Should I know "Java stack" well to be a good clojure programmer?

17:38 brehaut: nobodyzzz: initally you dont need to, but in the long term, learning some portions of it will be useful (IO, concurrency lib)

17:38 puredanger: nobodyzzz: it is useful to know certain parts of the standard library (java.lang, java.util, java.io) and to have a general understanding of things like the classpath

17:38 zanes: tbaldridge: I suppose not? I’m trying to understand how exactly :result-set-fm works.

17:39 Jaood: nobodyzzz: to be practical I would say yes, this tutorial has all you need: http://docs.oracle.com/javase/tutorial/index.html

17:41 nobodyzzz: ugh, there are a lot of tutorial =)

17:41 *tutorials

17:41 Jaood: nobodyzzz: you don't need most of it

17:42 arrdem: nobodyzzz: you can write working clojure without knowing Java, but much of Clojure's value comes from being able to interact nicely with Java

17:42 nobodyzzz: so I guess I should get a copy of "The Java Tutorial" and try to force myself read it?

17:42 Jaood: nobodyzzz: read learing the language, the essentials clases and collections part

17:43 hiredman: I doubt it covers the useful bits

17:44 this is a java language variable, this is how you declare it, this is how you set it, this is how you set it again, here is an array, etc etc etc

17:44 technomancy: nobodyzzz: know where to look when you need to; don't start with java material

17:44 puredanger: nobodyzzz: just go do Clojure. If you run into a Java question, come back here. :)

17:44 amalloy: i wonder how well it would work to start out by assuming that java is exactly like python (or c#, or whatever language you happen to already know), and then just filling in the gaps in that "knowledge" as they come up

17:45 then you only end up learning things that matter to you as a clojure programmer

17:45 Jaood: amalloy: java is easy to learn if you know oop and some Cish syntax

17:46 amalloy: okay, but the point is, why would you? you don't need to know anything about java; you need to know about the jvm and the classes included in the jre

17:46 nobodyzzz: yeah java is easy but toooo verbose. imo

17:46 technomancy: amalloy: it's just like you're in a new house and the silverware is in a different drawer

17:46 hiredman: watch as I use generics to remove the need to insert casts everywhere!

17:47 puredanger: technomancy: and you're wearing giant foam hands

17:47 hiredman: gawk in wonder as I capture a (final) variable in an inner class

17:47 technomancy: puredanger: hah, that's if you're writing java; I meant just the jdk IO classes

17:47 amalloy: (inc hiredman)

17:47 lazybot: ⇒ 51

17:48 puredanger: technomancy: ah, yes :) actually now it seems like what I want is split between .io and .nio is fairly arbitrary ways

17:48 I assume .nnio is up next

17:49 technomancy: n2io, n3io, etc

17:49 Jaood: amalloy: sure, he doesn't need how to "write" Java but instead how to read it well

17:49 hiredman: mio

17:49 TimMc: reiddraper: Ever seen generative testing of HTTP APIs?

17:49 puredanger: TimMc: I've done that for testing a clojure lib wrapping an access lib

17:49 reiddraper: TimMc: yep!

17:49 Jaood: nobodyzzz: don't write any java just learn how to read it

17:50 reiddraper: TimMc: not sure it's anything public, but quite a few folks i know have done it

17:50 hiredman: gaze captivated in to your teletype as I iterate over the contents of an array and am unable to iterate past the bounds of the array!

17:50 TimMc: Hmm. Well, if we end up doing it, I'll make sure to try real hard to make it open-sourceable!

17:51 puredanger: Anything public?

17:51 brehaut: amalloy: knowing how java does overload mangling to jvm methods is probably useful for clojure programmers too

17:51 puredanger: TimMc: nope, sorry.

17:52 TimMc: I'm thinking of making our server accept pathod specs as headers so we can mock out backend/gateway calls to other servers fron the front end.

17:52 amalloy: brehaut: sure. obviously you need to know some things. i was just proposing that it would be interesting to start from "java is exactly like [language x]" and refine that understanding gradually as flaws appear, rather than starting from "i know nothing about java" and having to learn everything whether or not it's relevant

17:52 hiredman: try and contain your gasps of disbelief as I continue to use memory without bothering to free it once I am finished with it!

17:52 TimMc: I'd like to be able to write invariants against the entire request + backend responses vs. response.

17:54 technomancy: hiredman: http://wifflegif.com/gifs/4326-the-hunchback-of-notre-dame-gif

17:54 hiredman: technomancy: perfect

17:56 martinklepsch: does "embedded Datomic Datalog" in Datomic free mean it's persistent?

17:57 hiredman: martinklepsch: I think they mean you can use the datalog to reason over in memory values

17:57 martinklepsch: but persistence requires a transactor, which you don't have when "embedded"

17:57 martinklepsch: hiredman, so datomic free is memory only?

17:58 hiredman: martinklepsch: I don't think so

17:58 puredanger: martinklepsch: no, it is not memory only

17:58 hiredman: martinklepsch: I am pretty sure datomic free lets you run a transactor

17:58 martinklepsch: I'm confusing things, sorry

18:00 puredanger: martinklepsch: in all of the Datomic editions, queries run in the "peer" (not the "transactor"). The peer is in *your app*, thus the datalog is "embedded" in your process.

18:01 queries always run in memory of your app

18:01 martinklepsch: basically I have a set of 4 mio records and I'm wondering if Datomic Free would allow me to manage/store that but I find it a bit hard to distinguish the editions

18:02 puredanger: what's a mil record?

18:02 Frozenbot: Is Datomic FOSS yet?

18:02 martinklepsch: puredanger, 4.000.000

18:03 technomancy: too many editions, huh http://www.penny-arcade.com/comic/2007/02/02/

18:03 amalloy: we know that was you, Frozenlock. switching to Frozenbot to ask your question was a clever ploy, but we all saw through it

18:04 Frozenlock: gasp, my evil ploy was discovered

18:04 Jaood: amalloy: how did you know? ;)

18:04 technomancy: not me, I have nick changes off

18:04 hyPiRion: me too.

18:04 amalloy: technomancy: you'd have to turn off your whole brain to not guess who Frozenbot is

18:05 * technomancy hums "Let it go"

18:05 technomancy: sorry what?

18:07 puredanger: martinklepsch: Free uses a lightweight db (H2) colocated in the transactor process. if you are storing serious data, you'll probably instead want to use Datomic Pro Starter (also no cost) which will let you use an external storage like Postgres, DynamoDB, Riak, etc

18:08 martinklepsch: puredanger, what means serious? could it lose data or are you refering to a lot of content

18:08 puredanger: just size

18:10 martinklepsch: puredanger, is that somehow quantifiable? what is the bottleneck

18:10 puredanger: for most uses, Datomic Pro Starter is a better choice than Free. there is a #datomic room btw if that makes more sense :)

18:11 Frozenlock: I'll just leave this here... "The freenode IRC network has some very specific goals and objectives, and it’s intended primarily for developers of free and open source software." :-p

18:11 TimMc: haha

18:12 We've got them now; they'll have to change the license to keep the channel!

18:12 puredanger: martinklepsch: Free uses an embedded lightweight database. With Pro Starter you can use Oracle, Postgres, Riak, etc for storage

18:12 zanes: Am I really barking up the wrong tree here?

18:12 https://gist.github.com/zane/304863e3f9157a4236ca

18:13 Frozenlock: TimMc: That, and Clojars!

18:14 amalloy: zanes: yes

18:14 you can only use <! and >! in the go scope; lambdas are separate functions

18:14 martinklepsch: puredanger, I understood that but I wonder what the consequences of that "lightweight database" are. Datomic Free seems easier to deploy right now (because I just drop it into my clojure app) so I'd like to understand if it might be enough for the stuff I'm doing

18:15 Jaood: martinklepsch: you should consult the docs of the DB storage in question then

18:15 not datomic

18:15 amalloy: it's not really clear what you're trying to do, but core.async with result-set-fn is gonna be hard to get working together

18:16 zanes: amalloy: So, even though it’s the same lexical scope it’s not going to work?

18:16 amalloy: right. go can't look inside lambdas

18:16 it's not all lexical

18:16 zanes: amalloy: I’m trying to feed the results of the query into a channel, and have the result set realized as the channel is consumed from.

18:16 TimMc: ztellman, reiddraper: I think I'm just going to write a general-purpose behavioral equivalence testing lib based on test.check.

18:17 martinklepsch: Jaood, right but what's the storage in the Free edition from that list? http://docs.datomic.com/storage.html

18:19 Jaood: martinklepsch: whatever it is that comes bundle in the jdk, I think is derby

18:20 TimMc: The extra features I need: 1) Massage return values to match (e.g. compare sorted values, not ordered seqs -- or ignore differences based on *which* exception was thrown)

18:20 2) Compare things that don't actually behave the same way (e.g. mutable vs. persistent) by giving corresponding versions of operators.

18:20 reiddraper: TimMc: neat

18:21 martinklepsch: Jaood,I'll take this to #datomic

18:21 amalloy: i don't think there's any way you can make that work, zanes, or at least not any that will make you happy

18:21 Jaood: martinklepsch: I'm not sure but I don't think openjdk has a DB include, you need the one from oracle

18:21 TimMc: 3) Maybe even try to automatically generate lists of operations based on reflection... :-D

18:22 [fin]

18:22 zanes: amalloy: What’s the issue exactly?

18:22 amalloy: The next thing I tried was using core.async.lab/spool as the :result-set-fm.

18:22 I feel like there’s a gap in my understanding.

18:23 martinklepsch: Jaood: I find it somewhat frustrating that it's so hard to figure out what's the storage when using Datomic Free, shouldn't that be very clearly documented somewhere?

18:23 zanes: Is the connection is closed as soon as result-set-fn returns?

18:23 amalloy: zanes: yes, that's the whole idea of result-set-fn

18:23 zanes: Got it.

18:25 amalloy: database clients hate to keep server connections open any longer than necessary. if you *really* want to keep the result-set open indefinitely, there are probably things you could do

18:25 for example, like (fn [rows] (<!! (go (doseq [r rows] (>! c r)))))

18:26 but that is probably super-fragile, like if something goes wrong you leak a database connection forever

18:30 also, as usual i have never written any core.async code so it may just be totally broken

18:34 Jaood: martinklepsch: probably, I guess its obvious for java programmers

18:52 tjd_: is there a more concise way to say: (if (= 1 (count x)) (first x) x) ? [x is always a vector or seq]

18:54 amalloy: tjd_: i hope x is never (range)

18:55 tjd_: amalloy: hah. x is a vector from an upstream api. fully realized seq.

18:55 amalloy: (that is, you should be really careful with counting unknown sequences)

18:56 anyway, there's no particularly nice way to write that. treating one-element vectors the same as non-vectors is kinda tacky, so it's not made super-easy

19:02 scape_: tjd_: maybe this:

19:02 ,(let [x (range 5)] (if (rest x) x (first x)))

19:02 clojurebot: (0 1 2 3 4)

19:02 amalloy: scape_: (rest x) never returns falsey ever. you mean (next x)

19:03 scape_: ,(let [x (range 1)] (if (rest x) x (first x)))

19:03 clojurebot: (0)

19:03 scape_: yes

19:03 true

19:03 :D

19:03 amalloy: you also don't handle empty collections

19:03 scape_: he didn't specify that

19:03 always a realized seq

19:03 amalloy: he compared (count x) with 1. 0 is not 1

19:04 and [] is an empty collection, with count 0

19:05 tjd_: im going to hell for this: (reduce (comp flatten vector) x)

19:06 ,(let [x (range 1)] (reduce (comp flatten vector) x))

19:06 clojurebot: 0

19:06 tjd_: ,(let [x (range 5)] (reduce (comp flatten vector) x))

19:06 clojurebot: (0 1 2 3 4)

19:07 tjd_: but amalloy is right. i talked myself out of doing this in the first place.

19:07 amalloy: tjd_: that's cute, although quite wrong if x contains any collections inside it

19:07 ~flatten

19:07 clojurebot: flatten is rarely the right answer. Suppose you need to use a list as your "base type", for example. Usually you only want to flatten a single level, and in that case you're better off with concat. Or, better still, use mapcat to produce a sequence that's shaped right to begin with.

19:08 amalloy: still, a novel approach i would not have thought of, on account of it being evil

19:09 scape_: lol

19:09 tjd_: some men just want to watch the world burn

19:09 Frozenlock: (flatten the-world)

19:09 scape_: i found concat over flatten to be ideal

19:09 tjd_: i'll take that as a compliment, though.

19:10 amalloy: (reduce (comp (partial apply concat) list) x) probably works as well, without the issue of nested collections

19:10 &(for [x '(() (1) (1 2 3))] (reduce (comp (partial apply concat) list) x))

19:10 lazybot: java.lang.IllegalArgumentException: Don't know how to create ISeq from: java.lang.Long

19:10 amalloy: welp, guess not. whatever

19:11 tjd_: this problem is no longer just a snack, it's a meal

19:12 scape_: tjd_: just curious why do you want the one element itself if it's only length of 1 but seq otherwise?

19:14 tjd_: i'm querying an upstream product attribute database, it returns data like <property> <name>Title</name> <value>Apple iPad</value> </property>, but also multi-valued attributes in a terrible way like <property> <name>Networking Type</name> <value>WiFi</value> <value>Bluetooth</value> </property>

19:14 it doesn't distinguish well between single and multi-valued attributes

19:14 numberten: is there a core function for this? (fn [f g] (fn [x y] (f (g x y) y))) ?

19:14 scape_: oh okay

19:14 tjd_: scape_: ebay internal ickyness :{

19:15 amalloy: tjd_: but the solution to that is to just always work with a seq

19:15 tjd_: amalloy: well, sort of. i want to present this data in a nicer format to an API caller. so i'd like to give them JSON like {"title": "Apple iPad"} not {"title": ["Apple iPad"]}

19:16 of course there is no schema provided for this mess, so i'm stuck guessing what's multi-valued

19:16 scape_: I would try and work with values being in a seq, even if it's just one. if possible some how

19:17 TEttinger: &(for [x '(() (1) (1 2 3))] (reduce (partial apply concat) [x]))

19:17 lazybot: ⇒ (() (1) (1 2 3))

19:17 amalloy: numberten: no

19:17 TEttinger: hm

19:17 tjd_: scape_: if you were an API consumer, would you prefer to consume seqs, like my example above?

19:17 scape_: since I work in clojure, yes :D

19:17 amalloy: i would much rather receive something that's always a seq than something that might be a seq

19:18 if it might be a seq, i have to write the opposite of this stupid (= (count x) 1) function just to deal with it

19:18 Frozenlock: amalloy: But isn't he always only taking the first element?

19:18 tjd_: Frozenlock: only if it's a single-value seq

19:19 Frozenlock: ugh

19:19 tjd_: yeah.

19:19 scape_: hah

19:19 tjd_: and there's the chance that upstream will mess with me and start sending stuff like [["iPad"]]

19:19 in which case i'll quit and go live in a trailer in the woods

19:20 amalloy: tjd_: ebay is providing you with a perfectly nice api, which is just a map of tagged sequences. don't make it gross by guessing at which things are really not sequences

19:20 tjd_: alright, i'll keep to seqs. consistency, i suppose.

19:20 amalloy: not unless you have a dtd or xsd or something promising it'll never have multiple instances of the same tag

19:21 tjd_: nope, no dtd

19:21 back-of-the-napkin dtd

19:48 ztellman: TimMc: I've thought about doing that for a while

19:49 (he replied an eternity later)

19:49 I'm interested to see what you come up with

19:54 twiceaday: would someone explain me if this

19:54 (= __ (filter #(> % 5) '(3 4 5 6 7)))

19:54 answer to this

19:54 '(6 7)

19:55 contains

19:55 ' <- this character just so it isn't executed as function (or code) ?

19:55 amalloy: well, "just", but yes

19:58 doritostains: lein ring uberjar seems to be including ring/ring-devel from the dev profile. When I remove it everything works fine. Otherwise it tries to use ns_tracker, which fails somehow, as it’s not including tools.namespace which is also in the dev profile. Anyone have this problem before?

20:15 twiceaday: amalloy: is there any other reason for that ? '() ?

20:16 scape_: ,(type '())

20:16 clojurebot: clojure.lang.PersistentList$EmptyList

20:16 scape_: ,(type '(1))

20:16 clojurebot: clojure.lang.PersistentList

20:26 ssutch: hello!

20:27 i have a pretty basic clojurescript/om question if anyone could help with that

20:28 Frozenlock: ,anyone

20:28 clojurebot: #<CompilerException java.lang.RuntimeException: Unable to resolve symbol: anyone in this context, compiling:(NO_SOURCE_PATH:0:0)>

20:29 Frozenlock: #anyone

20:29 cmon bots

20:29 ssutch: Just ask your question

20:29 amalloy: ~anyone

20:29 clojurebot: Just a heads up, you're more likely to get some help if you ask the question you really want the answer to, instead of "does anyone ..."

20:30 amalloy: ~ask

20:30 scape_: fancy

20:30 clojurebot: The Ask To Ask protocol wastes more bandwidth than any version of the Ask protocol, so just ask your question.

20:30 amalloy: (depending on your personal taste)

20:30 ssutch: i may have gotten it (investigating cursors)

20:30 brehaut: amalloy: depends if you are in #tcp or not i guess

20:30 ssutch: essentially i have to switch on some binary state in the global map

20:31 and update the UI based on that (ie user logged in or out?)

20:31 amalloy: brehaut: i thought of a tcp counter-joke this morning

20:31 for use when someone tells you one of those terrible tcp jokes

20:31 brehaut: amalloy: i cannot garuntee i will get it, but send it anyway

20:32 amalloy: after the punchline, you stare blankly at them for a moment, and then say "ACK 0"

20:32 scape_: heh

20:32 brehaut: haha great

20:35 amalloy: it's harder to pronounce "FIN ACK", but you can try that too

20:40 eraserhd: If I have evidence that filter-indexed is something I actually use, would I reopen http://dev.clojure.org/jira/browse/CLJ-670 for consideration or start a new ticket?

20:41 joegallo: hope springs eternal

20:41 ssutch: solved my problem by not overthinking it, thanks folks.

20:46 amalloy: eraserhd: i would not expect anything productive to happen from reopening that ticket or from opening another one which is a duplicate of it

20:47 eraserhd: No?

20:49 amalloy: it was turned down 3 1/2 years ago, and everyone has seemed to do fine without it, so it's probably neither exciting to rich nor critical. and clojure 1.6 seems to include a focus on functions that treat only nil as falsey, eg some?, if-some, and so on

20:50 especially given that you can implement it yourself in like two lines, i don't know why it would be in core. plus, there's the problem that rich brought up: filter returns the original input item, not the result of (f x). what is the "original item", when f is called like (f 10 x)? if that returns true, what goes into the sequence? true? x? 10? [10 x]?

20:53 verma: I am trying to reify an interface defined inside a class in Java, com.firebase.client.Transaction.Handler, not sure how to specify that in clojure com.firebase.client.Transaction.Handler says ClassNotFound,

20:54 eraserhd: Hrmm

20:55 It's strange, though. I've never found a safe place to use keep-*, does anyone use them?

20:55 brehaut: ,(apropos 'keep)

20:55 clojurebot: (keep-indexed keep)

20:55 brehaut: amalloy, eraserhd: sounds like a job for keep-indexed?

20:56 [bloody lag]

20:56 amalloy: brehaut: he's claiming that keep-indexed is no good for him and he wants filter-indexed

20:56 brehaut: amalloy: suspicious

20:58 eraserhd: The semantics of keep seem hard for me to deal with. It maps and filters, but won't work with predicates.

20:58 I'm curious why they are there, which is why I was asking whether anyone uses them.

20:59 amalloy: eraserhd: a quick grep suggests i've used keep in three projects

20:59 that's just the ones that i've cloned onto my most recent work desktop, though

20:59 brehaut: ive used keep a bunch althoguh i dont have anything handy to grep

21:00 amalloy: for a more obvious example, it's used in clojurescript, to look up protocol implementations

21:00 eraserhd: I just realized keep is kind of like mapcat for onesies. That helps.

21:00 amalloy: (keep fast-path-protocols (something)), where fast-path-protocols returns the fast path protocols for some object, if any exists, and we're just looking for any such fast-path

21:02 eraserhd: So what would be the idiomatic way to say, take the odd elements of a lazy sequence in a ->>?

21:02 amalloy: (->> xs (take-nth 2))

21:02 and a (rest), depending on what you mean by "odd"

21:03 eraserhd: Wow, did not understand what take-nth did.

21:04 TEttinger: (doc take-nth)

21:04 clojurebot: "([n coll]); Returns a lazy seq of every nth item in coll."

21:04 eraserhd: Yeah, just saw.

21:04 TEttinger: huh, how would you offset it

21:04 (->> (rest xs) (take-nth 2))

21:04 I guess

21:04 scape_: ,(->> (range 6)(partition 2)(map #(second %)))

21:04 clojurebot: (1 3 5)

21:05 Frozenlock: Am I missing something here? Why not just use `odd?'?

21:05 ,(->> (range 10) (filter odd?))

21:05 clojurebot: (1 3 5 7 9)

21:05 TEttinger: (->> (rest (range 10)) (take-nth 2))

21:05 the reason is for any seq

21:06 (->> (rest (map #(char (+ 64 %)) (range 26))) (take-nth 2))

21:06 ##(->> (rest (map #(char (+ 64 %)) (range 26))) (take-nth 2))

21:06 lazybot: ⇒ (\A \C \E \G \I \K \M \O \Q \S \U \W \Y)

21:06 amalloy: Frozenlock: "items in xs whose index is odd", not "items in xs which are odd"

21:06 he didn't ask very clearly; the context was implied from earlier questions

21:06 Frozenlock: Ah, shame on me for not ready the backlog I suppose.

21:07 "So what would be the idiomatic way to say, take the odd elements of a lazy sequence in a ->>?" Seemed like a direct question...

21:07 *reading

21:13 TimMc: ztellman: I've backed off somewhat from the idea of generating actions based on reflection. (I was starting to gibber slightly. Gibbering is a bad sign.)

21:17 verma: A function signature like: (fn [root korks f & args]) will not match (f a b c)?

21:18 amalloy: ~tias

21:18 clojurebot: tias is try it and see

21:18 verma: ,(fn [a & args]) 1)

21:18 clojurebot: #<sandbox$eval25$fn__26 sandbox$eval25$fn__26@1450a6c>

21:18 amalloy: c'mon, clojurebot, i know you have a more fun-sized factoid for that

21:18 verma: ,((fn [a & args]) 1)

21:18 clojurebot: nil

21:18 verma: dafuq, why am I getting an exception here

21:19 ok checking

21:20 my bad :P

23:00 TimMc: andyf: I did find one thing that iterator patch missed. Updating ticket.

23:01 andyf: Excellent!

23:07 doritostains: lein ring uberjar keeps adding ring-devel/reload even through ring-devel only appears in the dev profile. anyone else had this problem?

23:08 amalloy: doritostains: lein ring is a separate task from lein uberjar. it does not run in the uberjar profile

23:09 technomancy: amalloy: I think lein-ring has an uberjar subtask

23:09 amalloy: you could try lein with-profile uberjar ring uberjar, i suppose, although i'm not sure how well that would work

23:09 technomancy: doritostains: I would just get rid of lein-ring though

23:09 amalloy: technomancy: right, but does it run in lein's uberjar context?

23:09 technomancy: it's full of weird little quirks like this that are difficult to debug

23:09 amalloy: it might. old versions wouldn't though.

23:12 amalloy: yeah. i was guessing he has a version that doesn't, since it apparently is in fact including dev

23:13 doritostains: technomancy, amalloy: thanks, I was about to give up on lein-ring so I’ll go ahead and do that

23:13 amalloy: what’s weird is that it’s only including ring-devel, nothing else from dev. If i remove ring-devel from dev everything works fine

Logging service provided by n01se.net