#clojure log - Apr 21 2011

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

0:23 dnolen: is there a way to get a list of all currently loaded classes in Java?

0:27 mec: Is there a difference between equals and equiv?

0:32 gjahad__: (.allClasses (cdt.utils/vm))

0:33 amalloy: gjahad__: nice

0:33 not that i have any real reason to want to use that, but it's cool

0:39 dnolen: gjahad__: when I include the version of cdt into my project, and try run the snippet, (cdt.utils/vim) -> nil

0:42 amalloy: dnolen: vm, not vim?

0:42 dnolen: amalloy: oops yea.

0:48 mec: within a deftype do I have to refer to another method as (.method this args)?

0:50 dnolen: mec: what do you mean by another method?

0:53 mec: (deftype foo [s] ISeq (first [_] s) IPersistentStack (peek [this] (first this)))

0:54 other way around might be a better example

0:54 is the first in peek foo.first or clojure.core/first

1:00 dnolen: mec: it's faster to call .first directly, first will go through RT.

1:00 mec: ok so i do have to specifically do that, thanks

1:06 tomoj: that there is no foo.first, is there?

1:06 s/that//

1:08 dnolen: tomoj: no

1:09 tomoj: (.first this) or (first this) is what he meant.

1:24 mec: This is weird, running this deftype twice throws an error instead of just redefining

1:25 dnolen: mec: what is the error?

1:26 mec: Expecting var, but RegeneratingCounter is mapped to class user.RegeneratingCounter

1:29 Ah never mind, missed some periods

1:35 lenw: hello all

1:36 does anyone have an example of using crane to deploy simply using ssh - any pointers appreciated ?

1:47 dnolen: Logos is a pretty fun way to explore Clojure's interfaces

1:47 https://gist.github.com/933791

1:47 clojurebot: Huh?

1:57 dnolen: ooh especially queries like only Sequential *and* Counted

3:09 hoeck: ~ seen AWizzArd

3:09 clojurebot: AWizzArd was last seen in #clojure, 9652 minutes ago saying: edw: list comprehension is what for does. List comprehension can do mapping and filtering.

3:12 amalloy: haha 9652 minutes

3:12 $seen AWizzArd

3:12 sexpbot: AWizzArd was last seen talking on #clojure 6 days and 16 hours ago.

3:12 * amalloy makes a mental note to add "what he was saying" to sexpbot, but will soon forget to do it

3:46 ejackson: morning

4:39 oh oh.... fliebel is following me

6:35 ilyak: What's the best way to get a readable clojure backtrace?

6:35 ejackson: open question

6:36 i believe 1.3 has good stack traces

6:36 but haven't tried it myself

6:36 ilyak: Sadly, eclipse's clojure repl by default swallows backtraces

6:36 which is sad

6:37 That's the least painful way to develop in clojure?

6:40 ejackson: i'd say emacs

6:40 but its by taste, really

6:51 ilyak: Sadly my brain is not suited to either editing config files or remembering hotkeys

6:51 which rules out both emacs and vim

7:03 cemerick: ilyak: what was the problem with eclipse for you?

7:05 ilyak: cemerick: It's fine but pretty basic

7:05 For example, it doesn't show backtraces when error occurs

7:05 just description and (usually wrong) line no

7:05 Maybe I have ancient eclipse with ancient plugin

7:06 cemerick: ilyak: mayke sure you have the latest 0.2.0 RC installed.

7:06 But yes, the default is to print only the error summary; then hit Ctrl-E if you want to see a full stack trace of *e.

7:07 that is the behaviour of the stock Clojure REPL as well, FWIW

7:08 I think there's an issue open to eventually add a configuration option for that behaviour (so stacks are printed in full automatically), but it's lowish-priority…

7:09 If you care to track these sorts of thing: http://code.google.com/p/counterclockwise/issues/detail?id=187

7:59 fliebel: &(seque (java.util.concurrent.PriorityBlockingQueue.) [1 4 6 2])

7:59 sexpbot: java.lang.ClassCastException: java.util.concurrent.PriorityBlockingQueue cannot be cast to java.lang.Comparable

7:59 fliebel: … why is this giving me crap? locally it returns java.lang.NullPointerException or (1 4 6 2)

8:05 &(doc seque)

8:05 sexpbot: ⟹ "([s] [n-or-q s]); Creates a queued seq on another (presumably lazy) seq s. The queued seq will produce a concrete seq in the background, and can get up to n items ahead of the consumer. n-or-q can be an integer n buffer size, or an instance of java.util.concurrent B... http://gist.github.com/934334

8:07 fliebel: PriorityBlockingQueue implements blockingqueue, so I can't see why this would act weird.

8:12 cemerick: fliebel: the NPE is coming from inside PBQ, which is odd

8:13 fliebel: cemerick: It sure is. Or maybe not...

8:13 If I remember correctly, seque inserts itself at the end, so maybe that trows of the comaring?

8:21 Thinking about it, closing a que that way, does not work, since it does not return in order.

8:21 $source seque)

8:21 sexpbot: Source not found.

8:21 fliebel: $source seque

8:21 sexpbot: seque is http://is.gd/Ggbm1u

8:23 fliebel: "q itself is eos sentinel" So, what does it lok like when you hae a priority que containing [1 4 2 5 q]? q could be anywhere.

8:26 &(.compareTo 1 (java.util.concurrent.PriorityBlockingQueue.))

8:26 sexpbot: java.lang.ClassCastException: java.util.concurrent.PriorityBlockingQueue cannot be cast to java.lang.Integer

8:31 fliebel: So can a PriorityBlockingQueue even contain items of different classes?

8:34 Would this be a bug in seque(because it assumes order), or misuse of my side?

8:37 ejackson: Hi, have you seen my tweet? Really nice what you've done with quicksort.

8:38 ejackson: i didn't see it... lemme me see

8:38 thanks for the compliment - not my code, of course, but its cool

8:40 aaah heap sorts

8:40 fliebel: ejackson: I made this a while back, that does heapsort in a semi-lazy way: http://pepijndevos.nl/sorting-obsession

8:41 I was now trying to use a PriorityBlockingQueue in seque to do the same, but seque is kind of broken when using a non-standard queue.

8:42 I wonder if there are other interesting sorts that can be done lazily.

8:44 ejackson: i would imagine so - but I'm trying to avoid going down rabbit holes these days

8:44 maintaining focus

8:45 fliebel: ejackson: focus on what?

8:46 ejackson: the projects that will keep food on my table

8:46 i'm freelance

8:47 fliebel: hah, dnolen! You make me wonder if Logos can do sorting. (exist [x y z] (== (llist x y z) q) (project [x y] (> x y))

8:48 ejackson: You work with Clojure?

8:48 manutter: what this channel needs is a good Logobot

8:48 :)

8:48 ejackson: fliebel: whenever possible. Right now I have one client i'm doing in clojure, another in python.

8:49 manutter: what is a Logobot

8:49 fliebel: Well, if ##(require 'logos.core) was allowed...

8:49 sexpbot: java.io.FileNotFoundException: Could not locate logos/core__init.class or logos/core.clj on classpath:

8:51 manutter: ejackson: logobot == clojurebot, only for Logos

8:51 ejackson: ok

8:52 fliebel: manutter: That's easy… for sexpnot, add logos to deps, put require logos in some sort of init and run.

8:52 * fliebel needs to learn to type

8:53 fliebel: *fork sexpbot

8:53 TimMc: fliebel: Security might require more changes.

8:54 fliebel: TimMc: Why?

8:54 TimMc: Does Logos have any way of interacting with the filesystem, network, etc.?

8:55 fliebel: Not that I know...

9:02 dmead: hi channel

9:02 is there a clojure api thats callable from java?

9:02 i can't get a macro to compile, so i want to just write the function body in java

9:02 but i'm not sure if the interop goes like that

9:06 Chousuke: dmead: you can use clojure interfaces from Java, yes. It's not really documented, but google should give you some results.

9:07 dmead: though it sounds like making your macro compile is probably the better solution :P

9:07 fliebel: ~xy

9:08 clojurebot: xy is http://mywiki.wooledge.org/XyProblem

9:08 fliebel: I love doing that :P

9:10 dmead: Chousuke, i'm sure what it want to do won't work

9:10 yet works by default in common lisp

9:11 i want to return the second symbol in an unquoted s-expression

9:11 without evaluating the first

9:11 i've tried writting a macro that destrutures a single parameter

9:11 with little success

9:12 so like (defmacro msecond [[x y z] `'~y)

9:12 but depending on what i do with it, i get really unclear exceptions from the RT

9:13 Chousuke: hmh

9:13 (defmacro foo [[x y z]] `(quote ~y))

9:14 that should work

9:14 dmead: is that any different?

9:14 Chousuke: not really, just not missing a ] :)

9:14 dmead: :P

9:15 Chousuke: though honestly that looks like a rather pointless macro. :/ Anyway, what sort of errors are you getting?

9:17 dmead: i'll post

9:17 sec

9:18 Chousuke: remember to put the macro call that causes the errors in too, and the actual macro definition. :)

9:18 dmead: indeed

9:18 i'm sure the call is right

9:18 well

9:18 the call works on the repl

9:18 but not in some other code

9:23 (= (msecond (x <- y) <-)

9:23 err

9:23 (= (msecond (x <- y) `<-)

9:23 that returns true in common lisp

9:23 but false in clojure

9:23 Chousuke: ,`<-

9:23 clojurebot: sandbox/<-

9:24 Chousuke: maybe that's it :)

9:24 dmead: hmm?

9:24 whats it

9:24 Chousuke: ` namespace-qualifies symbols

9:24 ,(= '<- `<-)

9:24 clojurebot: false

9:24 dmead: but that changes the equality test?

9:25 Chousuke: yeah

9:25 dmead: thats awful.

9:25 Chousuke: it's a different name

9:25 dmead: right

9:26 so how would i test for equality to the not quoted <- symbol?

9:26 Chousuke: not quoted?

9:27 dmead: my macro is processing a bunch of play s-expressions

9:27 Chousuke: (= (msecond (x <- y)) '<-) will return true

9:27 note the quote mark is different

9:27 dmead: because ' doesn't namespace qualify?

9:27 yes

9:27 Chousuke: yeah

9:27 ' is just quote

9:27 dmead: is there a way to turn off namespace qualifiers for backquote?

9:27 Chousuke: no

9:28 though you can work around it whenever you need unqualified symbols inside syntax-quote forms

9:28 dmead: hows that?

9:28 Chousuke: ,`~'x like this

9:28 clojurebot: x

9:28 dmead: ah

9:28 right

9:28 like we did above

9:28 oh it's the reverse of what i had

9:29 hmm

9:29 Chousuke: yeah

9:29 * dmead wants to fork clojure just to remove the namespace qualifiers

9:29 dmead: hmm

9:29 Chousuke: why do you need ` in this case?

9:29 just use '

9:29 dmead: i don't, i was just porting some common lisp stuff

9:30 and i wasn't away the namespace qualifier changed the equality test

9:30 Chousuke: yeah, be mindful of the differences :)

9:30 it's not the same name, so it can't be equal

9:30 if foo/-> and bar/-> were equal to -> then they'd have to be equal to each other :/

9:30 and that's just not good

9:30 dmead: right

9:32 choffstein: Is there a clojure function that says whether a variable is "blank." I would consider blank to be an empty string, vector, map, or nil.

9:32 dmead: , (empty? nil)

9:32 clojurebot: true

9:33 Chousuke: seq is also idiomatic in some cases

9:34 empty? is in fact just #(not (seq %)) :P

9:34 dmead: ah

9:35 choffstein: empty is perfect :)

9:35 I find googling for my clojure solutions so hard

9:35 dmead: i sorely with clojure conformed to common lisp

9:35 *wish

9:35 it would be so much easier

9:36 TimMc: dmead: Not conforming is why it is awesome.

9:36 choffstein: Like ... trying to google for information on -?> is impossible

9:36 I don't know how to find it

9:36 TimMc: dmead: I.e., the breaking changes are fundamental.

9:36 choffstein: clojuredocs.org

9:36 dmead: TimMc, i don't really agree

9:36 it's not like it's breaking compatibility with pascal or some other garbage

9:37 choffstein: dear god. how did I not know that existed?!

9:37 dmead: it's lisp. FFS

9:37 choffstein: That is a game changer.

9:37 TimMc: &(map empty? [() nil ""])

9:37 sexpbot: ⟹ (true true true)

9:37 dnolen: dmead: Clojure is influenced by a bunch of things, CL is just one. Clojure's macro system is a sweet spot between Scheme and CL, IMO.

9:37 dmead: don't know scheme really

9:37 TimMc: choffstein: Yeah, just be aware that the autocomplete and the actual search behave differently. Namely, search is broken for hyphens, use spaces instead.

9:38 dnolen: dmead: thus your bias :)

9:38 dmead: maybe

9:38 choffstein: TimMc: Okay, thanks :)

9:38 dmead: ive just beeing porting some CL code

9:38 and getting frustrated :/

9:38 dnolen: dmead: it's learning exercise I ported cl-cont 3 years ago, wasn't that bad.

9:38 sh10151: is anyone familiar with Groovy? For some reason it has traction at my workplace while Clojure does not, really...

9:39 TimMc: sh10151: Tell your co-workers that Clojure has curly braces too! :-P

9:40 dmead: Clojure's seq and coll abstractions over lists, vectors, and maps are fantastic changes that break with CL's model.

9:40 (although I suppose that code using list, cons, first, and rest would be backwards compatible.)

9:40 choffstein: This is totally a strange, probably bastardized clojure question, but it tickles my curiosity: is it possible to have the user enter a function name and call that function by name? Something like (call :function-name [parameter list])?

9:41 dmead: thats really just a different way of saying that clojure isn't all that far abstracted away from the jvm

9:41 chouser: choffstein: sure

9:41 dmead: and that fact is what makes all these things crop up

9:41 i really don't see how breaking with 50 years of lisp practices is a good thing

9:41 TimMc: choffstein: You could look it up in the namespace.

9:42 dmead: when the changes are just syntactic

9:42 CL is nice and uniform, clojure is not

9:42 choffstein: How can I do that?

9:43 dmead: TimMc, so like clojure is weakly typed. but i get all kinds of type errors that wouldn't happen in CL

9:43 chouser: ,(resolve (name :reduce))

9:43 clojurebot: java.lang.ClassCastException: java.lang.String cannot be cast to clojure.lang.Symbol

9:43 manutter: ,(resolve (symbol (name :reduce)))

9:43 clojurebot: #'clojure.core/reduce

9:44 cemerick: dmead: Clojure is strongly and dynamically typed.

9:44 dmead: cemerick, blargh.

9:44 chouser: manutter: right-o

9:44 choffstein: chouser: awesome, thanks!

9:44 chouser: choffstein: so that gets you a var for a keyword, then you can call the var

9:45 cemerick: dmead: just sayin'

9:45 chouser: ,(apply #'reduce [+ [3 4 5]])

9:45 clojurebot: 12

9:45 devn: Clojure is dynamically strongly typed and strongly dynamically typed

9:45 TimMc: choffstein: Also see ns-resolve if you want to restrict it to a namespace.

9:45 choffstein: I love this channel :D

9:45 dmead: devn, stab.

9:45 devn: :d

9:46 cemerick: My kingdom for lazy seqs in Javascript.

9:47 chouser: dmead: Sorry you're frustrated, but this channel being what it is you're more likely to get defences of Clojure behavior than agreement that it should be like CL (after all, we could be using CL even on the JVM if we wanted to)

9:47 cemerick: just got those working yesterday

9:47 * cemerick refuses to fall for the trap ;-)

9:48 TimMc: chouser: Oh neat, I didn't realize you could invoke a var directly. Nice shortcut.

9:49 chouser: cemerick: so far I have lazyseq, cons, seq, first, rest, next, map, filter, concat, and flatten

9:50 that's a bit over 100 short lines of uncompacted js. No other deps.

9:50 cemerick: These are clojurescript refugees?

9:50 chouser: nope, fresh hand-written code. no persistent collections.

9:50 fliebel: ?? "(do @agt nil) ;touch agent just to propagate errors"

9:50 cemerick: chouser: oh, that's a little more interesting then

9:50 chouser: in clojurescript most of these were generated from core.clj and depended on big chunks of a clojure runtime

9:51 fliebel: deref'ing an agent that's got an error will throw that error

9:51 cemerick: Hrm, lazy seqs next to mutable collections. I can imagine bugs could get *really* hairy.

9:52 chouser: cemerick: probably. you certainly have to be careful.

9:52 fliebel: chouser: Great, what about futures and other derefables?

9:52 *chouser

9:52 * fliebel is misreading

9:52 chouser: on the other hand, the clojurescript persistent collections are hand-written js and might not depend on that much else either. Hm...

9:53 fliebel: For those that can "hold errors" I think they behave the same.

9:54 which is what, just futures I think.

9:55 fliebel: okay, thanks

9:56 I'm trying to make a sane implementation for seque

9:56 chouser: heh

9:57 fliebel: chouser: http://dev.clojure.org/jira/browse/CLJ-776

9:57 chouser: oh, interesting.

9:58 fliebel: chouser: Yea, but there is a lot of complexity in seque already I need to understand to actually improve it.

10:05 It seems an agent is used as a future that propagates errors when deref'd.

10:09 chouser: a future can only be run once. seque sends to that agent repeatedly, doesn't it?

10:09 fliebel: well, yes… let me see. Hard to tell what fill returns.

10:10 oh, right, s minus all the proccessed ones.

10:11 but offer does not work anyway for a SynchronousQueue

10:12 So I want to see if I can just use put in a future. I also need to get around using the eos sentinel.

10:13 chouser: because the eos could be re-ordered?

10:13 by the blocking queue?

10:13 fliebel: yea, it is not guaranteed the eos will actually be at the end of a priority queue

10:14 chouser: hm. tricky.

10:14 fliebel: and it also breaks the heap, because it throws a npe deep down there.

10:15 I'm now just writing down facts about seque and BlockingQueue to see what I need to do.

10:18 What are tests fro Clojure written in?

10:18 chouser: Clojure

10:18 fliebel: I mean, framework?

10:20 ah clojure.test

10:21 chouser: :-) sorry

10:22 fliebel: chouser: Do you know if there exist any tests for seque? I could not find any, in places I found logical.

10:22 chouser: fliebel: I don't know, sorry.

10:23 fliebel: np

10:24 They're not here at least: https://github.com/clojure/clojure/blob/master/test/clojure/test_clojure/sequences.clj

10:29 Would it make sense to make Exceptions be falsy? I can't find any case where I want an exception to be truthy.

10:30 so it'd be like "if it's false, nothing or an error…"

10:40 uh-oh, have pods landed yet? Because if I do what I'm doing now, I'm in trouble.

10:42 doing .put inside a dosync is a big screaming unretryable sideffect.

10:49 Isn't there future-error?

11:31 chouser: Done! https://gist.github.com/934781

11:34 bpattison: Does any one know how to :gen-class a Java class whose methods I want to override has a byte array, byte[], as arguments?

11:35 fliebel: bpattison: You might try type-hinting them, but I don't think Clojure has primitive support for arrays.

11:35 bpattison: I've tried byte[], and bytes in the :methods specifier

11:36 #^bytes doesn't work either

11:37 fliebel: bpattison: At least the new syntax dropped the hash

11:40 dnolen_: bpattison: did you try ^"[B" ?

11:40 ,(class (byte-array []))

11:40 clojurebot: [B

11:40 fliebel: dnolen_: As a string?

11:40 dnolen_: fliebel: yup

11:41 fliebel: oh, cool, I thought these where not redable, period.

11:41 bpattison: I'll try that

11:45 "[B" compiled -- I need to test further to see if my overloaded method is actually called

11:52 ejackson: oh dear, I'm busy doing pen and paper maths and just wrote (log X).... this is officially going to far now.

11:53 manutter: lol

11:54 * shachaf remembers when he accidentally wrote ">=" when talking to a mathematician.

11:55 ejackson: yes, the don't like that either

11:58 cemerick: Do enlighten me :-)

12:07 ejackson: cemerick: it is not the wind the moves, nor the flag that moves, but your mind that moves.

12:07 :P

12:16 fliebel: What the difference between "java.lang.RuntimeException: java.lang.RuntimeException: java.lang.Exception:" and "java.lang.RuntimeException: java.lang.Exception:"?

12:17 dnolen: so any tips today on discovering all currently loaded classes in the JVM ?

12:19 technomancy: dnolen: you could steal whatever swank does for tab-completion

12:19 dnolen: technomancy: good idea, will look into that.

12:20 fliebel: Something threw an error, and then I rethrew it, and it got all weird with java.lang.RuntimeException prepended.

12:22 I was testing for Exception, but that failed. (is (thrown? Exception …))

12:25 When I write RuntimeException instead, it works. But what kind of TDD is that? Writing the test to pass the code.

12:26 Anyone know what caused this?

12:27 hiredman: fliebel: depends, I think lazy-seqs wrap exceptions in runtime exceptions

12:28 fliebel: hiredman: Oh, I'll than lazy-seq for that then.

12:30 Okay, there we go, a new seque with tests: https://gist.github.com/934781

12:49 amalloy: $findarg map % [() nil "" [1]] [true true true false] ; TimMc, choffstein

12:49 sexpbot: [clojure.core/empty?]

13:04 ilyak: I've caught StackOverflowError in (drop-while)

13:04 not funny at all! :(

13:04 amalloy: ilyak: you're stacking up a bunch of lazy thunks and then realizing them all at once. let me see if i can find you a thread discussing the problem

13:05 http://groups.google.com/group/clojure/browse_thread/thread/6f5064532546a852

13:16 raek: anyone know if something like this has been done for Standard ML? http://blog.wuwon.id.au/2011/01/persistent-vectors-and-hash-maps-for.html

13:16 fliebel: Another not-funny-at-all problem. I have a clojure.test that checks for an exception, and fails. The exact same code does throw an error on the repl.

13:17 raek: laziness?

13:17 clojurebot: laziness is what will save us all

13:19 ilyak: amalloy: Maybe that, but what can I do about that?

13:19 raek: ,(lazy-seq (throw (Exception. "BOOM!")))

13:19 clojurebot: java.lang.Exception: BOOM!

13:19 raek: ,(do (lazy-seq (throw (Exception. "BOOM!"))) nil)

13:19 clojurebot: nil

13:20 raek: fliebel: maybe you need to run doall on som part of the result

13:20 fliebel: raek: Might be… So what ahppens when I do (is (range 10) (range 10))?

13:21 raek: fliebel: if you do (is (= (range 10) (range 10))), then it will pass

13:22 but without the =, it only checks if the lazy-seq is truthy, which it is

13:22 (and this does not force it)

13:22 fliebel: raek: Okay, the dorun worked. Now I have an actual bug to solve...

13:25 amalloy: ilyak: don't create expressions that look like (drop-while (drop-while (drop-while ...))). it's hard to say how you could accomplish that when i don't know anything about your project

13:31 ilyak: amalloy: I didn't

13:31 I can paste it to some kind of pastebin but it would make everybody cry

13:32 It's highly data-dependent so there's no much point

13:32 The problem with stack overflows - I don't even know where it happened

13:32 Because it didn't show the interesting part of backstrace

13:41 dnolen: huh SpiderMonkey is starting to sound like a much cooler Clojure JS target than V8...

13:41 fliebel: dnolen: how so?

13:42 dnolen: has yield, so it can represent lazy sequences more efficiently, isn't single-threaded, comparable speed now as far I can tell.

13:43 fliebel: dnolen: oh, neat

13:55 What do you do when you need to check if someone is running by checking if his legs hit the ground?

13:57 manutter: wait, what?

14:00 mids: fliebel: might be of minor use: http://stackoverflow.com/questions/4087919/how-can-i-improve-my-paw-detection

14:19 technomancy: clojurebot: Bruce's first law is "If it does not do exactly what you expect with zero hours consideration or experience, it is a bug in Lisp that should be fixed.

14:19 clojurebot: 'Sea, mhuise.

14:20 technomancy: gold mine going on here: http://replay.web.archive.org/20070712062420/http://brucio.blogspot.com/2006/05/concisification.html

14:20 cemerick: clojurebot needs to get a new handle; snarkbot, perhaps

14:22 technomancy: are you saying you fail to recognize that concision is equivalent to powerfulness?

14:23 cemerick: Yeah, I'll say I fail in that department. :-)

14:23 technomancy: inconcievable.

14:24 cemerick: "power" is about as meaningful as "elegance", of course

14:25 technomancy: what about powerfulness, though?

14:25 see, it's a lot like truthiness.

14:25 oklahomabythesea: expressiveness

14:25 amalloy: technomancy: puissance is so much more elegant

14:25 oklahomabythesea: "ess"es are like isms

14:25 bulters: expressivism?

14:25 cemerick: why bother with details when we can simply aggregate things into awesomeness?

14:28 bulters: are there any "nice" introductions into the java library ecosystem?

14:28 Trying to use jgit, but having problems to even get it "installed"

14:32 cemerick: bulters: No such thing, I think. It's far too large for any single "introduction".

14:33 bulters: cemerick: I was afraid of that...

14:33 cemerick: Heh. I figured that would be good news. :-P

14:33 bulters: cemerick: luckily, I still have the "trial-and-error" option

14:34 * amalloy plans to stab the next person who makes any errors of any kind

14:34 amalloy: your plan isn't looking so good now, is it

14:35 bulters: amalloy: depends on what you're stabbing with

14:35 edw: Wit?

14:35 amalloy: i'll use the java library ecosystem

14:35 as my weapon

14:35 you won't even know it's me

14:35 bulters: amalloy: that's not considered stabbing under the geneva convention... it's torture

14:35 amalloy: heh

15:22 ssideris: bulters: any specific questions?

15:28 choffstein: I'm assuming "no" is the answer here, but any idea on how I could create a generic http-interface wrapper or queue wrapper for a library I have developed? So let's say I know my library takes a string and returns a string, ideally I want the ability to simply create a wrapper which will handle construction of the input form and link together the routes to call my library appropriately. It's a pattern I keep running

15:28 across, and it seems like it would be a cool utility -- especially one that links a library to a queue

15:31 dnolen: choffstein: where is difficulty?

15:32 bulters: ssideris: Well, specifically: I would like to know how I include a 'random' java lib (jar) in a lein project

15:32 ssideris: tried adding it as a dependency in a lein project, but it's not in any of the sources

15:33 cemerick: bulters: anything added as a dependency must be in a maven repository somewhere

15:34 bulters: cemerick: so i added org.eclipse.jgit/org.eclipse.jgit "0.10.1" as a dependency, since it's in 'their' repo

15:34 edw: choffstein: Have you checked out Lamina (https://github.com/ztellman/lamina)? It provides a golang channel-like abstraction.

15:34 cemerick: bulters: their?

15:35 bulters: so I just found out how to add a repository to the project definition

15:35 cemerick: You need to add any non-central repository to your project.clj.

15:35 Yeah, there you go.

15:35 bulters: thanks ;-)

15:35 hiredman: I kind of doubt that is the group-id/artifact-id of jgit, but I could be wrong

15:36 huh, I guess it is

15:36 you could just say org.eclipse.jgit

15:36 edw: What is with people who ask a question and then immediately disappear? They're training me never to answer anyone non-regular's questions.

15:36 hiredman: lein assumes they are the same if you leave off the namespace part of the symbol

15:36 bulters: hiredman: http://eclipse.org/jgit/download/

15:37 like i made implicitely clear, I'm a complete and utter newbie :P

15:38 choffstein: dnolen: what do you mean?

15:39 edw: Haven't seen it. I'll check it out.

15:39 edw: sorry, business partner walked in the door.

15:40 Unfortunately, those old face-to-face conversations still take precedent over my irc convos ;) Didn't mean to be rude and disappear there.

15:42 edw: It'a not you, personally; but the straw is accumulating on thia x

15:42 Er, on this camel's back. (Sorry, yogurt spoon malfunction.)

15:43 choffstein: haha. I think Lamina / Aleph may work for me...

15:44 Though, I would like the webform to be constructed automatically for me too in a perfect world :D

15:44 edw: It's pretty cool. I fell in love with everything about Node.js but the fact that it's in JavaScript.

15:46 choffstein: My basic issue is that I have these libraries I build, then I need to give them an interface -- but in my opinion, the interface should be separate from the library. But in the last 3 libraries, the interfaces have all been the same general framework: a web interface with an input page hooked to the background library. After doing it 3 times -- and while it is simple enough to do -- I realized that I could probably

15:46 figure out a way to automatically generate the routes and forms given enough information.

15:48 edw: I'm not following what you're getting at exactly, but it sounds like the sort of problem the duck streams module was designed in response to viz. "I don't care if it' a file or a string or a URL or a whatever."

15:53 choffstein: hold on, i'll whip up a gist

15:58 ...as I'm writing up this gist, i'm realizing it's probably just as fast to write the base moustache / hiccup code :D

16:03 Something insane like this: https://gist.github.com/935346

16:09 edw: choffstein: If I'm interpreting your code correctly, I ran up against similar problems when I was writing my Scheme web app framework. Have you considered creating a macro that combines the function definition and interface binding?

16:09 choffstein: edw: I have. But I am new to clojure, so I tried to write the macro and went hulk mode :)

16:09 But yes, that is exactly what I am talking about!

16:11 In my ideal world, I would have the ability to separate the actual function definition and the interface binding, only because I would like to have the opportunity to create an interface for already existing libraries I can't alter

16:12 edw: I wrote a macro like DEFINE-HANDLER or something that took a route definition regular expression and zero or more EXPRs and wired everything up. And then I exposed procedureal versions so I could bind existing procedures similarly without the need for an extra level of indirection.

16:12 Dude, yeah, what I just said.

16:13 choffstein: yes! THAT!

16:13 Do you still have the scheme code? I'd be interested in porting it to Clojure...

16:14 It would probably give me some great experience writing macros

16:14 edw: I was just off looking for it...

16:14 They're in syntax-rules form. Non-hygenic macros make me shudder.

16:19 choffstein: I don't know what that means :-\

16:21 amalloy: choffstein: scheme has a different kind of macro system, more template-oriented i think, in addition to the CL-style "macro as compile-time defn" kind that clojure has

16:21 choffstein: ah, I see

16:21 edw: choffstein: Here's the source: https://gist.github.com/935383

16:21 choffstein: edw: much appreciated :)

16:23 edw: I recommend reading it bottom-to-top.

16:24 amalloy: edw: is syntax-rules much like haskell's pattern-matching, applied to macros?

16:24 i'm only vaguely familiar with the haskell one, but i know ~nothing about syntax-rules

16:25 edw: amalloy: Not really. Someone's written a LET-MATCH for Scheme that lets you do a lot of the Haskell-y pattern matching stuff.

16:26 But SYNTAX-RULES does employ Haskell-like pattern matching when trying to figure out how it should expand a macro.

16:27 Re-reading that code, it makes me feel nostalgia for that time...

16:27 choffstein: You know, utilizing hiccup, I don't actually think this would be too hard to reproduce...

16:28 edw: I would not recommend reinventing the wheel; I wrote this out of spite, mostly.

16:29 It was originally called "FuRoR" i.e. "Fuck you, Ruby on Rails."

16:29 ieure: Hah.

16:29 edw, You misspelled "Rubby."

16:29 edw: ;)

16:30 And then Paul Graham was talking up Arc, so I wrote a new version showing how unimpressive Arc's framework. (The example's at the bottom of the source file.)

16:31 choffstein: Haha. FuRoR ... priceless

16:32 edw: Never try to give a "Data Modeling for Grown-ups" talk to DHH. He really loves those plural table names. Loves his damn pluralize function.

16:37 Somelauw: people don't like clojure just because it is a lisp

16:37 wahts wrong wth lisp?

16:37 markskilbeck: too many parens

16:38 choffstein: edw: Yeah ... RoR has become a language of its own. It's sort of absurd

16:38 edw: Yeah, but Clojure has brackets and brockets.

16:38 ieure: Somelauw, Nothing, it’s a lizard-brain reaction to that which is different than what is known.

16:38 choffstein: I wrote a couple rails 2 apps, but rails 3 seems like a whole new beast.

16:38 edw: choffstein: At least every other headline on Hacker News isn't a reference to some world-changing RoR-related "DSL."

16:39 choffstein: Somelauw: As someone who just started Clojure and never touched lisp before, I can honestly say it took me all of 1 week to get over the whole parenthesis thing

16:39 Somelauw: At this point, I find well formatted clojure code just as easy to read as C++ or Ruby ... or any other language I have worked with.

16:40 ieure: People do have a guttural reaction to the parens in Lisp.

16:40 But it’s just that, guttural.

16:40 bulters: ieure: Lot's of people start to get that same kind of bowel-reaction to ror-rails...

16:40 choffstein: Somelauw: I think, more likely, people have a hard time with the concept of immutability and using reduce / map. But I think that's why more Ruby programmers are coming to Clojure, because they are used to using functional paradigms on their arrays with the inject and map methods.

16:41 edw: is that a jab at all the clojure posts on HN?

16:41 bulters: hmm, make that ror-ruby

16:42 edw: I'm not saying this as a fanboy, but... Lisp code is more like poetry than most other languages that read like prose. You need to stare at Lisp code and think about what it means, whereas e.g. C code is more straightforward. I used to really turned on by elegant C code (see Practice of Programming) but it the more time I spend in Lisp land, the less magic there is even in beautiful C.

16:44 choffstein: Not a reference to the Clojure posts. I wish they would go away. I like having a competitive advantage over other people. Same with Node.js. Both require people to think differently, and thus cause a lot of peeople to show up on Freenode and ask questions that make you face-palm.

16:44 Somelauw: Okay. Yeah, my teacher told us that there is the turing model and the lambda calculus model (he mentioned lisp and haskell) and he said that functional programming doesn't really fit one's brain.

16:44 choffstein: Like me :D

16:44 Somelauw: And I didn't really like that statement.

16:45 * bulters feels the same as choffstein...

16:45 bulters: if I would get a dime for every facepalm I induced..... *sigh*

16:45 amalloy: Somelauw: you should find out if a shovel fits your teacher's brain, cause that suggestion is kinda bullshit

16:46 Raynes: amalloy: +300.3

16:48 Somelauw: But it might be hard to find a company that allows you to program in clojure, because your fellows would probably complain that it is unreadable.

16:48 choffstein: Is there a resque like library for clojure? It seems like it could be built pretty easily using Aleph...

16:49 edw: Here's a tip: work for a marketing company or ad agency. I'm sort of a lone wolf here, and no one gives a shit what I use as long as I produce insights and help them make money.

16:50 choffstein: Sorry -- resque is a ruby library for pushing tasks to redis that can then be polled by background workers

16:50 bulters: Somelauw: I'm learning Clojure together with a co-worker; hope to do some proof of concepts with him.

16:50 Somelauw: The company is open to any language, as longs as it produces results.

16:51 edw: bulters: What industry?

16:51 Somelauw: It would probably mean you need to work alone as a freelancer or something.

16:52 chouser: There are several companies using Clojure either exclusively or as a significant component

16:52 edw: Somelauw: No, because oftentimes clients want assurances that any monkey can pick up where you left off. Thus thus the popularity of Drupal.

16:53 mreynolds: edw: Nooooo! Don't do it! Actually, it is a ton of fun, and there's neat problems to solve. But your soooouuullllll!

16:53 dnolen_: Somelauw: are you studying CS? Seems like an odd thing for a prof to say.

16:54 edw: mreynolds: I store my soul in a padded box under my feet while I'm at the office.

16:54 mreynolds: edw: hehe

16:54 edw: As an ex-marketing employee twice over, it's not bad, but I'm glad to now be doing it anymore

16:54 bulters: edw: web development, we're a ruby shop; mostly

16:54 Somelauw: Yes. I study CS.

16:55 bulters: edw: but there are a lot of processing tasks that we would like to try in clojure.

16:56 edw: bulters: Cascalog is the shit. I slurp tons of data from Google Analytics and use Cascalog to do ad targeting.

16:56 Somelauw: That prof doesn't teach functional programming. I don't know if he is very good in functional programming himself. Maybe he was just talking about what most people think of FP. Nobody protested, so I think most of the people in the room agreed with him.

16:56 bulters: edw: I was thinking of porting one of our language processing tasks to clojure

16:56 choffstein: bulters: Do background tasks get queued up?

16:57 bulters: choffstein: hell yeah ;-)

16:57 choffstein: and it's a long queue... most of the time

16:57 usually gets depleted after the weekend...

16:57 choffstein: Somelauw: Most people aren't introduced to FP except in school. I didn't know about it until my sophomore year and I had been a self-taught programmer for 7 years before that

16:57 bulters: So it shouldn't be so hard to just get a clojure background worker going, right? What queue system do you use, if you don't mind me asking?

16:58 bulters: Somelauw: I got absolutely NO FP in my BSc. programme; only some prolog

16:58 choffstein: I'm trying to figure out the math behind a redis based queue (resque), but I don't understand how workers know what keys to use...

16:58 bulters: choffstein: everything ruby, so it's all resque now.

16:58 choffstein: Do you understand the backend of it? How in the world do workers know how to pull jobs without the keys?

16:59 Well, CMU just introduced their first FP class recently, right? CMU is arguably one of the best CS programs in the US...

16:59 My FP class at Cornell was actually pretty cool. It was in SML/NJ, but I think they switched to O'Caml a year or two after...

16:59 fliebel: Could anyone look over my shoulder on this one? https://gist.github.com/934781 On line 45 I check if the future is still busy consuming the seq, and if so, wait for a value. The thing is that there seems to be a tiny timeframe where the last item has been consumed but the future has not finished yet. This causes the .take to wait forever.

17:01 bulters: choffstein: drop me a line tomorrow, really have to go to bed now; sorry. But would like to answer your questions on resque if not answered by then.

17:01 choffstein: will do

17:01 bulters: cool.

17:01 choffstein: maybe i'll drop into #ruby *shudder*

17:02 bulters: you intro extreme sports? ;-)

17:02 anyway... g'night everyone.

17:03 choffstein: fliebel: That code is above me. Sorry :(

17:04 hiredman: fliebel: you should use a sentinal (Object.)

17:05 if you take, and the object you took = the sentinal then you are done

17:05 ,(= (Object.) (Object.))

17:05 clojurebot: false

17:05 fliebel: hiredman: that is what clojojure.core is doing. Sentinels don't go well with priority queues.

17:06 hiredman: fliebel: well, then live with your race condition

17:06 fliebel: which is more, 5 or (Object.)?

17:08 hiredman: Hm, well, neither are very acceptable for me. So I'll have to rethink the whole idea.

17:08 hiredman: fliebel: give that 5 is some number of bits sitting in memory, and (Object.) is some number of bits as well, and they don't mean anything until I choose to interpret them, I can say whichever I want is greater

17:08 given

17:08 fliebel: hiredman: well, depending of what you choose, the sentinal might get out of the queue before the last value.

17:09 hiredman: fliebel: then you aren't doing it right

17:09 dnolen_: fliebel: PriorityBlockingQueue takes comparator, how come you can't just pass a comparator that guarantees the sentinel is always last? (I don't know much about this stuff)

17:10 fliebel: dnolen_: I could, but seque allows any BlockingQueue to be passed in, so I want to make it work for any of them.

17:11 It's just that I have to find a way to correctly synchronize the end of the seq with the consumer, without involving the queue.

17:15 anyway, I need sleep. I'll think about it tomorrow.

17:36 choffstein: Anyone know of an available background worker queue library for clojure along the lines of github's resque for ruby?

17:36 I know bandalore is one that uses amazon SQS

17:37 hiredman: there are a lot of queue libraries for clojure

17:45 choffstein: mmm, spine seems like a good one with beanstalk

17:46 seancorfield: Q about promise... is there any way to inspect a promise to find out whether it has been delivered?

17:48 hmm, looks like realized? in 1.3.0 will do that

17:48 nm

17:53 mreynolds: Man, I totally missed the yegge kerflufle. I now also feel strange for not caring about ordering functions in clojure code. As a Java convert, I guess I don't care? I just moved them and kept going. I don't get why people care so intensely.

18:01 nickik: mreynols, i think everybody blow it out of proportion. If you read the hole hackernews debate most people acually argue that "pro rich".

18:02 seancorfield: ,(clojure-version)

18:02 clojurebot: "1.2.0"

18:02 seancorfield: not helpful :)

18:02 ##(clojure-version)

18:02 sexpbot: ⟹ "1.2.0"

18:02 seancorfield: bah...

18:02 mreynolds: nickik: Yeah, I'm just finishing it up now. I don't even get a "pro rich" more just a "WTF dude" vibe towards people complaining about the language and culture.

18:02 seancorfield: so i looked in the 1.3.0 source code and there's realized? at the bottom of core... but it doesn't seem to be in the latest master SNAPSHOT

18:04 dnolen_: hmm so swank-clojure 1.3.0 doesn't work with clojure 1.3.0-alpha6 ?

18:04 seancorfield: I think you might need to build from source.

18:05 technomancy: dnolen_: correct

18:06 dnolen_: technomancy: huh, but I see that it works fine with HEAD

18:06 technomancy: oh cool

18:06 seancorfield: dnolen_: doesn't hudson build the snapshot every time it changes?

18:07 realized? was committed march 18th and the snapshot should be april 19th if i'm reading things right

18:08 dnolen_: technomancy: well, looks like the cyclic dependency checking code is effed.

18:09 technomancy: dnolen_: swank's or clojure's?

18:09 dnolen_: oh, take that back, it's does the right thing.

18:10 clojure's

18:20 false alarm, clojure 1.3.0 master and swank-clojure 1.3.0 work beautifully together.

18:27 technomancy: pleasant news

18:27 Apage43: i feel like i should learn emacs one day

18:29 carllerche: It seems strange to me that there isn't a lazy map that comes w/ clojure (I found a couple libs out there for it). Is it not idiomatic to a lazy map?

18:32 technomancy: carllerche: what's the difference between a lazy map and a memoized function?

18:33 hiredman: carllerche: I would recommend just using a map of keys=>delays

18:33 carllerche: i don't know... I guess I should look at memoized functions :P

18:33 well, i guess I have my answer :)

18:35 currentB: I'm trying to read a file but spaces keep being read as "^@" and causing parse errors. I'm guessing this is an encoding issue but does anyone know a good way to solve it?

18:36 I've been messing with java Charset stuff for awhile but to no avail

18:41 carllerche: technomancy: so, i guess the difference would be you could do (:foo lazy-map) instead of ((:foo lazy-map)) ?

18:41 probably doesn't matter

18:41 amalloy: carllerche: ((:foo lazy-map)) is not what i think he meant

18:42 carllerche: i understood it as putting memoized functions in a map?

18:42 amalloy: carllerche: a memoized function *is* a lazy map

18:43 &(let [lazy-map (memoize println)] (take 3 (repeatedly #(lazy-map 5))))

18:43 sexpbot: ⟹ (5nil nil nil)

18:43 amalloy: it calls (println 5) exactly once, caches the nil, and returns that on later lookups

18:43 technomancy: well, you can't call keys/vals or keywords on it. but it's the same thing otherwise.

18:45 carllerche: It's not a collection though

18:46 technomancy: right, but that has more to do with clojure's built-in memoization than anything else.

18:46 with a smarter cache it could be

18:47 carllerche: i guess my goal is that I want a map (can look up by key and is a collection), but populating it up front is expensive and all the keys are not always accessed

18:47 I'm probably thinking about the problem wrong

18:49 technomancy: not necessarily. it shouldn't be hard to reify a lazy map around a smarter memoization cache like http://kotka.de/blog/2010/03/memoize_done_right.html

18:51 carllerche: i'll read the article

19:15 seancorfield: technomancy: is it a known issue that leiningen doesn't search the sonatype repo by default? (and thus 1.3.0-master-SNAPSHOT pulls an outdated snapshot from build.clojure.org)

19:17 i guess i should phrase that as "is it a deliberate decision or just an artifact of leiningen not having caught up with recent changes in clojure build processes?"

19:18 technomancy: is build.clojure.org retired?

19:21 clojars transparently proxies to build.clojure.org, so it should be removed from the list anyway.

19:21 I really want to move away from including snapshot repos by default in lein

19:22 I've been waiting for 2.0 since with Clojars it will be a breaking change. but if clojure/core is doing the breaking for me with b.c.o then I'll just go ahead and drop it now.

19:23 just gotta slap a big ol' FAQ on that, because people are going to wonder.

19:32 micahmartin: Anyone know why (compile 'clojure.contrib.def) doesn't generate any .class files?

19:33 When I try to run my precompile project, I get: java.io.FileNotFoundException: Could not locate clojure/contrib/def__init.class or clojure/contrib/def.clj on classpath

19:34 seancorfield: technomancy: 'kthx .. i guess it wouldn't have saved me any time or frustration if clojars still let me pull an old snapshot .. but if you disable snapshots by default (and perhaps require people to specify a snapshots repo?) then i could only have gotten a snapshot from the right place

19:34 * seancorfield is still new enough to maven to make rookie mistakes like that :)

19:35 micahmartin: compojure.core uses clojure.contrib.def

19:35 technomancy: seancorfield: well clojars still needs some work to separate out snapshots and releases into their own repos

19:35 right now everything goes into the mosh pit.

19:35 seancorfield: ah, the mosh pit... happy days...

19:36 technomancy: incidentally, if anyone's looking for a good web-centric high-profile getting-started project ...

19:36 seancorfield: must admit, i'm not wild about depending on snapshot for clojure core since this code will go to production "soon" but they keep adding useful stuff :)

19:36 technomancy: ^^^

19:38 huh; most of the goodies I was interested in made it into 1.2.1

19:42 TimMc: amalloy: botsnack!

19:43 amalloy: wzt? *looks around, confused*

19:43 TimMc: $findarg map % ["botsnack" "amalloy"] [8 7]

19:43 sexpbot: [clojure.core/count]

19:44 TimMc: :-)

19:48 devn: so im using a library where the macro lets unbound vars leak in -- what im trying to do is find a way around it by determining what is unbound ahead of time to generate a function that takes named arguments for unbound symbols in the macro's output

19:48 anyone have any suggestions on where to look/start?

19:49 hiredman: is there a good reason to use the library? if it's not any good, why use it?

19:49 devn: planning on fixing it, but am more interested in the idea of making this work

19:50 hiredman: bound as in has a root value, or bound as in binding?

19:50 devn: binding

19:51 hiredman: basically, the answer is, read Var.java

19:52 pjstadig: (bound? #'some-var)

19:53 hiredman: pjstadig: that depends on waht version of clojure you are on

19:53 but it might be in 1.2, which should be everywhere

19:53 pjstadig: works in 1.2 what version are you expecting?

19:54 hiredman: dunno, it wasn't always there and didn't know when it was added

19:54 pjstadig: but bound? returns true when a var has a root binding

19:55 if you want to know if it is a binding binding, then maybe a different story

19:56 (doc binding?)

19:56 clojurebot: Huh?

19:56 pjstadig: hehe uh

19:56 ,(doc binding?)

19:56 clojurebot: No entiendo

19:56 hiredman: ,*clojure-version*

19:56 clojurebot: {:major 1, :minor 2, :incremental 0, :qualifier ""}

19:57 hiredman: ,(doc thread-bound?)

19:57 clojurebot: "([& vars]); Returns true if all of the vars provided as arguments have thread-local bindings. Implies that set!'ing the provided vars will succeed. Returns true if no vars are provided."

19:57 pjstadig: duh right

19:57 ,(doc bound?)

19:57 clojurebot: "([& vars]); Returns true if all of the vars provided as arguments have any bound value, root or thread-local. Implies that deref'ing the provided vars will succeed. Returns true if no vars are provided."

21:52 znutar_: I'm kinda confused as to why (defrecord foo [x]) (foo. 4) works but (apply foo. (4)) doesn't

21:53 I mean other than just it being somehow special because it's a ctor

21:56 dnolen: znutar_: defrecord creates Java classes, ctors are not first class, you need to create your own ctor fn. There's some work being done one figuring out how this will be done automatically for you.

22:03 znutar_: ah, I was assuming they were magically promoted to first classiness. Thanks!

22:04 ieure: We try to keep classiness to a minimum.

22:12 devn: heh

22:12 I've admirably succeeded at that very task for years!

Logging service provided by n01se.net