#clojure log - Sep 03 2013

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

0:00 xeqi: benkay: either (partial < n) or #(< n %)

0:00 benkay: ,(< 0 %) [1 2 3]

0:00 clojurebot: #<CompilerException java.lang.RuntimeException: Unable to resolve symbol: % in this context, compiling:(NO_SOURCE_PATH:0:0)>

0:00 benkay: ,#(< 0 %) [1 2 3]

0:00 clojurebot: #<sandbox$eval57$fn__58 sandbox$eval57$fn__58@1e6a3b9>

0:00 benkay: i'll go play with that xeqi, thanks.

0:01 xeqi: ,(every? #(< n %) [1 2 3])

0:01 clojurebot: #<CompilerException java.lang.RuntimeException: Unable to resolve symbol: n in this context, compiling:(NO_SOURCE_PATH:0:0)>

0:01 benkay: (in private, at the risk of making a bad joke)

0:01 xeqi: ,(map #(< 2 %) [1 2 3])

0:01 clojurebot: (false false true)

0:01 coventry: xeqi: Right, that is what I meant. It's actually a (:require [clojure.tools.trace]) component of ns form which is failing, but (require 'clojure.tools.trace) is working at the repl. I think it's time for bed. Probably be clear in the morning...

0:04 Ph_D: xeql: Lesson learned: typos kill. Finally found two letters switched in my database function. Bleh. Thanks for the help, anyway.

0:05 xeqi: Ph_D: thats unfortunate

0:05 but does that mean it works for you now?

0:10 Ph_D: xeql: Yes! Everything's up and running. I did, however, have to use that strange nested mapping structure. Still unsure as to why.

0:25 bja: Anyone else writing core.async stuff have a function or macro that takes a body/expression and returns a channel that is populated with the result of that body/expression?

0:26 johnmn3: just gotta say, if you use multiple desktops, for whatever reason, and you use chrome on them, the the CIRC extension IRC client is pretty awesome

0:27 I just opened it up in another computer and it has all my same settings.. didn't have to configure anything.

0:27 anyhow... anyone know if any good chat rooms to discuss digital audio theory?

0:30 xeqi: bja: I believe `go` returns a channel with the result of the last expression of the body (if non-nil)

0:30 benkay: johnmn3: been playing with Overtone?

0:30 maacl: dnolen: Is there an obvious reason why I would get a rom ["src/cljs"]... WARNING: cljs.core.logic.macros/*occurs-check* not declared ^:dynamic when using run-nc. I amusing core.logic 0.8.4

0:31 bja: xeqi: but why use easy-mode? also, thanks

0:31 johnmn3: benkay: no, but that might not be a bad idea... What I am trying to do is take an audio file and extract the entropy from it, for use as a source of randomness in encryption.

0:31 so that a user can use the microphone on their device for entropy.

0:32 benkay: uh, pardon me, but wat wat wat wat wat

0:32 Raynes: benkay: http://31.media.tumblr.com/tumblr_lyp98aYfG21r6zvo6o1_400.png

0:33 johnmn3: but there are plenty of patches of non-randomness in an audio stream... so I am trying to think of a good algorithm to take out the non-randomness.

0:33 benkay: Raynes: http://blog.mkasprzyk.net/wp-content/uploads/2012/09/watman.jpg

0:33 johnmn3: perhaps a deflate...

0:34 lol

0:34 Raynes: benkay: We find ourselves in a stalemate, sir.

0:34 benkay: johnmn3: are you a crypto person to begin with?

0:34 Raynes: Until next time!

0:34 benkay: o/ Raynes

0:34 johnmn3: benkay: uh, I understand the basics

0:35 ddellacosta: sorry Ph_D, I got caught up in a meeting. But sounds like you have things worked out, so great!

0:35 benkay: i've always been gently dissuaded from doing crypto stuff by people i really respect

0:35 johnmn3: Not trying to reinvent the wheel here. I just need tons of randomness and the browser's random function ain't gonna cut it.

0:35 benkay: itb crypto? either this project is above my pay grade or above yours ;)

0:36 i kid, i kid

0:36 but bad crypto kills

0:37 you obviously are the only judge of how competent you are to write crypto stuff, but "the basics" does not make me comfortable.

0:38 (no intent to hurt your feelings or cast aspersions on your abilities)

0:38 johnmn3: well, random.org essentially does the same thing... using white noise from radio signals.

0:39 benkay: there's a lot of hand waving in that word "essentially"

0:39 johnmn3: no offense taken... just trying to get an example implementation going first. then I can sort out the why-fors :)

0:39 benkay: just out of curiosity, why not just pull random seeds from random.org?

0:40 johnmn3: because I need non-public random data :)

0:41 callen: johnmn3: you realize microphones aren't good sources of entropy right?

0:41 benkay: i wash my hands of this

0:42 johnmn3: callen: no I did not realize that. Source?

0:42 callen: johnmn3: learn to evaluate entropy sources, then test for yourself. Also account for the noise reduction performed in some cases.

0:43 johnmn3: you should just pull from urandom if you need entropy, you're not going to do better than kernel hackers.

0:43 johnmn3: browsers don't have uniform access to good sources like urandom

0:44 I intend on using this: http://www.fourmilab.ch/random/ to evaluate the randomness

0:45 one obvious approach is to truncate the bytes down to their least significant bits... where most of the noise is.

0:45 there are a few papers on it.. looking for them...

0:50 Ph_D: I've dug around some more in the Friend source code, but I'm wondering what the difference is between putting config params in the opposed to adding them in the 'authenticate' wrapper.

0:51 coventry: johnmn3: There's this whole "don't do crypto in the browser" thing which may interest you. https://news.ycombinator.com/item?id=5787498

0:51 Ph_D: ddellacosta: No problem! Glad it's coming together.

0:52 ddellacosta: Ph_D: what do you mean about putting config params in the "opposed?"

0:52 Ph_D: oh, I think you left out a word there

0:52 callen: ddellacosta: accidentally a word?

0:52 ddellacosta: callen: smartass. ;-)

0:53 Ph_D: ddellacosta: Whoops. It's getting late. :p "in the" should be "as to"

0:53 callen: ddellacosta: I acquired a futon and have a place now. it is a nice futon, found a very nice store in Japantown.

0:53 Ph_D: Or just "as". Ha, I need to call it a night soon.

0:53 ddellacosta: Ph_D: "putting config params as opposed to adding them in the 'authenticate' wrapper?"

0:54 callen: awesome! Is it the type you wanted? Forget what they're called. Something buton

0:54 callen: ddellacosta: shikibuton, ie, the real thing, yes.

0:54 ddellacosta: Ph_D: unfortunately, I still am not sure what you mean--what config params are you talking about?

0:54 callen: ddellacosta: as opposed to the very poor foam filled things that are popular out here.

0:55 Ph_D: ddellacosta: Seriously can't words. I meant to say: "Putting config params in the workflows as opposed to adding them in the 'authenticate' wrapper"

0:55 ddellacosta: callen: ah, gotcha. Yeah, that's one of those Japanese words I just never bother to learn, as they just call them "futons" here…haha

0:55 johnmn3: coventry: yea, I know. This is just a proof of concept.. Eventually, I'd like to make it more secure by moving it to an offline extension, much like cryptocat.. and also smart-phone apps as well. But I think, for someone who is in a pinch, in an internet cafe somewhere, it might be useful to have a pure browser based version, no?

0:55 callen: ddellacosta: the "shiki" part distinguishes the primary cotton-filled mattress part.

0:56 benkay: someone using an internet cafe box has already lost johnmn3

0:56 ddellacosta: Ph_D: huh, didn't know you could put config vars in the authenticate wrappers, unless you are talking about roles

0:56 benkay: they should be booting off of a usb drive at the very least

0:56 and even that's not great

0:56 ddellacosta: Ph_D: but generally I've never done anything other than configure in workflow call when setting up routes.

0:57 johnmn3: benkay: depends on the circumstances

0:57 ddellacosta: callen: gotcha. Yeah, I have a western style bed so I don't think about it much...haha

0:57 Ph_D: ddellacosta: Ah, okay. I'm wondering if authenticate's config is treated as global.

0:57 "global"

1:00 ddellacosta: Ph_D: oh, wait, you're talking about the authenticate call itself, which *is* where you configure stuff as far as I know. Sorry I misunderstood. Generally, you are not going to be editing workflow code itself. Does that answer your question?

1:02 johnmn3: benkay: I wonder if it'd be possible to... hmmm. to keep a javascript script on your thumb drive. When you go to the "zero knowledge" site, that purports to send safe javascript encryption libraries to the browser, it serves the page -- the user can then apply their js script to the page to get a sha256 of the full dump of the page. Then that hash is compared against a known good hash stored on the thumb drive. Is this method feas

1:02 ddellacosta: Ph_D: authenticate just wraps up a ring handler, so it's global in the sense that, if it wraps up your top-level (bottom-level?) handler then everything is filtered through it.

1:04 Ph_D: ddellacosta: No worries! Yes, that's what I needed to know.

1:05 ddellacosta: Ph_D: excellent. :-)

1:05 benkay: johnmn3: why not VMs in the browser?

1:05 johnmn3: benkay: I suppose that's silly... if you have scripts on the thumb drive, you don't need to download scripts from the server... just use the app offline, except for the encrypted data sent over the wire to the server.

1:05 benkay: man i am going to bow out of this conversation again

1:06 if you think that this is a good idea and are willing to take responsibility for the lives that may come to depend on your imperfect crypto, go right ahead

1:06 because humans are dumb and take dependencies on dumb things

1:07 i am clearly not going to convince you of the folly of implementing your own in-the-browser crypto library

1:07 and am going to bow out

1:07 and write code.

1:08 callen: johnmn3: you could end up endangering somebody.

1:08 I don't really know how else to impress that upon you.

1:08 technomancy: operations on large primes in a runtime without integers, huh? what could go wrong?

1:08 benkay: i don't know shit from shinola from sugar but i know not to roll my own crypto

1:09 johnmn3: I'm not rolling crypto

1:09 I'm just using one time pads and I need random data

1:09 callen: "just"

1:09 brehaut: technomancy: you can enforce integers with weird unary operations

1:09 johnmn3: what just? it's a bitxor

1:10 brehaut: technomancy: still a terrible idea

1:10 callen: technomancy: in a runtime without reliable/verified access to urandom.

1:10 brehaut: relying on the good graces of the implementation at that point aren't you? Numbers are defined as IEEE 754 in the spec AFAIK.

1:11 johnmn3: well, I'm not doing any prime number crypto anyway

1:12 brehaut: callen: i understand that while thats 90% the case, theres some weird craziness on the edges

1:12 callen: specifically regarding certain operations

1:13 callen: brehaut: sigh. what a ghetto.

1:13 At least thinking JS is well designed is a good sniff test for programmer competence.

1:13 without that, I'd just have to ask if they thought void*'ing all their "object oriented" code in C was a good idea.

1:13 brehaut: callen: indeed :/

1:14 callen: reminds me, ive never understood why JS has a 'void' operator

1:14 callen: brehaut: safe access to undefined value is the...practical reason.

1:15 brehaut: callen: then why is it a unary operator :P

1:15 (rather than just a constant)

1:16 callen: brehaut: so you can pass in arbitrary expressions.

1:16 brehaut: the original purpose was to enable bookmarklets.

1:16 brehaut: ah bookmarklets

1:16 callen: yeah. real elegant.

1:17 futile: Good morning.

1:17 callen: futile: hi

1:17 futile: callen: What are you up to?

1:18 seabre: Oh JavaScript

1:18 This is my favorite JS engine related bug: http://stackoverflow.com/questions/11833319/ie-error-2147024882/11909547#11909547

1:19 callen: futile: scratching an itch.

1:19 futile: callen: oh cool me too, what's yours?

1:19 callen: seabre: wow.

1:19 futile: wiki

1:19 futile: callen: writing a wiki engine?

1:19 callen: futile: ya

1:19 futile: in Clojure?

1:19 callen: I already have a CMS'ish.

1:19 futile: ya

1:19 futile: callen: open source?

1:20 callen: it will be once I push.

1:20 jack_rabbit: More code should be written in lisp.

1:20 :)

1:20 futile: seabre: wow

1:21 jack_rabbit: ew no

1:21 callen: what's the niche?

1:21 jack_rabbit: futile, eww what? You're on the clojure channel.

1:21 futile: jack_rabbit: oh. I guess I don't think Clojure when I hear "lisp"

1:21 callen: futile: programming language knowledge accumulation and sourcing.

1:21 futile: callen: ooh, *that* wiki

1:21 jack_rabbit: futile, lol. Clojure is absolutely lisp.

1:21 futile: callen: where will you host it?

1:21 callen: and what domain name do you have planned for it?

1:22 jack_rabbit: yes but when people say "lisp" they usually mean another dialect

1:22 jack_rabbit: (even in here)

1:22 benkay: callen: will you share the cms?

1:22 jack_rabbit: I suppose.

1:22 futile, I wish to rectify that error.

1:22 callen: benkay: CMS is already on my github, the wiki is the new part.

1:22 futile: jack_rabbit: and besides the parentheses, I think Clojure has little in common with Scheme and CL

1:22 jack_rabbit: futile, scheme is a lisp.

1:23 callen: jack_rabbit: it's not though.

1:23 futile: jack_rabbit: I stand by what I said.

1:23 benkay: callen: whatchoo github?

1:23 callen: the CMS is very micro though.

1:23 jack_rabbit: callen, it is, though.

1:23 callen: benkay: github.com/bitemyapp

1:23 jack_rabbit: it's an offshoot.

1:23 need full macros to be a lisp.

1:23 shaungilchrist: bah this is uppercase lowercase anarchism all over again

1:23 benkay: callen: o right >.<

1:23 futile: too many definitions of "lisp"

1:23 shaungilchrist: there is lisp and there is LISP

1:23 jack_rabbit: callen, I think that's an arbitrary distinction.

1:23 futile: mah head asplode

1:24 shaungilchrist: oh come on

1:24 jack_rabbit: callen, Also, I think clojure benefits from being considered a lisp.

1:24 callen: jack_rabbit: Clojure is a Lisp. Schemes are not.

1:24 shaungilchrist: hahah what!?

1:24 futile: now you're all just trolling

1:24 jack_rabbit: callen, well I'd argue that, but that's a whole other argument.

1:24 shaungilchrist: ok I have to walk away from this one

1:24 futile: none of these definitions are shared

1:24 :D

1:24 callen: shaungilchrist: I've succeeded.

1:24 TEttinger: no no no

1:24 lisp is a speech impediment

1:25 futile: trololololololololololo.com

1:25 shaungilchrist: it's when all of your word are surrounded by parens

1:25 callen: didn't fogus make a lithp?

1:25 jack_rabbit: shaungilchrist, I think you're simplifying things just a bit.

1:25 futile: I think Clojure shares little in common with any other lisp. I still don't think of it as a lisp.

1:26 jack_rabbit: futile, that's a shame.

1:26 futile: I barely create any macros of my own or use recursion, which are probably the two mainly spouted features of lisps.

1:26 jack_rabbit: futile, because it derives much of it's being from existing lisps.

1:26 brehaut: callen: http://ecma-international.org/ecma-262/5.1/#sec-9.5 prepare to be sad

1:26 futile: jack_rabbit: derivation has little to do with actuation

1:26 TEttinger: yeah, clojure is a different kind of lisp, I would say, but still a lisp. there's that LISP-1 categorization, right?

1:26 brehaut: callen: you cant call ToInt32 directly, so you (n)|0

1:27 benkay: callen: demonico?

1:27 * futile is just making up words now

1:27 callen: brehaut: I know this because it's how that asm.js is implemented.

1:27 futile: TEttinger: true but Ruby is also a LISP-1

1:27 brehaut: callen: right. its using this horrible soup hidden in the spec

1:27 jack_rabbit: futile, Well that's valid, but I'd say it's a poor argument.

1:27 callen: brehaut: the "compiler" output of asm.js is literally nothing but integers because that's how it encodes the machine.

1:28 jack_rabbit: futile, Either way, I wasn't attempting to argue.

1:28 futile: :)

1:28 brehaut: callen: yes

1:28 callen: brehaut: I love that the ToInt32 function doesn't obey intent, that's nice.

1:28 benkay: demonico?

1:28 brehaut: callen: you had higher hopes for its definition than me

1:28 jack_rabbit: futile, I was just trying to express that the things that Clojure and other lisps share are valuable and under-used.

1:28 futile: I've been drinking the same sugar free red bull for about 6 hours now, and finally finished it just before midnight (a few minutes ago).

1:28 jack_rabbit: futile, And I wish more code were written in some lisp dialect.

1:28 futile: So now I have to work on my crazy project all night.

1:29 callen: brehaut: were I weaker man, JS would pierce my zen.

1:29 I a*

1:29 futile: jack_rabbit: well I can't agree

1:29 jack_rabbit: futile, why not?

1:29 callen: benkay: what's demonico?

1:30 benkay: callen: a mistake of a portmanteu

1:30 callen: late night brainfog is setting in: what's the name of your clojure CMS?

1:30 callen: benkay: Neubite

1:30 jack_rabbit: futile, Just curious. Again, not trying to create an argument.

1:31 benkay: callen: thanks.

1:31 callen: benkay: it could be made fully general if one changed the landing page to a flatpage.

1:31 it's very micro and minimal, doesn't do much.

1:31 also the persistence layer is trashed. the wiki is fixing that too.

1:31 trash*

1:31 futile: jack_rabbit: well I don't think Scheme or Common Lisp are very good languages, and I think the lisp features they have don't help but actually cause more harm

1:31 callen: trash in this case means, "MongoDB"

1:31 MongoDB == I don't care about my data.

1:32 futile: callen: gonna use Datomic?

1:32 callen: futile: I abuse the aspects of Lispy-ness that Clojure shares with those languages all the time.

1:32 futile: of course @ Datomic.

1:32 a wiki is historical. Datomic fits like a glove.

1:32 I'm even going to do the diffing as a stored function in Datomic :P

1:32 * futile opens emacs and starts writing a Clojure IDE

1:33 futile: callen: woo, that sounds fun

1:33 jack_rabbit: futile, I see. That's clearly a matter of opinion, and I won't argue that. But as for the actual syntax that Clojure and other lisps share, don't you find value in that?

1:33 benkay: callen: a client is open to reorganizing their stack (in parts and in toto) and i want to put clojure everywhere it makes sense. a cms would be awesome, but they're already happy with what they have so...*shrug*

1:33 futile: jack_rabbit: I like Clojure's syntax but I'm not a fan of CL's or Scheme's.

1:34 jack_rabbit: I think Racket's syntax might be okay, since it's closest to Clojure.

1:34 jack_rabbit: futile, but their syntax is very similar compared to those of many other languages. That's why they are lisps.

1:34 futile: Then again I've not seen or written very much CL so maybe it can emulate Clojure better than I know with custom readers.

1:34 jack_rabbit: futile, CL can do pretty much anything, but that's beside the point.

1:35 callen: benkay: well, I tend to do PRs/projects/ideas in response to materialized interest in things and needs.

1:35 futile: jack_rabbit: the parentheses are only half the battle. Then there's differentiation of sections, and using [] for param-lists and let-forms is super useful.

1:35 callen: benkay: so if you've got an itch, discuss it in here.

1:35 jack_rabbit: futile, you can do that easily in CL, and that's an implementation detail. As far as I'm concerned, the "parentheses" are the important detail.

1:36 futile: jack_rabbit: I rescind all my statements and opinions

1:36 I've just remembered that they're vastly uninformed.

1:36 jack_rabbit: futile, I'm sorry. I'm not trying to invalidate your opinions.

1:36 futile: jack_rabbit: you're not

1:36 opinions are meant to be changed

1:36 especially as you get more information and more experience

1:36 jack_rabbit: Cool!

1:37 futile: but im not saying i agree with you yet

1:37 jack_rabbit: That's fine.

1:37 futile: anyway, going to start parsing clojure now

1:38 jack_rabbit: futile, have fun! I hope you take the time to learn some other lisps someday. They do have value, even if they're out of date.

1:38 futile: ive spent a few weeks trying to learn scheme and a few days reading Practical Common Lisp

1:39 and so far i cant see any benefit they have over Clojure.

1:39 but i found a lot of downsides

1:39 brehaut: fast, native executables

1:39 fast particularly in the sense of start up time

1:39 futile: im not sure that's an upside anymore

1:40 jack_rabbit: futile, I can agree with that, but there's also a lot of good in CL that Clojure doesn't have.

1:40 callen: "good"

1:40 jack_rabbit: callen, I suppose that's an opinion as well.

1:40 futile: brehaut: and im sure in the next 10 years there will be a better solution for that in plain Clojure

1:40 jack_rabbit: CLOS?

1:41 jack_rabbit: futile, I do like CLOS, but Clojure's relation to Java seems like a fine object implementation.

1:41 brehaut: futile: i'm not holding my breath. its been a problem with JVM languages for 15+ years, and clojure does a lot more at startup than most JVM languages

1:41 futile: jack_rabbit: I'd say there's [unnecessary and complex feature] in [other language] that Clojure doesn't have, and that's actually the point

1:42 jack_rabbit: futile, that seems like a generalization to me. And generalizations seem to me to be a bad thing when instead of preventing you from avoiding bad things they prevent you from learning things.

1:42 futile: brehaut: I could see ClojureScript getting a whole lot mature in the next 5 years, a new JS environment that competes with JVM, and a really nice system to tie them altogether seamlessly

1:42 *lot more

1:42 brehaut: (and threading)

1:44 jack_rabbit: futile, I'm certainly not suggesting that CL should be used instead of Clojure, or that one is a better language than another. I'm saying that the things they have in common are valuable, and I wish they were better taught and more used.

1:44 futile: jack_rabbit: I'm mainly thinking of things like Ruby's object system or CLOS or Haskell's super-strict type system or Go's type system

1:44 jack_rabbit: futile, How about CL's error handling system?

1:44 futile: it's probably wonderful

1:44 jack_rabbit: futile, rather its condition system.

1:44 futile, it is. And it's worth learning IMO. Still this is tangential to my initial statement.

1:45 callen: I missed CL conditions until I started using robert.hooke and dire.

1:45 then I just...stopped caring.

1:45 futile: callen: hooke looks like something that if I ever start using it, it would be a sign that I'm already doing terribly terribly wrong

1:46 just like monkey-patching in Ruby

1:46 callen: futile: I reserve my greatest evils for libraries, if that comforts you at all.

1:46 futile: callen: not one bit

1:46 callen: well. die.

1:46 futile: eventually

1:46 TEttinger: oh, and on the VMs for functional languages front: F# now runs on LLVM

1:46 callen: TEttinger: still don't care to use ML-Windows.

1:46 jack_rabbit: I feel I've started a war.

1:47 futile: callen: hooke looks like it would let me do this kind of thing in Clojure: https://github.com/sdegutis/zephyros/blob/master/libs/zephyros.rb#L195-L209

1:47 TEttinger: callen, oh yeah, I prefer Clojure too

1:47 futile: and I hate those lines of code very much

1:47 callen: TEttinger: I mean that I'd rather use OCaml.

1:47 jack_rabbit: callen, lol

1:47 futile: ... granted they've actually saved me a little work over the past few weeks

1:48 TEttinger: but clojure would probably improve a bit on startup performance if it ran on LLVM, though that is a guess since AFAIK no one has tried yet. also it would be easier to call C and C++ libs

1:48 futile: Any alternatives to "ns-tracker"?

1:49 seabre: I could never get F# running in Linux, so I really never checked it out.

1:49 futile: TEttinger: yeah but what would that mean for GC?

1:49 TEttinger: futile, LLVM has a GC, it's optional and controllable

1:49 futile: TEttinger: when something gives me I shouldn't free, how does the GC know not to free it, etc?

1:49 TEttinger: but it would have to know all about the C libs I'm using and their memory rules

1:49 seabre: With mono, which was/is supposedly able to run it.

1:50 futile: TEttinger: or I'd have to specify it my programs

1:50 callen: TEttinger: I would <3 a Clojure LLVM but a non-hosted Clojure would be a little...odd.

1:50 TEttinger: yeah C/++ stuff would probably need to be deallocated. it's a whole issue that java doesn't have

1:50 futile: Also ns-tracker is taking up 100% cpu :(

1:51 TEttinger: seabre, oh yeah. F# used to be really hard to run on linux. mono 2.8 actually couldn't run it

1:51 and they claimed it had better support for F#...

1:52 I'd suggest making a newer better JVM, but if it got successful oracle would just sue whoever tried it into oblivion.

1:54 futile: callen: I would imagine it would have C extensions just like Ruby.

1:55 What the heck? Upgraded 'magit' the other day, and now it spins up another emacs process just to commit.

1:57 benkay: not to digress, but how would i compare all of the elements in vector a to all of the elements of vector b?

1:57 futile: benkay: =

1:57 ,(= [1 2 3] [1 2 3])

1:57 clojurebot: true

1:57 futile: benkay: or, what do you mean by "compare"?

1:57 benkay: nope, that's vector a to vector b ;)

1:58 futile: ,(= [1 2 3] (conj [] 1 2 3))

1:58 clojurebot: true

1:58 futile: benkay: vector comparisons just compare each element

1:59 benkay: i'm searching for permutation comparisons

1:59 TEttinger: ah, there we go. Clojure on LuaJIT (JIT specifically because they have added a bunch of interop features that make it really easy to call C). it's also a very good JIT compiler for a GC'ed dynamically-typed language. probably a lot of work on CLJS would apply too.

1:59 futile: benkay: maybe http://clojuredocs.org/clojure_core/clojure.data/diff

1:59 benkay: (fn [1 2 3] [5 2 9]) either returning a comparison for each ([1 5] [1 2] [1 9])

2:00 or just returning t/f if all comparisons pass or something

2:00 TEttinger: ,(for [a [1 2 3] b [1 1 1]] (= a b))

2:00 clojurebot: (true true true false false ...)

2:00 benkay: ,(doc for)

2:00 clojurebot: "([seq-exprs body-expr]); List comprehension. Takes a vector of one or more binding-form/collection-expr pairs, each followed by zero or more modifiers, and yields a lazy sequence of evaluations of expr. Collections are iterated in a nested fashion, rightmost fastest, and nested coll-exprs can refer to bindings created in prior binding-forms. Supported modifiers are: :let [binding-form expr ...], ...

2:00 benkay: thanks TEttinger

2:01 yeah. perfect.

2:01 thanks again!

2:01 TEttinger: benkay, np

2:01 for is exceedingly useful, there's also doseq for the similar case where you don't want a sequence, and just want to, say, print something for each iteration

2:02 fkey: Is there a built-in function like map, except that it doesn't keep track of results?

2:02 TEttinger: I think that's also doseq

2:02 mihneadb: I find myself using doseq pretty often for "real world" stuff, and it feels like writing imperative code

2:02 :(

2:03 TEttinger: ##(doseq [a (range 1 10)] (println a "!!!"))

2:03 lazybot: ⇒ 1 !!! 2 !!! 3 !!! 4 !!! 5 !!! 6 !!! 7 !!! 8 !!! 9 !!! nil

2:03 fkey: oh, looks like my question got answered before asking haha

2:04 thanks

2:04 TEttinger: np fkey

2:04 this really makes me realize how full-featured clojure's standard lib is

2:04 seabre: You could do something like doseq with loop and recur

2:04 but you're probably better off not.

2:05 mihneadb: of course, since it's already there :)

2:05 I actually did, before finding out about doseq

2:05 but really doseq is for .. in

2:06 TEttinger: I need to get back to hiphip, the author wanted a pull request if I could solve the complicated macro macro thing

2:06 rurumate_: Can I use a clojure library, like math.combinatorics, in clojurescript? I get an error message "ReferenceError: combinatorics is not defined" in the running javascript..

2:07 ddellacosta: benkay, or use clojure.set

2:07 rurumate_: but it compiles?

2:08 TEttinger: rurumate_, that sounds like a dependency thing. it's weird if it's runtime though

2:08 ddellacosta: I guess that's a dumb question. But, more dumb questions: you are including the name space in your code?

2:08 rurumate_: ddellacosta: yes, but I have the code that uses the the combinatorics in a "shared" (.clj) file

2:08 benkay: i gather that let is not a recursion target?

2:08 is that correct?

2:09 rurumate_: nvm I'll make a refheap

2:10 seabre: benkay: As far as I know it shouldn't be, why?

2:10 TEttinger: benkay, fairly certain, yeah

2:10 I think I've used loops with let inside

2:12 benkay: thanks all. i'm asking questions that experimenting at the REPL could answer. time to stop coding and switch to reading :)

2:12 rurumate_: here's the two files: (first the .clj, then the .cljs that refers to it): https://www.refheap.com/18251

2:13 seabre: Does recur even target anything other than loop?

2:14 Raynes: A function definition.

2:14 TEttinger: seabre, yes, I believe function dammit Raynes

2:14 rurumate_: btw this project will play wuerfel bohnanza if it goes well, see http://boardgamegeek.com/image/1210283/wurfel-bohnanza

2:15 TEttinger: rurumate_, excellent, I made a dice roller for Star Wars Edge of The Empire, rather than pay $5 for an android app to roll dice and do less than what my clojure app did

2:15 seabre: Ah. I've only ever used recur with loop.

2:15 rurumate_: ok nice, was it in clojure or clojurescript?

2:16 TEttinger: rurumate_, clojure

2:16 ##(reduce * (repeat 7 6))

2:16 lazybot: ⇒ 279936

2:16 rurumate_: that's because you throw 7 6-sided dies..

2:17 futile: What's a good way to enumerate a UTF8-encoded string 1 char at a time, being able to peek ahead 1 char too?

2:18 TEttinger: map-indexed, futile?

2:18 although that will just use whatever string encoding clojure uses

2:20 rurumate_: so basically I want to call (shared/check-odds :red :red :red :green :green :orange) from the clojurescript and stick the result in the dom tree. But alas it crash!

2:20 TEttinger: rurumate_, if you want to know... the most effective my die roller got for more than like 4 dice was either by just treating a die as a fractional result of the symbol on the face (like the 12-sided die had one Triumph symbol, so it was worth 1 Triumph, but like 6 Advantage, and summing penalty dice and bonus dice gave the approximate average.).

2:21 the least effective was rolling 10,000 dice

2:21 and finding the average

2:21 rurumate_: TEttinger: ok, but I'm thinking of listing all possible combinations for a given rule, and printing then color-coded..

2:22 TEttinger: oh ok

2:22 rurumate_: just because you can, in the browser!

2:22 TEttinger: so you aren't calculating worth, you need a lot of things to print out

2:25 futile: Does (for) use codePointAt or charAt when given a string?

2:26 TEttinger: futile, it should just give you chars. hang on let me find some contrived example

2:26 futile: ,(for [a "hello™ n o"] a)

2:26 clojurebot: (\h \e \l \l \o ...)

2:27 futile: ,(for [a "™test"] a)

2:27 clojurebot: (\? \t \e \s \t)

2:29 TEttinger: ##(for [c "Molla ዶ/ር™tኣበ"] c)

2:29 lazybot: ⇒ (\M \o \l \l \a \space \ዶ \/ \ር \™ \t \ኣ \በ)

2:29 TEttinger: yeah, it doesn't seen to preserve the weird change codepage characters

2:30 ##(for [c "Molla ዶ/ር™tኣ הֲקוֹדֶበ"] c) ; let's try with RTL...

2:30 lazybot: ⇒ (\M \o \l \l \a \space \ዶ \/ \ር \™ \t \ኣ \space \ה \ֲ \ק \ו \ֹ \ד \ֶ \በ)

2:30 TEttinger: combining diacritics are their own characters

2:41 rurumate: ok, so when I do try to import math.combinatorics directly in the clsj, I get a compile time error that goog.require can't find that. Where can I see which libs are available cljs?

2:42 I mean is there something analogous to clojars, for clojurescript?

2:44 ddellacosta: rurumate: it is clojars. Is the lib in your project.clj? As a test, I just added it and put the namespace in a cljs file in my project, and it compiled fine

2:44 rurumate: let me actually try to run some code

2:45 rurumate: oh, no, you're right--get a runtime error.

2:45 rurumate: ddellacosta: the project.clj has this line in dependencies: [org.clojure/math.combinatorics "0.0.4"]

2:45 ddellacosta: rurumate: possible that it's not compatible w/clojurescript. let me take a look

2:47 rurumate: nothing in the source suggests it should be cljs specific, but there is no cljs version. As a test, you could try simply putting the file () in your directory, changing it to .cljs and seeing if that does it for you

2:48 doh, meant to link to: https://github.com/clojure/math.combinatorics/blob/master/src/main/clojure/clojure/math/combinatorics.clj

2:48 looks pretty much non-platform specific.

2:48 rurumate: hmm

2:49 futile: Oh man I forgot that writing a parser is kinda hard.

2:49 ddellacosta: probably just add a crossover section for the project and it would be done…without knowing

2:49 (http://yogthos.net/blog/45)

2:50 rurumate: ddellacosta: thanks. I'm off to my daytime job now, will try tonight

2:50 ddellacosta: rurumate: good luck! have a good day. ;-)

2:52 babu`: In core clojure is there a way to check if a variable is unbound?

2:52 futile: babu`: bound?

2:53 ,bound?

2:53 clojurebot: #<core$bound_QMARK_ clojure.core$bound_QMARK_@17281c0>

2:55 babu`: I am getting "ClassCastException clojure.lang.Var$Unbound cannot be cast to clojure.lang.Var"

2:56 amalloy: babu`: you want the var itself, not its current value. (bound? #'whatever)

2:56 futile: yeah that

2:56 babu`: ok thanks. bound? is a function that evaluates its args, right

2:57 futile: babu`: yes, but it takes a var

2:57 babu`: compare these:

2:57 ,+

2:57 clojurebot: #<core$_PLUS_ clojure.core$_PLUS_@1007a>

2:57 futile: ,#+

2:57 clojurebot: #<RuntimeException java.lang.RuntimeException: EOF while reading>

2:57 futile: ,#'+

2:57 clojurebot: #'clojure.core/+

2:57 futile: ,[(type +) (type #'+)]

2:57 clojurebot: [clojure.core$_PLUS_ clojure.lang.Var]

2:58 babu`: Thanks. I knew it was futile to ask a question like this!

2:58 futile: :P

2:58 babu`: it's hardly futile, you're learning aren't you?

2:58 ;)

2:59 How would you guys go about writing a recursive descent parser without using mutable state?

2:59 babu`: yes, but I could have looked it up.

3:00 futile: heh

3:00 babu`: Why is there a get-possibly-unbound-var in clojure.test?

3:07 futile: babu`: they probably needed it

3:08 Aha, this is a neat alternative to read() and peek()

3:08 https://www.refheap.com/18252

3:08 babu`: futile: how is it different from bound?

3:08 futile: babu`: i dunno

3:09 babu`: (defn get-possibly-unbound-var

3:09 "Like var-get but returns nil if the var is unbound."

3:09 {:added "1.1"}

3:09 [v]

3:09 (try (var-get v)

3:09 (catch IllegalStateException e

3:09 nil)))

3:09 futile: whoa

3:09 babu`: so basically it's like var-get but returns nil if the var is unbound

3:10 babu`: Written by none other than Hickey so there must be a reason

3:10 Isn't it expensive to trigger an exception and catch it?

3:11 opqdonut: I think on the jvm it's relatively fast

3:11 babu`: why can't you use the value of bound? and return null?

3:11 opqdonut: maybe you should run a quick benchmark, (var-get bound-var) vs (get-possibly-unbound-var bound-var) vs (get-possibly-unbound-var unbound-var)

3:15 amalloy: futile: functional parsers generally involve passing around the "remainder", ie what is left to parse

3:15 futile: amalloy: hmm interesting

3:16 amalloy: I think the passing around the structure I'm currently building up and mutating it would be the harder thing

3:16 amalloy: well don't mutate it, silly

3:16 futile: amalloy: the only solution I can think of is some really ugly (possibly mutually) recursive functions with ugly param lists

3:16 amalloy: there is a lot of literature about doing it in haskell; google for "X parser combinators" and you'll learn some exciting stuff about parsers in language X

3:16 futile: cool, thanks

3:19 dissipate_: amalloy, which language is better for parsing, haskell or clojure?

3:19 futile: Is there a short-hand for (juxt first rest)?

3:19 ,((juxt first rest) [1 2 3])

3:19 clojurebot: [1 (2 3)]

3:22 amalloy: subjective and unanswerable, dissipate_

3:24 dissipate_: amalloy, :(

3:42 futile: I think I would never use peek.

3:42 ,(doc peek)

3:42 clojurebot: "([coll]); For a list or queue, same as first, for a vector, same as, but much more efficient than, last. If the collection is empty, returns nil."

3:48 hyPiRion: I think I would never use when-first

3:48 dissipate_: i want to create a searchable data structure that has functions that i can do a phrase based search on at run time. then, i want to try to call the function on some arguments, if that fails it tries the second hit in the search and so on, until one of the functions returned from the search is called with the arguments without failing.

3:48 futile: ,(doc when-first)

3:48 clojurebot: "([bindings & body]); bindings => x xs Roughly the same as (when (seq xs) (let [x (first xs)] body)) but xs is evaluated only once"

3:49 futile: wat

3:49 dissipate_: my goal here is to be able to call functions that i can't remember the exact name. the ultimate in lazy programming.

3:53 ordnungswidrig: dissipate_: how is "fail" defined? throwing an exception?

3:53 dissipate_: ordnungswidrig, correct

3:53 futile: Wow, 2005 was so long ago.

3:54 dissipate_: ordnungswidrig, i don't care about IDE searches for function names either. that takes too long IMO. i just want to type in a search phrase and some arguments.

3:55 that search phrase might match keywords in a function's comments/documentation

3:59 ordnungswidrig, imagine how fast you could code if you didn't even have to remember function names. just put a search phrase in quotes with some arguments, e.g. ["finds nth fibonacci number" 10]

3:59 ordnungswidrig: dissipate_: fast like going full speed in the city?

4:00 dissipate_: ordnungswidrig, yep

4:00 ordnungswidrig: dissipate_: that's rather not what I do

4:00 dissipate_: ordnungswidrig, you don't like this idea?

4:01 ordnungswidrig: dissipate_: no, but here for you problem of application until no error:

4:01 (some #(try (apply % ["1.0"]) (catch Exception e nil)) [#(Integer/parseInt %) #(Double/parseDouble %)])

4:02 dissipate_: ordnungswidrig, thanks

4:03 ordnungswidrig, and how about indexing all of the functions (including comments) for search?

4:04 ordnungswidrig: dissipate_: have a look at clojure.repl/doc

4:05 dissipate_: ordnungswidrig, why is my idea bad?

4:05 ordnungswidrig: dissipate_: what's your goal?

4:06 dissipate_: ordnungswidrig, extreme rapid prototyping. i don't want to take the time to look up function names, i just want to whip out a search phrase and have the function looked up during run time.

4:06 ordnungswidrig: dissipate_: why not using the search in the repl to lookup the function?

4:08 dissipate_: ordnungswidrig, takes too much time. i have to stop to search the repl. i just want to type a phrase fast and have it figure out what to do at run time.

4:08 ordnungswidrig: dissipate_: I prefer to think before i code.

4:08 ordnungswidrig: you can also enhance your ide with a full text search for functions

4:09 dissipate_: that would be a nice thing, imho.

4:09 dissipate_: ordnungswidrig, what do you think of the code: ["finds nth fibonacci number" 10]

4:09 ordnungswidrig: dissipate_: is't a vector

4:09 dissipate_: and I'd prefer (fib 10)

4:10 dissipate_: ordnungswidrig, but do you see? i don't have to remember the name of the function that calculates fibonacci numbers.

4:10 ordnungswidrig: dissipate_: I might be an interesting experiment, though. go on and try :)

4:10 kaw: It's hard for a text search to get nuances, e.g. distinguish between something like "returns a sequence of fibonacci numbers starting with the nth fibonacci number" and "finds the nth fibonacci number"

4:10 TEttinger: dissipate_, there's a looku[ thing in lazybot or clojurebot

4:10 lookup*

4:11 ordnungswidrig: kaw: typed clojure will help, like hoogle is amazon for haskell

4:11 dissipate_: kaw, how about 'calculates nth fibonacci number'

4:12 ordnungswidrig: kaw: not amazon, amazing :-) But it's also a little bit like amazon

4:12 TEttinger: &findfn 1 2

4:12 lazybot: java.lang.RuntimeException: Unable to resolve symbol: findfn in this context

4:13 ordnungswidrig: & clojuredocs fibonacci

4:13 lazybot: java.lang.RuntimeException: Unable to resolve symbol: clojuredocs in this context

4:14 ordnungswidrig: $clojuredocs fibonacci

4:14 lazybot: No results found.

4:14 TEttinger: $findfn [0 1 1 2 3]

4:14 kaw: Well, if you have to get the wording (like "returns" vs "calculates" vs "finds") right in the text search, you're back to square one, aren't you?

4:14 lazybot: []

4:14 TEttinger: fib isn't usually a lib function

4:14 kaw: Now you just have to remember a phrase that's much longer than "fib", and you can choose between a few different phrases to remember

4:14 ordnungswidrig: kaw: he wanted to try one match after the other

4:14 TEttinger: but

4:15 kaw: Hmm, okay

4:15 TEttinger: $findfn [0 1 1 2 3] [1 2 2 3 4]

4:15 lazybot: []

4:15 kaw: Still not convinced of its usefulness, but interesting as an experiment I guess

4:15 TEttinger: hm, it can't find combinations

4:15 kaw: Agreed that types would help a lot

4:16 TEttinger: $findfn [0 1 1 2 3] "01123"

4:16 lazybot: [clojure.string/join]

4:16 TEttinger: a ha!

4:16 dissipate_: kaw, what if you saw an application that had search phrases instead of function names?

4:17 TEttinger: dissipate_, no clue what to do

4:17 kaw: I think I would probably be confused? Now there are several ways to refer to one function

4:17 TEttinger: and search isn't always approaching accurate

4:17 ordnungswidrig: dissipate_: how would this look like with search terms? https://gist.github.com/swannodette/3217582

4:18 TEttinger: like a slight wording difference yields a slightly different function -- inc or unchecked-inc ?

4:19 here, these all do the same thing for 1, but will react in different ways on BigIntegers

4:19 $findfn 1 2

4:19 dissipate_: ordnungswidrig, would look good imo

4:19 ddellacosta: what is ".." in clojurescript? is it like "doto" ?

4:19 lazybot: [clojure.core/unchecked-inc-int clojure.core/unchecked-inc clojure.core/inc clojure.core/inc']

4:19 TEttinger: a search for "add 1" could be any of those

4:20 $findfn 111111111111111111111111 111111111111111111111112

4:20 lazybot: [clojure.core/unchecked-inc clojure.core/inc clojure.core/inc']

4:20 TEttinger: I guess inc works, but (partial + 1) wouldn

4:20 't

4:22 dissipate_: TEttinger, no, the search phrase would be: "increment an integer value by 1"

4:24 kaw: $findfn 9223372036854775807 9223372036854775808

4:24 ambrosebs: new blog post on annotating polymorphic types in core.typed http://t.co/50FFbZM1IN

4:24 lazybot: [clojure.core/inc']

4:26 kaw: That's a cool function, is $findfn available in the REPL or just a lazybot thing? Also what functions does it search?

4:26 ddellacosta: ambrosebs: very cool, thanks

4:26 ambrosebs: been meaning to dig into core.typed for some time now.

4:26 ambrosebs: ddellacosta: cheers

4:29 bja: is (map inc (range)) the way to get an infinite range starting from 1?

4:30 ordnungswidrig: bja: (rest (range))

4:31 ambrosebs: ,(range 1)

4:31 clojurebot: (0)

4:31 ordnungswidrig: ,(take 5 (rest range))

4:31 clojurebot: #<IllegalArgumentException java.lang.IllegalArgumentException: Don't know how to create ISeq from: clojure.core$range>

4:31 ordnungswidrig: ,(take 5 (rest (range)))

4:31 clojurebot: (1 2 3 4 5)

4:31 ambrosebs: ,(doc range)

4:31 clojurebot: "([] [end] [start end] [start end step]); Returns a lazy seq of nums from start (inclusive) to end (exclusive), by step, where start defaults to 0, step to 1, and end to infinity."

4:31 ordnungswidrig: bja: map inc would work but you'd invoke inc for every element of the seq

4:33 bja: ordnungswidrig: in this case I don't think the N is large enough to matter, but (rest (range)) is both shorter and less intensive

4:33 thanks

4:34 ambrosebs: ,(take 5 (range 1 Long/MAX_VALUE))

4:34 clojurebot: (1 2 3 4 5)

4:34 ambrosebs: bja: I personally like that better ^

4:35 ordnungswidrig: ambrosebs: that's more explicit

4:35 ambrosebs: I like explicit :)

4:36 TEttinger: kaw, let me find the source

4:36 ordnungswidrig: ambrosebs: Me too, was not meant as a negative point :) But it's long to type

4:36 TEttinger: https://github.com/flatland/lazybot/blob/master/src/lazybot/plugins/clojure.clj#L214

4:37 ambrosebs: ordnungswidrig: usually the tradeoff of explicitness I guess :)

4:37 ordnungswidrig: ambrosebs: but Long/MAX_VALUE is very unsexy, too. "max-long" would be nicer

4:38 bja: fwiw, I defn'd it to range1

4:38 so (range1) should be reasonably explicit in my codebase

4:38 ambrosebs: bja: (range-start 1) might be a useful utility to have.

4:39 ordnungswidrig: or range>

4:40 btw range defaults to Double/POSITIVE_INFINITY

4:40 ambrosebs: ah yes, that's what I meant.

4:42 ordnungswidrig: ambrosebs: I just read about heterogeneous map and vectors. I wonder I one can use the core.typed annotations for web request validation

4:43 ambrosebs: ordnungswidrig: yep. I've yet to find good specs describing compojure or ring web requests.

4:44 ordnungswidrig: ambrosebs: the type of a handler is map -> map

4:45 ambrosebs: how do I declare a homogeneous map?

4:46 ambrosebs: ordnungswidrig: (IPersistentMap k v) or (clojure.core.typed/Map k v)

4:46 ordnungswidrig: use :import/:require/alias as usual to bring into scope.

4:48 ordnungswidrig: ambrosebs: it's hard to annotate because every ring middleware typically ads it's on stuff to the request map

4:49 ambrosebs: I think AWizzArd works on this.

4:49 ambrosebs: ordnungswidrig: interesting. AWizzArd was talking to me before about ring.

4:50 ordnungswidrig: ambrosebs: what I am interested in, is to do runtime validation with proper error reporting.

4:50 ambrosebs: ordnungswidrig: core.typed supports that to some degree. It understands assertions.

4:50 ordnungswidrig: ambrosebs: so I defined a "type system" for the request parameters. I need this for string -> x conversion

4:51 ambrosebs: and for validation. No I see that it is shaped somewhat like the core.typed system :)

4:51 ambrosebs: cool!

4:52 bja: ugh

4:52 ordnungswidrig: ambrosebs: but the error reporting from cf is not quite sufficient, IMHO (not tried, though)

4:53 bja: congrats to myself for just futzing around with range>= so I could rewrite map-indexed

4:53 ordnungswidrig: bja: *g*

4:53 clgv: bja: ;)

4:53 bja: you learned something, didnt you? ;)

4:53 ordnungswidrig: bja: always tell us the complete story.

4:54 ambrosebs: ordnungswidrig: ah, no, core.typed can tell you if your assertions are sufficient to never have a type error.

4:54 TEttinger: bja, I think many people here have done that once

4:54 ordnungswidrig: ambrosebs: cant' we mix in some monadig fary dust and have a proper error reporting :-)

4:54 dissipate_: holy cow, this talk is hilarious http://www.youtube.com/watch?v=P76Vbsk_3J0&feature=youtu.be (Clojure for Java Programmers Part 1 - Rich Hickey)

4:54 ambrosebs: ordnungswidrig: so it's complimentary to your system.

4:54 ordnungswidrig: it's another thing if core.typed can understand yours though

4:55 ordnungswidrig: can you give me an idea of the reporting you want?

4:56 ordnungswidrig: ambrosebs: I'd love to drop my own system. As reporting I imagined replacing every typed value with a pair (left: error, right: value)

4:56 dissipate_: listen to the javaheads be bewildered

4:58 ambrosebs: ordnungswidrig: Could you go into a little more detail?

4:58 ordnungswidrig: with an example?

4:59 ordnungswidrig: ambrosebs: so (validate (v/map :strict true :required {:a v/string :b (v/int 0 5)}) {:a "ab" :b 27}) gives [nil {:b ["integer within 0 5" nil]}]

4:59 this means, the error has the same "shape" as the type def, but uses vector-pairs to encode an error at a leaf

5:01 I'm not sure about the exact "encoding". Thinking about web forms you will typically "iterate" over the fields and fetch the entered unparsed value and optional error

5:02 ambrosebs: ordnungswidrig: hmm. core.typed might not be useful for that.

5:03 ordnungswidrig: ambrosebs: I thought so. I just saw how my "type system" resemlbed the one in core.typed. Can a type in core.typed be instrospected at runtime easily?

5:04 ambrosebs: ordnungswidrig: you might have a function validator-a-b-map which is Any -> (U [NoError {:a String :b Number}] [Error Any])

5:04 ordnungswidrig: not really, it's designed to only be used at development time.

5:05 ordnungswidrig: ambrosebs: so it's all macro magic?

5:05 ambrosebs: ordnungswidrig: yes. it's syntactic analysis.

5:06 ordnungswidrig: ambrosebs: so I cannot access a "type value" like "(HMap required {:a AnyInteger})" at runtime?

5:07 ambrosebs: ordnungswidrig: what are you thinking of doing?

5:08 ordnungswidrig: ambrosebs: resuing a core.typed type definition for runtime validation

5:10 ambrosebs: ordnungswidrig: you would need to load core.typed at runtime, which might not be cheap.

5:10 ordnungswidrig: but sure, core.typed has good facilities for manipulating types.

5:10 or recursing over them etc.

5:11 ordnungswidrig: ambrosebs: I see. So I will steel the syntax for type declaration and add custom validation like range checks in to.

5:11 ambrosebs: ordnungswidrig: that's an area I'll like to explore also.

5:11 ordnungswidrig: ambrosebs: you mean arbitrary validation functions?

5:12 ambrosebs: ordnungswidrig: static types -> runtime contract transformation.

5:12 ordnungswidrig: ambrosebs: does this include runtim contract validation?

5:13 ambrosebs: ordnungswidrig: I'm more interested in throwing a type error on failed contracts.

5:13 ordnungswidrig: ambrosebs: on runtime?

5:13 ambrosebs: ordnungswidrig: yes

5:14 ordnungswidrig: ambrosebs: what are the cases where a this could happen? wouldn't the type error be caught at compile time?

5:15 ambrosebs: ordnungswidrig: when there is interaction between typed and untyped code, we want to protect typed code at runtime from "unchecked" untyped code.

5:16 ordnungswidrig: ambrosebs: I see, on the boundaries between typed and untyped code. Could you then skip the runtime verification for calls from typed to typed?

5:16 ambrosebs: ordnungswidrig: yes.

5:17 ordnungswidrig: core.typed doesn't do *any* runtime validation currently, so it's a deficiency that untype/typed interaction isn't checked at runtime.

5:17 ordnungswidrig: ambrosebs: I see.

5:49 AWizzArd: core.typed experts: I did (ann ring.adapter.jetty/run-jetty [Any Any -> org.eclipse.jetty.server.Server]) but still get “WARNING: Type Checker: Definition missing: ring.adapter.jetty/run-jetty”. Ideas?

5:51 ambrosebs: (ann ^:no-check ...)

5:53 Anderkent: hm. That seems like a disconnect between the error message and what it does. ^:no-check makes core.typed not validate calls to run-jetty, right? Why would that solve a 'definition missing' error? Or is that 'definition matching call missing', not 'symbol has no type definition'?

5:54 ambrosebs: :no-check means: don't check any `def`s of this var, and dont' worry if its missing.

5:54 Anderkent: ah, the point is it has a type declaration but no definition. K.

5:55 ambrosebs: Anderkent: yes. I'll make the warning more descriptive.

5:55 AWizzArd: Ah :)

5:55 Anderkent: so no-check means don't go into the definition of this function, but still verify that anything that *uses* this function is valid. Right?

5:55 AWizzArd: So if I had a def somewhere, the warning would go away too.

5:56 ambrosebs: yes. The def must have a 2nd argument though.

5:56 Anderkent: yes.

5:56 Anderkent: cool

6:03 silasdavis: I was just able to 'systemctl enable insync@<user>'

6:04 but when I ran systemctl list-units and searched for 'insync' I found nothing

6:04 I thought list-units gave all available services...

6:04 ?

6:04 sorry wrong channel

6:34 turbopape: Hi guys,

6:34 anyone already done mahout/hadoop work on clojure ?

6:34 how did you find the journey ?

6:34 did you then use cascalog to query, etc.. ?

6:45 llasram: turbopape: It's mostly like integrating with any other Java library

6:45 turbopape: A significant amount of Mahout's functionality is pre-packaged into complete sets of Hadoop jobs fronted by "driver" classes

6:46 So for the most part you can e.g. use Cascalog to build jobs which get the data into the appropriate input form

6:47 turbopape: ok llasram , just to make sure I understood, you mean that the algorithms are just queries

6:47 I Can issue using cascalog ?

6:47 llasram: Mmmm. No

6:47 turbopape: Ok llasram , it's more like cascalog is used to feed mahout vectors etc... ?

6:48 llasram: Sorry, haven't had my coffee yet and am typing slowly :-)

6:48 But that's closer

6:48 Most of Mahout's entry points run complete Hadoop jobs

6:48 turbopape: no problem, you are saving my life already :)

6:48 llasram: Or sets of jobs

6:48 turbopape: I am totally new at this...

6:48 llasram: Cascalog doesn't provide a direct way to integrate existing Hadoop jobs as queries

6:49 So you end up running a query to get concrete output on HDFS

6:49 turbopape: Ok...

6:49 llasram: Then calling a Mahout driver class method on that intermediate output

6:49 And putting the Mahout output somewhere else concrete on HDFS

6:50 turbopape: But is there a significant gain to do this in clojure ? I'd like to take advantage of its vectors, immultability, expressiveness, etc...

6:50 But will it add overhead ?

6:50 like translating to classes, etc... ?

6:51 (I mean translating cloj seq <-> vectors, sequencefile, etc... ?)

6:51 Anderkent: is CinC published to clojars?

6:52 llasram: turbopape: There's no more overhead w/ Mahout than anything else in Clojure. If you're already using Cascalog, then it provides a completely reasonable and in-Clojure mechanism for building the input to Mahout's algorithms

6:52 turbopape: Ok llasram , that makes perfect sense :)

6:52 Thank you for the help !

6:52 llasram: np. Best of luck!

7:08 ambrosebs_: FYI just created #typed-clojure

7:08 Anderkent: ,(apply @#'or nil nil [1 2])

7:08 clojurebot: (clojure.core/let [or__3943__auto__ 1] (if or__3943__auto__ or__3943__auto__ (clojure.core/or 2)))

7:08 Anderkent: who said you can't take the value of a macro

7:08 muahahahaha

7:12 ucb: eep

7:12 nice one Anderkent

7:12 hhenkel: Hi all, someone here to the rescue? I don't get it I got a HashMap "collection" and a Vector "values" defined like that:

7:13 (def collection {"FreePhysicalMemorySize" {"cycle" 30, "option" "ignoreErrors=true", "action" "read", "attribute" "FreePhysicalMemorySize", "mbean" "java.lang:type=OperatingSystem"}, "FreeSwapSpaceSize" {"cycle" 30, "option" "ignoreErrors=true", "action" "read", "attribute" "FreeSwapSpaceSize", "mbean" "java.lang:type=OperatingSystem"}, "TotalPhysicalMemorySize" {"cycle" 3600, "option" "ignoreErrors=true", "action" "read", "attribute" "FreeSwapSpaceSize",

7:13 (def values ["FreePhysicalMemorySize" "attribute"])

7:13 Now I would like to do something like: ((collection (first values)) (rest values)) wich gives me nil

7:14 If I do it like this: ((collection (first values)) "attribute") I get the expected value "FreePhysicalMemorySize" as a result.

7:14 Anderkent: ,(rest [1 2])

7:14 clojurebot: (2)

7:15 Anderkent: rest gives you a list, not just the second param

7:15 since you want "attribute" not ["attribute"], you must take it out with (second values) instaed of rest

7:15 hhenkel: Anderkent: okay, so I use (str (rest [1 2]) ?

7:15 hmm, okay

7:15 Anderkent: either that or

7:16 (apply (collection (first values)) (rest values))

7:16 but that doesnt make much sense in this example

7:16 do you ever expect values to have more than 2 elements?

7:16 actually

7:16 hhenkel: No, as I check for that earlier on.

7:16 Anderkent: the best solution is (get-in collection values)

7:16 hhenkel: I could also use last I think?

7:17 Anderkent: ,(get-in {"a" {"b" :c}} ["a" "b"])

7:17 clojurebot: :c

7:17 Anderkent: you could, but second is better, and get-in is nicer still

7:19 hhenkel: Anderkent: Agreed, get-in is very nice...it looks like it solves all the thinks I want to do all at once.... ;)

7:19 But I learned much...

7:35 clgv: any opinions on the comparison "congomongo vs monger"?

7:41 Anderkent: Bronsa: I can't seem to get cinc analyzer to parse ns forms (complains about namespaced symbols in host expressions). Is that expected or new? Should I raise an issue?

7:48 Bronsa: Anderkent: it's a bug, i'm looking into it thanks

7:50 squidz: how can I use sets in clojurescript? when I call (set [1 2 3 3]) #{1 2 3 3} is returned. Shouldn't it be #{1 2 3} ?

7:50 is there a bug in clojurescript?

7:51 Anderkent: Bronsa: the issue is that clojure.core/with-loading-context expansion includes (. clojure.lang.Var (clojure.core/pushThreadBindings

7:51 Bronsa: Anderkent: yes, I saw that

7:51 Anderkent: which is apparently perfectly valid because the compiler just takes (name sym) as fn name, discarding the namespace

7:52 Bronsa: Anderkent: I just fixed that but apparently there's still a problem with the method finder

7:53 Anderkent: bleh, I just forgot to convert it back to a symbol, everything is working now

7:53 going to push a fix just now, thanks a lot

7:54 Anderkent: no problem. I was looking at using cinc for code walking (with proper lexical scope tracking), and I think if I hook into -analyse/parse I might get something useful. There's no published jar of cinc yet though, right?

7:55 squidz: is there a way to find out the clojurescript version being used with lein cljsbuild? I am not sure why clojurescript wouldnt handle sets correctly

7:55 Bronsa: Anderkent: no, it's not complete/tested enough that I feel confident to release even the analyzer only yet

7:55 Anderkent: the analyzer on its own wouldn't be that useful either, at least without a unparse method :P

7:56 Bronsa: Anderkent: I have a yet-to-finish emit-form pass here

7:57 I'm having an exam at the uni tomorrow so I'm not going to finish it today but in the next days I'm going to push it

8:00 squidz: anybody know why i'm getting this? et [1 2 3 3])

8:01 (set [1 2 3 3]) -> #{1 2 3 3}

8:01 Anderkent: ,(set [1 2 3 3])

8:01 hyPiRion: well, that's a bug

8:01 clojurebot: #{1 2 3}

8:01 Anderkent: ,(set [1 2 3 3L])

8:01 clojurebot: #<NumberFormatException java.lang.NumberFormatException: Invalid number: 3L>

8:01 hyPiRion: 3N, rather.

8:01 squidz: it's only happening for clojurescript

8:01 Anderkent: ,(set [1 2 3 3N])

8:01 clojurebot: #{1 2 3}

8:01 Anderkent: ah.

8:02 blame javascript

8:02 augustl: squidz: 3 vs "3" maybe?

8:02 hyPiRion: Floats, how to they work

8:02 Anderkent: my thinking exactly

8:02 hyPiRion: ,(set [1.0 1.0M])

8:02 clojurebot: #{1.0 1.0M}

8:02 augustl: the literals 3 and 3 ought to be the same float, though

8:02 hyPiRion: ,(set [1.0 1.0M 1.00M]) ;; etc.

8:02 clojurebot: #{1.0 1.0M 1.00M}

8:02 augustl: if the example is exactly that - (set [1 2 3 3])

8:02 squidz: yeah that is the exact example

8:03 let me try it in a fresh clojurescript repl

8:03 edbond: discussion of the bug - https://groups.google.com/forum/#!msg/clojurescript/SKzdT-GOQaw/VOhPcpljil0J

8:03 Anderkent: reproduced on himera

8:04 right, http://dev.clojure.org/jira/browse/CLJS-516

8:05 squidz: ah yeah I see it

8:05 edbond: squidz, you can use distinct until is solved

8:06 squidz: edbond: thanks for the tip

8:08 borkdude: Is it possible to start lein from a specific path?

8:15 Anderkent: Other than (cd path && lein), I guess?

10:21 hhenkel: I found "update-in" and I'm able to work with it, as long as it comes to numbers. All examples I found increment or modify number values. With what kind of function could I replace a string?

10:23 pepijndevos: &(update-in {:a "foo"} [:a] str "bar")

10:23 lazybot: ⇒ {:a "foobar"}

10:24 pepijndevos: hhenkel, any function that returns a string relly

10:24 clgv: in mongodb how do I get a list of all collections or documents in the db?

10:24 I am using monger

10:26 ah found it in the source: monger.db/get-collection-names

10:28 hhenkel: the function you need to pass to update-in is like follows (defn f [current-value & optional- arguments] ...) and then (update-in m [:somekey] f opt-arg1 opt-arg2 ...)

10:29 you can implement everything you like in that function

10:35 srruby: How do I read in stdin as follows cat abc.txt | java -jar foo.jar ?

10:37 nDuff: srruby: Depends. Do you want to iterate line-by-line? Read to EOF all at once? ...?

10:38 srruby: (as an aside -- it's more efficient to java -jar foo.jar <abc.txt, avoiding cat and the pipeline).

10:38 srruby: ...that way your process gets a FD directly on the file itself.

10:39 srruby: All at once

10:39 nDuff: I'd play with slurp, then.

10:40 You also have all the standard Java methods on System/in

10:42 Anderkent: yeah, (slurp *in*) should do it

10:46 mpenet: core.async folks: is it safe to do (put! ch) then (close! ch), since put! is async is there a chance that the chan gets closed before the put! ?

10:47 well technically (put! ch :something)

10:51 hhenkel: pepijndevos: I don't want to join to strings I would like to replace it. That is the issue I got.

10:52 pepijndevos: &(update-in {:a "foo"} [:a] constantly "bar")

10:52 lazybot: clojure.lang.ArityException: Wrong number of args (2) passed to: core$constantly

10:53 pepijndevos: &(update-in {:a "foo"} [:a] (constantly "bar"))

10:53 lazybot: ⇒ {:a "bar"}

10:53 pepijndevos: hhenkel, ^

10:53 but that's rellly just assoc-in

10:55 hhenkel: pepijndevos: ah, okay...that was what I was looking for. Currently I'm totally lost in my missing knowledge of the clojure vocabular, resulting in me trying to reimplement stuff that's allready there...but I keep learning by doing so... ;)

11:04 sheldonh: is there a clojure function that returns the first or last (don't care which) item in a coll, depending on whether first or last is fastest for the concrete type of the coll?

11:05 clgv: hhenkel: if you have only a flat map just use assoc

11:05 supersym: can anyone tell me how to get the possible combinations of elements in a sequence while maintaining the order, like [2 2 5 5] ~> [[2][2 5 5]], [[2 2][5 5]], [[2 2 5][5]], [2 [2 5] 5]

11:05 clgv: &(assoc {:a "foo"} :a "bar")

11:05 lazybot: ⇒ {:a "bar"}

11:06 clgv: hhenkel: btw there is `assoc-in` for replacing values

11:06 hhenkel: clgv: pepijndevos allready mentioned that earlier on.

11:06 clgv: &(assoc {:a {:b "foo"}} [:a :b] "bar")

11:06 lazybot: ⇒ {[:a :b] "bar", :a {:b "foo"}}

11:06 clgv: &(assoc-in {:a {:b "foo"}} [:a :b] "bar")

11:06 lazybot: ⇒ {:a {:b "bar"}}

11:07 clgv: hhenkel: oh ok. what I wanted to say is. for replacing the value with a constant (wrt the current value) use the assoc functions ;)

11:07 llasram: supersym: So you want all possible ways of dividing a sequence into any number of subsequences?

11:09 supersym: llasram: that is correct, but the order can't be changed so [2 5 2 5] is out

11:09 looks like a recursive pattern but I fail to

11:10 see it

11:10 hhenkel: clgv: okay, an for "really" changing the value in the actual map I can create an atom from it and change the value with that, right?

11:11 llasram: supersym: I believe what you actually want is all sequences of integers >0 which add up to (count coll)

11:11 clgv: hhenkel: I dont know if understand correctly. just provide a code example

11:11 supersym: llasram: dude..thank you

11:11 you are right

11:12 hhenkel: clgv: respectively, it works like described for me, I'm not sure if it is the way to do it.

11:12 clgv: hhenkel: show example code demonstrating your atom idea and we can talk about it ^^

11:13 hhenkel: clgv: okay, I'll try to show a simple example.

11:13 clgv: and dont forget to state the goal you want to achieve

11:16 hhenkel: (def my-atom (atom {"aa" "a" "bb" "b"}))

11:16 (defn alter-value [collection variables new-string] (assoc-in collection variables new-string))

11:16 (swap! my-atom alter-value ["bb"] "test")

11:18 clgv: hhenkel: you can do that more directly if you like: (swap! my-atom assoc-in ["bb"] "test")

11:18 hhenkel: my-atom now provides the altered value "test". As said, that works for me, I'm not total sure if it is the way to do stuff.

11:19 clgv: yes it is. except that you should not use (def my-atom ..) for "variables" like in other procedural languages in your regular program

11:20 but for that demo or in repl that is ok

11:20 to try it here ##(let [my-atom (atom {"aa" "a" "bb" "b"})] (swap! my-atom assoc-in ["bb"] "test"))

11:20 lazybot: ⇒ {"aa" "a", "bb" "test"}

11:21 clgv: hhenkel: usually you'd also use keywords as keys instead of strings except your application really needs strings

11:22 hhenkel: clgv: okay, so I better user "let" to define "variables" (like in other languages) then?

11:23 clgv: hhenkel: yes you use `let` to assign a name to values to reuse the value in the following code

11:24 hhenkel: def is only for top-level vars that reside in the namespace, e.g. functions or constants

11:24 hhenkel: clgv: I had keywords before but I struggeled with it, as I tried to reimplement stuff that was allready there and decided to stick with string for the moment...^^

11:25 pbostrom: sheldonh: &(doc peek)

11:25 &(doc peek)

11:25 lazybot: ⇒ "([coll]); For a list or queue, same as first, for a vector, same as, but much more efficient than, last. If the collection is empty, returns nil."

11:25 hyPiRion: pbostrom: ##(doc peek)

11:25 lazybot: ⇒ "([coll]); For a list or queue, same as first, for a vector, same as, but much more efficient than, last. If the collection is empty, returns nil."

11:25 hyPiRion: heh

11:25 hhenkel: As I allready mentioned first I struggled with a poor mans implementation of "get-in" and now with "assoc-in".

11:30 clgv: How would I do the altering when I using a ref instead of an atom? I know I need do-sync...and maybe alter?

11:31 clgv: hhenkel: yes like that: ##(let [my-ref (ref {"aa" "a" "bb" "b"})] (dosync (alter my-atom assoc-in ["bb"] "test")))

11:31 lazybot: java.lang.RuntimeException: Unable to resolve symbol: my-atom in this context

11:31 clgv: &(let [my-ref (ref {"aa" "a" "bb" "b"})] (dosync (alter my-ref assoc-in ["bb"] "test")))

11:31 lazybot: ⇒ {"aa" "a", "bb" "test"}

11:31 clgv: &(let [my-ref (ref {"aa" "a" "bb" "b"})] (alter my-ref assoc-in ["bb"] "test"))

11:31 lazybot: java.lang.IllegalStateException: No transaction running

11:32 clgv: without the `dosync` you get that exception ^^

11:34 hhenkel: clgv: ah, okay, seems like I missed bracket. Thank you very much for your help!

11:35 clgv: np

11:37 zerokarmaleft: hhenkel: fwiw, if you altering a non-nested key, you can just use assoc

11:38 &(-> {"aa" "a" "bb" "b"} (assoc "bb" "test"))

11:38 lazybot: ⇒ {"aa" "a", "bb" "test"}

11:40 zerokarmaleft: assoc-in and update-in let you drill down into a nested map

11:40 &(-> {:a 1 :b {:x "hello" :y "goodbye"} :c 3} (assoc-in [:b :x] "test"))

11:40 lazybot: ⇒ {:a 1, :c 3, :b {:y "goodbye", :x "test"}}

11:41 hhenkel: zerokarmaleft: Thanks clgv mentioned that. I'm currently playing around with nested maps (configurations) - I would like to implement something like "variables" in config files, therefore replacing placeholders with other stuff.

11:42 zerokarmaleft: hmm sorry, I should read the scrollback more carefully

11:44 hhenkel: zerokarmaleft: np, I'm impressed how helpful people are in this channel.

11:44 clgv: $karma zerokarmaleft

11:44 lazybot: zerokarmaleft has karma 1.

11:44 clgv: :O

11:45 zerokarmaleft: clgv: now you've done it

11:45 clgv: :D

11:59 kittylyst: Monger is giving me this exception:

11:59 reporting.core> (connect-to-jclarity-prod)

11:59 MongoException can't find a master com.mongodb.DBTCPConnector.checkMaster (DBTCPConnector.java:518)

11:59 I see a couple of references to this on SO, but no resolutions - anyone got any thoughts?

12:16 ethanis: Hi folks, any core.typed users around?

12:18 dnolen: ethanis: there are a few, just ask your question, there's also a core.typed IRC channel #typed-clojure

12:18 ethanis: I am just starting to try it out, but have run into an issue with annotating defrecords in version 0.1.26

12:19 dnolen: ethanis: if no one can answer now you also have the core.typed mailing list, Ambrose is a pretty responsive guy

12:19 ethanis: alright, thanks for the suggestion dnolen

12:21 ambrosebs_: ethanis: Have you tried version 0.2.1?

12:22 ethanis: no!

12:22 will do that, thought latest was 0.1.26 for some reason

12:22 ambrosebs_: ethanis: That version is only a few weeks old.

12:23 ethanis: (I think I assumed this because on github, master is marked as 0.1.27-SNAPSHOT)

12:23 trying 0.2.1 now

12:23 here's what I'm attempting, just want to make sure I'm not being completely knuckleheaded about this

12:23 https://gist.github.com/sherbondy/6425817

12:23 Anderkent: I recommend using either [artifact-name "RELEASE"] or lein try artifact-name when playing around with stuff

12:24 exactly to avoid the pain of discovering what the last stable version of X was

12:24 srruby: I want to read stdin into a string. Is there a more idiomatic way than this? (pprint (apply str (interpose "\n" (doall (line-seq (java.io.BufferedReader. *in*)))))))

12:25 Anderkent: srruby: (slurp *in*)

12:25 weird, it's the second time reading stdin came up today

12:26 ambrosebs_: ethanis: there's no error there.

12:26 ethanis: do you mean the "INTERNAL BUG!"?

12:26 ethanis: yeah

12:26 but that doesn't appear in 0.2.1

12:27 Instead, I get: "clojure.lang.Compiler$CompilerException: java.lang.Exception: Found inner call to check-ns or cf, compiling:(rt.core:12:1)"

12:27 Is check-ns intended for use in the repl only?

12:27 ambrosebs_: ethanis: Yes, don't put check-ns directly in your namespace.

12:27 or for unit tests.

12:27 yes.

12:29 clgv: srruby: (println (slurp *in*)) should work as well. maybe you can wrap the bufferedreader here as well

12:29 ethanis: ambrosebs_ how is a user supposed to know that? was that mentioned somewhere and I glossed over it?

12:29 ambrosebs_: ethanis: I don't think its mentioned explicitly anywhere.

12:30 futile: It seems that creating an uberjar is the right way to deploy a Lein (web) app, right?

12:30 srruby: Thanks all.

12:30 Anderkent: futile: if you're deploying as an executable jar, yes.

12:30 ambrosebs_: ethanis: I'll add to the check-ns docstring.

12:30 futile: Anderkent: as opposed to..?

12:30 Anderkent: targetting a servlet

12:30 futile: Oh, no I'm just deploying to AWS.

12:30 clgv: futile: it is one option when you deploy with jetty. but you could also create a war file for a popular servlet container

12:31 futile: Okay.

12:31 ethanis: ambrosebs_ woohoo, thanks. Would it be helpful for me to open an issue just for record keeping?

12:31 ambrosebs_: ethanis: yes.

12:31 futile: Does "lein repl" require the source of a lein project to work?

12:31 ethanis: on it!

12:31 ambrosebs_: ethanis: also mention that cf cannot be used recursively

12:31 thanks!

12:32 technomancy: futile: technically bytecode is enough

12:32 ethanis: okay

12:32 technomancy: futile: but lein assumes it's being run from a checkout

12:32 futile: Oh.

12:33 technomancy: you can embed nrepl in an application easily enough though

12:33 futile: Basically I'm wondering if I can deploy just an uberjar (per your mailing-list email on Aug 19) and still use lein repl in production.

12:33 technomancy: futile: you would do `lein repl :connect $PORT` rather than `lein repl` but it should still work

12:33 or `grench repl` =)

12:34 srruby: echo "hello" | lein run works ok. But echo "hello" | echo "hello\nworld" | java -jar ./target/foo.jar fails- Exception in thread "main" java.lang.ExceptionInInitializerError

12:34 lazybot: "hello" | lein run works ok. But echo "hello" | echo "hello\nworld" | java -jar ./target/foo.jar fails- Exception in thread "main" java.lang.ExceptionInInitializerError

12:35 futile: grenchman!

12:35 Anderkent: futile: our web app uses drawbridge in which case you can just lein repl :connect https://foo/debugging/repl

12:35 very convenient

12:35 futile: Anderkent: I can dig that.

12:36 technomancy: futile: sausage-leg jeans, kicky-boots; the whole deal

12:37 * futile wonders when Google is gonna kill Google Drive saying "sorry everyone; just use Dropbox"

12:37 Anderkent: srruby: does it run if you remove the slurp *in* call?

12:37 my guess would be your packaging process went wrong

12:37 didn't compile main or sth

12:37 srruby: OK. looks like a java configuration problem

12:37 callen: futile: prolly never since it encompasses Google Docs now.

12:37 clgv: futile: when the NSA is tired of watching two places ;)

12:40 futile: heh

12:41 ethanis: alright ambrosebs_, issue submitted. Hope it's well-formatted (never used jira before): http://dev.clojure.org/jira/browse/CTYP-41

12:41 thanks for your help, will ping if I run into further issues

12:42 ambrosebs_: ethanis: perfect!

12:42 ethanis: please do.

12:42 Anderkent: jira is just such a pain :((

12:44 srruby: When I run it through java -jar it is failing when it sees slurp

12:45 callen: technomancy: I am kinda curious as to what sausage leg jeans look like

12:45 srruby: Do I have to downgrade Leiningen ?

12:45 callen: I'm almost afraid to know.

12:46 Anderkent: srruby: works for me. Wanna post the code?

12:47 srruby: https://www.refheap.com/18261

12:50 TimMc: callen: Perhaps those really skinny jeans that make people's legs look like they were stuffed into a sausage casing?

12:51 callen: TimMc: that's what I figured. Hrm.

12:51 srruby: Anderkent: Thanks. That part works.

12:54 technomancy: callen: I think it means they're mostly round but tied off at the end

12:59 dissipate__: interesting fact: clojure's founder Hickey is a former C++ developer

13:00 callen: dissipate__: yawn.

13:01 dissipate__: if you look at the sort of work he did, that's not surprising at all.

13:01 muhoo: well yeah, he wrote a famous paper on c++ functors in the 90s

13:01 callen: muhoo: poor bastard was trying to get out of the trap even back then.

13:01 srruby: When I run clojure via jar it is not finding my resource. I've got (slurp (clojure.java.io/resource (str "resources/fixtures/" file-name)))

13:02 Anderkent: srruby: ah. is the resources dir included in your uberjar?

13:02 dissipate__: callen: why a yawn? i think it's interesting that lisp turned him around to a completely different 'paradigm'

13:02 srruby: Anderkent: Yes

13:02 Anderkent: srruby: basically when you run via lein run, current directory is on the classpath so it 'just works'

13:02 hm.

13:02 callen: dissipate__: do you know what a functor is?

13:03 dissipate__: callen: in c++ no

13:03 srruby: I'm running it via java -jar

13:04 Anderkent: I'm running it via java -jar it works fine when I do lein run

13:04 dissipate__: callen: i ran into functors briefly in ocaml

13:05 callen: I don't think Hickey had any singular epiphanies. Clojure represents a well-thought out approach to design that he'd been accumulating for a long time.

13:05 Anderkent: srruby: yes but that's because your classpath is different with lein run. What's your directory structure? The "resources/" in your name seems suspicious, it shouldn't have to be there (unless your file path is ./resources/resources/fixtures)

13:05 callen: I once got him to recommend some books to me and the impression I got was that Clojure was long coming.

13:06 srruby: Anderkent: Thanks I'll look into it

13:07 Anderkent: srruby: https://www.refheap.com/18261 that works for me

13:08 dissipate__: callen: this 'issue' of macros not being very composable with functions predates clojure, right?

13:10 technomancy: dissipate__: yes, but it's less noticeable in CL because CL makes it awkward to use higher-order functions

13:10 callen: dissipate__: gods yes. lol. What technomancy said is very true.

13:10 mutable code and excessive macros made it overly difficult to compose functions in CL.

13:10 mutable data, I guess I should say. you get my meaning.

13:11 dnolen: dissipate__: people seem to misunderstand the source of that meme, in the early days Clojure devs were not primarily composed of people experienced with Lisp and produced libraries that unnecessarily leaned on macros where functions would suffice.

13:11 Anderkent: dissipate__: not composable? ##(apply (comp (partial @#'or nil nil) (partial @#'and nil nil)) [1 2 3])

13:11 lazybot: ⇒ (clojure.core/let [and__3822__auto__ 1] (if and__3822__auto__ (clojure.core/and 2 3) and__3822__auto__))

13:13 dissipate__: dnolen: i see. in one of his talks aimed at Java devs, Hickey admitted that macros are really language design. that's pretty heavy.

13:14 ethanis: okay, ambrosebs_, here's a tricky one for you: is there any way to annotate an individual implementation (defmethod) of a multimethod that has been required from a library (and thus has no type annotations of its own)?

13:14 or, alternatively, is it possible for me to annotate the multimethod once it's been required?

13:14 muhoo: well the problem i've had with macros is with libraries like noir, where, once you start down the road of macros, often you have to use more macros to deal with those, and you end up wiht a macro infestation.

13:14 dissipate__: i can totally see macros being abused

13:14 ambrosebs_: ethanis: hmm. Probably not currently.

13:15 muhoo: or as zach said in one of his talks (paraphrasing), programs that write programs is cool, but programs that write programs that write programs puts you into a danger zone

13:15 Anderkent: muhoo: or midje. I love midje, but sometimes it's such a pain

13:15 dissipate__: muhoo: how about a shop where your coworkers send you to macro hell?

13:15 ambrosebs_: ethanis: want to bring the convo over to #typed-clojure?

13:15 muhoo: dissipate__: charge by the hour :-)

13:15 ethanis: okay!

13:16 Anderkent: (alter-var-root #'defmacro (constantly #'defn)).

13:16 ;D

13:16 dissipate__: somehow i don't think all these java devs that Hickey is giving these talks to are going to properly implement macros

13:17 srruby: :Anderkent where is your resources directory

13:17 Anderkent: under project root

13:17 all paths are relative to project root

13:17 muhoo: all you have to do is screw it up once, then you go "oh, wow, i shouln'ta done that"

13:18 technomancy: srruby: resources/ is on the classpath; you should load things relative to it rather than relative to the project root

13:18 srruby: (you should never see the string "resources" in your code)

13:18 muhoo: i made a patch to a library some time ago that was all macros, and didn't need even one. i almost literally did what Anderkent suggested, and took out all the # and ~

13:19 srruby: Is project root the src directory? I see the word resources in jar tvf foo.jar

13:19 dissipate__: muhoo: so it's all functions now?

13:19 Anderkent: srruby: no, it's where your project.clj lives

13:19 technomancy: there shouldn't be a resources directory in your jar

13:21 muhoo: dissipate__: yep. it was a small library, maybe a page or two of code, a wrapper around some java stuff. i changed all the macros to funtions, submitted a pull request, it got accepted. it was just a newbie "oh i though you needed macros fo that" situation, apparenntly

13:21 lynaghk: Is there a way to test with Midje that something is logged (via taoensso's timbre library)?

13:21 callen: lynaghk: 1. Don't use midje 2. with-out-str ?

13:22 lynaghk: I tried using Midje's prerequisites, but `info` is a macro

13:22 hmm, with-out-str is ghetto but may work.

13:22 dissipate__: muhoo: hmm, interesting. i could be wrong, but i suspect that functions are turing equivalent to macros.

13:22 callen: lynaghk: well, that or patch/mock the logging library to use an fn that puts messages into a core.async channel

13:22 lynaghk: then take off the channel.

13:23 Anderkent: callen: why not use midje? lynaghk: hook into timbre/send-to-appenders!

13:23 lynaghk: Anderkent: my gut feeling is that the proper way to do this is to ensure the logging fn is called, not actual try to catch the side effect.

13:23 callen: lynaghk: just add a callback fn, for pete's sake.

13:24 Anderkent: lynaghk: the problem is that there's no logging fn, timbre (if level ...) is inlined into your code to avoid the performance hit

13:24 lynaghk: Anderkent: yeah, right.

13:24 muhoo: dissipate__: i dunno. seems to me that macros are functions! they just oprate on code before it compiles. i'm no expert on macros, they have been only minimally necessary for me so far.

13:25 callen: muhoo: macros can be useful for things like Korma.

13:25 muhoo: but their use in Korma is very limited and represents only a top-level DSL.

13:25 the macros just gather the operator and body up.

13:25 Seems a fine use of macros to me.

13:25 dissipate__: muhoo: yeah, that sounds about right. i'm staying far away from them for now. after watching that video 'macros are hard', i'm afraid they are going to get me all twisted up. some really gnarly stuff going on there.

13:25 callen: I am grateful their fn* counterparts exist though.

13:26 Anderkent: lynaghk: you can register middleware with timbre

13:26 and use that to see if your message comes through

13:26 callen: that's what I said earlier.

13:26 Anderkent: it won't be an end to end test but you

13:26 you can trust timbre to work and just test your side

13:26 callen: just send logs through a core.async channel

13:26 Anderkent: callen: you did? I didn't catch that.

13:27 callen: yes I've been trying to get him to use a core.async channel log-event handler this whole time.

13:27 lynaghk: callen: I already have a core.async appender for timbre in this library, so I'll give that a go =)

13:27 dnolen: dissipate__: there's nothing wrong with macros, #1 use case is simple sugar where functions will not suffice, or a functional solution is not worth the cost of admission

13:27 lynaghk: but grudgingly; only because I can't stub the fn because timbre is using macros =)

13:28 dnolen: dissipate__: Java devs are familiar with macros, sadly it's called ANTLR

13:29 Anderkent: I don't see why you'd use core.async instead of just appending the intercepted log messages to a list

13:29 coventry: lynaghk: Could you wrap the test in a lexical closure which stubs out the timbre macro?

13:29 arity: Are there any site for podcasts on clojure or functional programming in general?

13:29 lynaghk: Anderkent: the test syntax is a bit cleaner using core.async than with-out-str

13:30 callen: dnolen: *shudder*

13:30 lynaghk: it's not just syntax, it's semantically cleaner and easier to test.

13:31 Anderkent: uh what? I was thinking more of (fn logging-middleware [args] (alter seen-messages conj args)). Where does with-out-str come in?

13:31 callen: with channels you get discrete log messages, with with-out-str you have to split and sanitize things yourself.

13:31 Anderkent: unless you really care that they arent printed out, but why would you

13:31 then obvlsy reset seen-messages in a fixture around your tests (probably the same one that hooks the logging middleware in)

13:31 callen: Anderkent: the reason for using core.async rather than...a ref? (not sure what you're thinking there) is to avoid global state.

13:32 Anderkent: if you have multiple tests or test-cases testing the logging library, core.async will work even if they run concurrently, this is not the case if you're using a top level def'd atom or ref.

13:32 you should hold your test code to a higher standard than that.

13:32 dissipate__: dnolen: you can change the java language with ANTLR?

13:32 Anderkent: you create the atom in a fixture around your test

13:32 it's not global

13:32 lynaghk: callen: unfortunately that's a moot point since Timbre uses a global atom as its config.

13:32 callen: Anderkent: that would work if it's scoped to each test.

13:33 Anderkent: (around :facts ...)

13:33 callen: lynaghk: I just got done figuring out a nice closure + global atom pattern for such things, I might consider patching timbre to use this.

13:33 then you're given the option of muggle-mode or a closure.

13:33 lynaghk: callen: you should gist up and example and email me at the very least, I'd love to see that

13:33 Anderkent: would core.async even preserve log message order? If you hit the channel twice, both writes will park and your read will read from a random one, right?

13:33 lynaghk: atoms rub me the wrong way.

13:33 callen: lynaghk: no need, just look at bulwark. github.com/bitemyapp/bulwark

13:34 Anderkent: or are you using some kind of buffering channel?

13:35 callen: Anderkent: I actually just got done hammering out a nice structure for core.async with functional tests that need to interact with "global" resources like queues and logging libraries.

13:35 worked fine for me.

13:35 Anderkent: lynaghk: using mutable state to represent side effects to the 'outside' world in tests seems totally fine.

13:35 well, gotta run

13:37 callen: it's not insanely problematic, but you can do better.

13:41 srruby: In project root I have /resources/fixtures/foo.txt How do I access foo.txt in my code ?

13:41 justin_smith: srruby: io/resource

13:41 what looks things up in the resource path

13:42 (slurp (io/resource "fixtures/foo.txt"))

13:42 the cool thing with io/resource is it even works if your code is inside a jar, without having to change anything

13:42 make that "if your resource is inside a jar with your code"

13:46 dnolen: lynaghk: your notes re: analyzer/compiler are a good start but very broad. would like be nice to get smaller actionable chunks. cleaning up closure.clj would be a good start. closure.clj is meant be consumed so solidifying things there would be great. As far as exposing analyzer.clj and compiler.clj I think we need some file above them that provides tooling

13:46 services.

13:46 lynaghk: dnolen: yeah, I'm definitely not done with the notes

13:47 hear you on the actionable chunks---already a few people are asking for some really big stuff

13:47 but I will try to arrange things so there are clear next steps

13:48 what do you think about putting public API fns in their own namespace (jonase's suggestion)

13:48 dnolen: lynaghk: yes this is what I meant when I said separate file.

13:48 bbloom: lynaghk: link to notes?

13:49 lynaghk: bbloom: https://github.com/lynaghk/clojurescript-compiler-proposal

13:49 bbloom: core.async does this w/ a public API file. i like that approach in general, even though it's a little verbose/annoying to "copy" functions over to the public namespace

13:49 lynaghk: dnolen: I don't know if I actually want/need separate analysis stuff. I think that info could be returned with a sucessful compile

13:50 i.e., a sucessful compile just returns a map {:namespaces [...] :js "actual-js-output" ...}

13:50 bbloom: i think we should focus on the compile API & keep the analyzer API private for now. the schema of the AST is much more important to spec out than the analyze API

13:50 lynaghk: I haven't thought through it all yet, though, hence the lack of concrete suggestions in the notes.

13:51 dnolen: lynaghk: these concerns will need to be kept separate, I'm not convinced you want to involve compile if you're getting a namespace dependency graph.

13:51 lynaghk: nor do you want the overhead of compile if you just want to locate all errors/warnings

13:52 lynaghk: dnolen: from the source, I thought all errors/warnings came from Google Closure

13:52 dnolen: lynaghk: analyzer warnings?

13:52 lynaghk: closure.clj just sets the flags for analyzer.clj

13:52 lynaghk: dnolen: maybe my grep skills failed me, but the only place I saw errors/warnings were Java interop calls

13:53 dnolen: lynaghk: no warnings come from many places in analyzer.clj

13:53 lynaghk: dnolen: separate sounds good to me; ideally there is some simple pipeline of analyze->emit->optimize or whatever that you can juggle yourself, or use an "easy" fn that does it for you.

13:53 dnolen: ah, cool.

13:54 I have to make some progress on my other yak shaves this morning, but I'll circle back to the cljs stuff this afternoon

13:56 dnolen: lynaghk: that should be the goal, re: pipeline, but it's going to take some work to get there.

13:57 lynaghk: dnolen: totes. I'm more than happy to dive in and do some of that work too---I just want to write out explicit goals and a plan first.

13:58 dnolen: bbloom: I agree AST aspects should be left alone, but I think errors/warnings/ns dependencies/pseudo-var facilities/ns queries in general all these we can sensibly expose.

13:58 bbloom: dnolen: probably

14:09 futile: Could ClojureScript get to the point of replacing Clojure for server-side web apps?

14:11 bbloom: futile: i mean it could, but why should it?

14:11 futile: faster start-up time :)

14:12 bbloom: futile: how often are you starting your servers? :-P

14:12 gfredericks: not having to deal with pesky exact arithmetic

14:12 futile: constantly. they'er always crashing

14:12 every 10 sec prolly

14:12 bbloom: gfredericks: math is for suckers

14:14 gfredericks: besides, don't everybody just use church numerals?

14:15 futile: never heard

14:15 bbloom: futile: google it

14:16 futile: thanks i just might

14:21 squidz: dnolen: do you know about the bug in clojurescript where sets aren't proper sets. calling (set [1 2 2]) will return #{1 2 2}

14:23 gfredericks: bbloom: just pastors afaik

14:25 dnolen: squidz: hrm, probably a unintended side effect of some optimizations we have in place, I check JIRA, feel free to make a ticket if not present

14:25 "I would check JIRA"

14:25 mihneadb: squidz: tried online at clojurescript.net and it works

14:26 dnolen: mihneadb: clojurescript.net is not a reliable resource, that's the CLJS-in-CLJS project

14:26 squidz: hm we tried earlier at himera, I assume that is the same site and it didnt work, let me try it again

14:26 bbloom: dnolen: can we get fogus/relevance to update clojurescript.net with a caveat about that? :-P

14:26 dnolen: squidz: I can confirm that it's broken

14:27 bbloom: fogus/relevance don't run that domain

14:27 bbloom: dnolen: well they created himera. somebody else just pointed a domain at it

14:27 dnolen: bbloom: no, it's a seperate thing entirely, it's a CLJS-in-CLJS thing

14:28 bbloom: dnolen: ooooh i just re-read the copyright: CLJS-IN-CLJS © 2013 JOEL MARTIN


14:28 mihneadb: dnolen: oh, ok

14:28 bbloom: dnolen: can we get joel to add a caveat? :-P

14:29 dnolen: squidz: feel free to file a bug

14:29 rurumate: Here's some 'basic' code that runs fine in clojure but crashes in clojurescript: https://www.refheap.com/18264

14:29 any ideas what's going on there?

14:29 jtoy: im trying to refactor my code by moving code in one namespace into another (im grouping all the time methods into one ns), I then :use that time ns from many other namespaces, I am getting errors now though such as "now_long already refers to: #'pusher.time/now_long in namespace: pusher.web.admin" can anyone help me understand what i am doing wrong?

14:30 squidz: dnolen:

14:30 `fogus: Only the "design" (i.e. pretty UI elements) are copy me and Relevance.

14:30 squidz: okay will do

14:30 gfredericks: jtoy: stale repl state?

14:31 jtoy: gfredericks: I dont think so, I am calling "lein repl" and it dies loading that

14:32 or can that be stale also?

14:32 gfredericks: shouldn't be

14:32 maybe `lein clean` just to be paranoid

14:33 dnolen: rurumate: need more context, what's the actual error that you see? Is this a compiled program? Is this evaluated in the REPL?

14:33 jtoy: gfredericks: nope, same error

14:33 clojurebot: excusez-moi

14:33 rurumate: dnolen: I'll make a github repo..

14:33 dnolen: rurumate: before you do that, more info please :)

14:34 rurumate: ok, yes maybe github repo is not so useful, because it may be the emacs settings's fault

14:35 so my inferior-lisp-program is "lein trampoline cljsbuild repl-listen"

14:35 the project looks exactly like the advanced example from lein-cljsbuild

14:36 adamt: Hi. What is the name of "->"? Google is being really unhelpful. :P

14:36 rurumate: First, I start a ring server on localhost:3000 with lein ring server-headless

14:36 futile: adamt: thread-first

14:37 justin_smith: also called thrush or arrow

14:37 rurumate: then I open src-cljs/example/print.cljs in emacs and do C-c -z to open the inferior-lisp buffer in lisp-mode

14:37 adamt: thanks guys.

14:37 justin_smith: symbolhound.com is cool for this stuff http://symbolhound.com/?q=-%3E+clojure

14:37 symbolhound searches for the weird programming glyphs that google etc. do not index

14:38 rurumate: In the inferior-lisp repl I write (ns example.print) and then (load-file "example/print.cljs")

14:38 (have to open localhost:3000/repl-demo or evaluation will hang)

14:38 dnolen: rurumate: but does this error happen if you just compile your program? and you still haven't said what the exception *is* :) stack overflow?

14:39 rurumate: oops, I meant (ns example.dice) and (load-file "example/dice.cljs")

14:39 ambrosebs_: bbloom: https://github.com/frenchy64/lein-typed

14:39 bbloom: ambrosebs_: yes! :-)

14:40 rurumate: dnolen: I don't know what the exception is because the stack trace (or whatever it is) is so long, it would take very long to the first line

14:40 bbloom: ambrosebs_: exciting. announce that bad boy :-)

14:40 ambrosebs_: bbloom: :)

14:40 eric_normand: very exciting

14:41 rurumate: ok anyway, so after the (load-file "example/dice.cljs") I run (cljs-ouch) and it crashes every time (after running for some seconds)

14:42 to run it in nrepl (normal clojure), I just make a soft link to the file from another project and open nrepl....

14:43 technomancy: ambrosebs_: why not collapse the two subcommands?

14:44 ambrosebs_: technomancy: I didn't give it much thought. Like what?

14:44 technomancy: ambrosebs_: like the test task; it'll run all the namespaces you give it as args, but if you don't give it any, it'll just figure it out for itself

14:45 (in this case it could be by looking at the project map, or scanning via bultitude or something)

14:45 bbloom: i say you should claim `lein type`

14:45 ambrosebs_: technomancy: ok thanks.

14:45 technomancy: looks handy though; very nice

14:46 ambrosebs_: bbloom: naww I like typed.

14:46 technomancy: thanks

14:46 rurumate: in https://www.refheap.com/18265 the function is written a bit shorter (shows the same behaviour and should be equivalent)

14:46 bbloom: ambrosebs_: i guess i could deal w/ one extra letter :-P

14:46 vijaykiran: is there a way I can tel leiningen to build stuff from different dir ?

14:46 technomancy: ambrosebs_: for bonus points you could emulate `lein compile` and accept regexes either on the cli or in the project map

14:46 ambrosebs_: bbloom: typed is so much cooler

14:46 technomancy: plus support :all

14:47 vijaykiran: just add to :source-paths

14:47 :source-paths ["src2"] or wahtever

14:47 vijaykiran: technomancy: sorry - I meant while not in the project dir

14:48 technomancy: oh you mean like looking for project.clj in something other than the current directory?

14:48 vijaykiran: it was because we have a project in which the clojure project is in a subdir of git repo - so we want to specify a sub dir

14:48 technomancy: yes

14:49 technomancy: alias lein-in="pushd $1 && lein $@; popd"

14:49 ambrosebs_: technomancy: ok. I should probably support that in core.typed, then call it from lein-typed.

14:49 vijaykiran: technomancy: :) thanks

14:49 technomancy: ambrosebs_: yeah, I'm a fan of making plugins as small as possible

14:50 ambrosebs_: in many cases you can get rid of plugins entirely and just have :aliases {"typed" ["run" "-m" "clojure.core.typed"]}

14:50 (but you can't do that if you need access to the project map)

14:51 you could get around that by using ns-level metadata instead of defproject keys, but then you have to load every ns before you can check a subset of them, which is slow

14:52 rurumate: dnolen: could you reproduce it?

14:53 ambrosebs_: technomancy: right. good to know.

14:55 gfredericks: bbloom: `lein type` should be reserved for the thing that infers types and adds them to your source

14:56 bbloom: gfredericks: `lein type infer` :-)

14:57 dnolen: rurumate: sorry can't look at it closely right now, perhaps someone else can.

14:58 ambrosebs_: FWIW I like showing the relation to Typed Racket with "typed".

14:59 Since that's where the awesomeness comes from.

14:59 rurumate: hmm yeah, someone should be of help here

14:59 dnolen: rurumate: or ask your question on the CLJS mailing list

14:59 rurumate: oh yeah, but where can I join it?

15:00 amalloy: gfredericks: lein do type infer, type check

15:01 rurumate: mailing list, or google group?

15:04 dnolen: rurumate: google group

15:09 noprompt: dnolen: is there a way to keep protocol extensions in clojurescript isolated to a namespace?

15:10 dnolen: it seems like when you extend a protocol in one ns all others are affected

15:11 :-(

15:11 bbloom: noprompt: nope

15:11 * noprompt has tears streaming down his face.

15:11 bbloom: noprompt: i needed that one time tho, so i made this project: https://github.com/brandonbloom/dispatch-map

15:11 noprompt: it's kinda experimental & doesn't have explicit cljs support, but it might be helpful to you

15:13 noprompt: bbloom: why does that happen?

15:13 bbloom: noprompt: protocol dispatch tables are global/mutable

15:13 noprompt: they have dynamic scope, just like vars

15:14 amalloy: bbloom: dynamic scope doesn't sound like a good way to describe protocol extensions at all

15:14 bbloom: amalloy: unbounded dynamic scope? :-P

15:15 amalloy: it's global and permanent

15:15 noprompt: bbloom: so what's the big difference from clj and cljs? why the bleed?

15:16 bbloom: noprompt: with respect to protocols? both have the same behavior

15:16 futile: Is it a bad idea to stick @(future (Thread/sleep 200)) inside a (while true ...) on the main thread?

15:16 callen: futile: it's a sign of a very bad design.

15:16 futile: Why?

15:16 clojurebot: futile: because you can't handle the truth!

15:16 noprompt: bbloom: really? cause that's not what it looks like from the repl.

15:17 amalloy: futile: @(future ...) is always a sign of lunacy

15:17 noprompt: it's the same

15:17 noprompt: i think i'm missing something here.

15:17 Apage43: futile: you probably want a ScheduledTheadPoolExectuor

15:18 futile: Oh.

15:18 aaelony: I'm using nrepl from emacs within screen on a remote server and am trying to forward x11. It doesn't work yet but I think I'm pretty close b/c it works from lein repl, just not from screen + emacs/nrepl yet. The error is "java.awt.HeadlessException: null" even though my project.clj contains :jvm-opts ["-Xmx2g" "-Djava.awt.headless=true"] … DISPLAY=:0 and my localbox from which I am doing ssh -Y remote-server-name is already xhos

15:18 Apage43: https://github.com/overtone/at-at is a convenient wrapper around that

15:18 aaelony: …. any ideas?

15:18 rurumate: dnolen: I posted in the group but now I can't find the post in the postings list.. does it normally take a while to show up?

15:20 noprompt: i create a protocol in `ns foo`. then in `ns bar` i `(require 'foo)` and extend the protocol to c.l.PersistentVector or whatever. then i switch to `ns baz` and try to call some function from the protocol and it fails because it can't resolve the symbol.

15:20 amalloy: aaelony: setting headless to true is disabling graphics entirely; i think you just want to leave it on, and x-forwarding will take care of sending it to the right place

15:20 noprompt: in cljs that's not the case. calling the function w/o requiring the protocol ns happily works.

15:21 wait. hang on.

15:21 aaelony: amalloy: ok, will try that but I put it in the project.clj only because it was complaining about it and was reading through this http://stackoverflow.com/questions/10165761/java-cant-connect-to-x11-window-server-using-localhost10-0-as-the-value-of-t

15:21 seancorfield: rurumate: first postings are moderated, I believe.

15:23 amalloy: hm. well, i confess i'm not very experienced with X forwaring, aaelony, it just seems like that would be a weird way for things to work

15:24 noprompt: oh geeze. nm. i see what's going on.

15:24 aaelony: amalloy: thanks, I'll tinker a bit more…

15:24 noprompt: so it seems to me like extending protocols to object can be a bad idea, no?

15:25 in cljs that is.

15:25 * noprompt needs more coffee.

15:26 llasram: aaelony: What's the value of DISPLAY w/in the emacs (and parent screen) process? After removing the extraneous headless JVM arg, that seems like the most likely thing to check

15:26 noprompt: or at least certain protocols seem like a bad idea. ILookup being one of them.

15:27 amalloy: noprompt: that does sound dangerous

15:27 noprompt: cause say you implement ILookup for object then you create a new type and you also want to implement ILookup for it, you're fucked.

15:27 amalloy: uhhhh, don't cljs protocols obey the inheritance tree just like jvm protocols?

15:27 dnolen: noprompt: that's how protocols work

15:28 noprompt: we might start issuing warnings about multiple implementations

15:29 bbloom: noprompt: you should only extend a protocol to an object if you own (logical-or the-protocol the-object)

15:29 or s/the-object/the-type/

15:30 amalloy: dnolen: really? as i understand the discussion, that's not how they work in jvm-clojure, and i didn't realize it was different

15:32 aaelony: llasram: in screen the value is :0 , not sure how to check the value within emacs

15:33 llasram: aaelony: Eval (getenv "DISPLAY")

15:34 M-: (getenv "DISPLAY") RET

15:34 aaelony: Probably is :0 too though, which would be the problem -- the `lein repl` launched by emacs will inherit that value, and thus not connect to the correct forwarded port

15:35 aaelony: llasram: confirmed that it is set to :0 in emacs as well

15:35 llasram: aaelony: You should be able to w/in emacs use `M-x setenv` to set DISPLAY to the correct value, then all should be good!

15:36 aaelony: llasram: I thought the correct value was :0 though…. or perhaps I can try `hostname`:0.0

15:36 llasram: aaelony: Usually it'll be something like `localhost:10` in a forwarded session. Check what it *actually* is in the forwarded session where things work

15:37 And then don't close the SSH session which is forwarding X :-)

15:38 aaelony: llasram: can I check the forwarded session from emacs? where is that exactly? thx

15:39 noprompt: bbloom: i think that's sound advice.

15:40 llasram: aaelony: You mean w/o launching `lein repl` and seeing if you get explosions? You can always `M-!` an random X program, like `xdpyinfo`

15:41 aaelony: llasram: hey, it worked!! within emacs did a (setenv "DISPLAY" "localhost:10") and voila!

15:41 noprompt: fwiw here's a gist of console macros for clojurescript https://gist.github.com/noprompt/6428301

15:42 aaelony: llasram: awesome thanks :)

15:42 llasram: aaelony: Glad to help

15:44 noprompt: i think the key with cljs is not fighting js.

15:45 rurumate: dnolen: posted it here: http://bit.ly/1dDPCpV

15:47 noprompt: i'm kind of surprised there isn't a clojurescript contrib or clojurescript.tools project for some of this shit. seems like every cljs project has some sort of console.log wrapper.

15:49 would it be of any benefit to someone if i just put these macros in a clojar? seems like that would make sense.

15:51 amalloy: noprompt: it doesn't really seem like those should be macros

15:52 noprompt: amalloy: not all of them, no.

15:52 amalloy: almost none of them

15:52 noprompt: amalloy: most of those take a variable number of arguments and you can't use apply.

15:53 amalloy: you can use apply, it's just a little less convenient

15:53 (.apply (.-log js/console) js/console args) looks right from a quick glance at https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Function/apply

15:54 noprompt: amalloy: oh yeah, i forgot about the context part.

16:01 robink: I have a small Java interop problem

16:01 When calling a method on a class instance (Rtf/rtf), I get the following exception: ClassCastException java.lang.String cannot be cast to [Ljava.lang.Object; user/eval1243 (form-init9112115781670751618.clj:1)

16:02 I know this is a question best asked in ##java, but I'm really flummoxed as to what I'm doing wrong.

16:06 danlentz: hello clojurers; I'm coming from a background in common-lisp and I was wondering if there was a clojure equivalent to "the idiot's guide to symbols and packages" which was a document I found very helpful at demystifying the basic issues when I was learning CL

16:07 callen: danlentz: http://www.infoq.com/presentations/Clojure-Namespaces-Vars-Symbols

16:07 danlentz: I think you'll find it very educative. I came from CL and found that talk extremely helpful.

16:07 scgilardi: robink: some argument you're sending needs to be an array of objects, but you're providing a string. is this a variable-arity function in java? you'll need to pass an explicit object array from Clojure.

16:07 danlentz: callen: thanks that looks good

16:08 robink: scgilardi: Lemme look at the source to see what it expects.

16:09 noprompt: amalloy: thanks for pointing that out.

16:09 bbloom: dnolen: writing code in continuation passing style is my least favorite thing ever

16:10 dnolen: and it doesn't even solve the fucking problem i have… i need a trampoline....

16:10 dnolen: bbloom: heh what are you doing?

16:10 bbloom: dnolen: CPS works for async calls b/c the call occurs in some dispatcher loop elsewhere

16:10 dnolen: i'm experimenting w/ the effect system stuff more

16:11 dnolen: bbloom: oh yeah, the trampoline is the host event loop

16:11 danlentz: is it bad style to expect something like (def rdf/type " "http://www.w3.org/1999/02/22-rdf-syntax-ns#type") to work? IE defining symbols in packages other than the "current"?

16:11 bbloom: dnolen: i have a working interpreter, but it stack overflows in a lot of cases

16:11 dnolen: b/c i'm doing some crazy stack hackery

16:11 dnolen: w/o tail calls, restartable exceptions, etc it's absurdly hard to code those things in to your own interpreter w/o extreme care and verbosity

16:12 robink: scgilardi: public static RtfTextPara p( Object... texts )

16:12 scgilardi: It wants an array? A list? A sequence?

16:12 amalloy: danlentz: it blatantly doesn't work, so i don't see how style is relevant

16:13 scgilardi: a java array. see clojure.core/into-array

16:14 (you'll probably want the 2 arg version to avoid making the array the same type as the first item in the seq you pass in)

16:15 danlentz: amalloy: yes I've seen that. I was just wondering if there was a succinct reason why it should not. sorry i probably phrased the question poorly

16:15 callen: danlentz: try to learn more before proceeding.

16:15 a book and that talk is a good place to start.

16:15 danlentz: :)

16:15 robink: scgilardi: 'k, thanks, will try

16:15 callen: danlentz: clojurebook.com

16:16 danlentz: k thanks; I will do that

16:16 SegFaultAX: Are ido-mode and org-mode minor modes?

16:17 robink: scgilardi: Doesn't throw an exception, but returns nil when I call .p with (into-array "My single string"). I think I may be hitting bugs in jRTF now. Thanks for your help with the Java end of things.

16:17 hiredman: org-mode is pretty major

16:17 SegFaultAX: Let me ask my real question: how does one quickly find a file in their project

16:18 Without typing the whole path

16:18 Like ctrl-p for vim

16:18 llasram: SegFaultAX: I use ido-mode + find-file-in-repository

16:18 SegFaultAX: (I'm trying to follow that tutorial posted earlier on HN for getting started in emacs. I'm a vim user)

16:20 llasram: Does that do fuzzy matching?

16:20 amalloy: SegFaultAX: you can turn on fuzzy matching for ido

16:20 llasram: SegFaultAX: You can configure ido to do various kind of fuzzy matching

16:20 SegFaultAX: I just do filename substrings myself, but there's other options

16:20 SegFaultAX: amalloy: How?

16:20 Or what's the best way for an emacs newb?

16:21 amalloy: SegFaultAX: i just turn on ido-enable-flex-matching

16:21 there may be other options

16:21 scgilardi: robink: you're welcome

16:21 SegFaultAX: amalloy: Is that M-x what you just typed in?

16:21 robink: scgilardi: and now it's fixed completely. Thanks very much :-)

16:21 * robink will someday learn Java

16:21 amalloy: M-x customize-variable RET ido-enable-flex-matching RET

16:21 scgilardi: sweet

16:22 danlentz: i'm glad to see how vibrant the clojure community t is -- an exciting difference from the sometimes echoing halls of CL. Thanks for the help, guys.

16:23 amalloy: honestly i don't think flex matching has provided me any additional benefit over ido-mode, but doesn't hurt to turn it on

16:23 dnolen: bbloom: so dead end? or you got another plan?

16:24 SegFaultAX: amalloy: So if I wanted to navigate to a deeply nested file, I still have to type all the intermediate dirs?

16:24 bbloom: dnolen: i'm gonna replace my Evaluable protocol's eval method with an extend-k method. nothing will do any actual work, instead it will take a machine & return a new machine with an extended continuation. will be slow as hell, but i'm fine with that for now :-P

16:25 amalloy: SegFaultAX: yes, though llasram's suggestion of find-file-in-repository may help, i dunno

16:25 SegFaultAX: amalloy: No that's fine for now.

16:25 One does not simply switch from vim to emacs...

16:27 gfredericks: clojurebot: org-mode is pretty major

16:27 clojurebot: Ok.

16:27 SegFaultAX: But is it technically a major mode?

16:28 callen: SegFaultAX: yes but it supports editing code blocks in their native major mode.

16:29 SegFaultAX: there's also outline-minor-mode that provides some of the org-mode look and feel in other major modes.

16:29 SegFaultAX: callen: So when that article says that only one major mode can be active, he's kinda sorta lying?

16:29 arohner: what was the name of the DSL for constructing regexes?

16:29 technomancy: SegFaultAX: find-file-in-project lets you jump straight to deeply-nested files with ido

16:30 SegFaultAX: technomancy: When I do M-x find-file-in<tab> I get no completions

16:30 callen: SegFaultAX: major-mode combinators are...you don't want to go there unless you're an Emacs wizard. Assume it's true.

16:30 technomancy: SegFaultAX: it's a third-party function

16:30 SegFaultAX: Oh!

16:30 callen: and just bucket org-mode's functionality as magic.

16:31 SegFaultAX: How do I install it? (emacs 24.3)

16:31 technomancy: http://marmalade-repo.org/packages/find-file-in-project

16:31 SegFaultAX: Thanks

16:31 technomancy: np

16:32 futile: I must prefer https://github.com/hoffstaetter/find-file-in-repository

16:32 SegFaultAX: Oh man, find-file-in-project is awesome.

16:32 futile: *much

16:32 \cc SegFaultAX

16:32 callen: SegFaultAX: just be prepared to tweak the file extensions variable.

16:32 and the project decls.

16:32 but yeah, ffip is nice.

16:33 futile: genehack: with find-file-in-repository you don't need to tweak those things callen is talking about

16:33 i mean SegFaultAX

16:33 dangit

16:33 * futile isn't IRCing well today

16:33 callen: futile: I need to investigate this. thanks.

16:34 futile: callen: the only time ffir has let me down is when I want to jump to a new file I haven't committed yet

16:34 callen: yeah that looks promising because @work uses hg. Tragically.

16:34 futile: potentially problematic but probably worth it anyway.

16:34 thanks for the heads up.

16:34 futile: yup

16:34 np

16:34 in melpa

16:36 SegFaultAX: technomancy: Starter kit is awesome! :)

16:36 callen: futile: meh, installed it myself. Works brilliantly, thanks.

16:36 futile: heh

16:36 technomancy: SegFaultAX: ehrm... it's okay.

16:36 SegFaultAX: technomancy: Well I don't know any better.

16:36 callen: technomancy: isn't it moderately out of date/unmaintained?

16:36 futile: I wrote my own emacs starter kit once

16:37 * futile really has to start making real progress on his Clojure IDE

16:37 technomancy: callen: more that it's The Wrong Thing

16:37 SegFaultAX: technomancy: Oh, what do you mean?

16:37 futile: Dang, I wish I didn't delete this: http://lists.gnu.org/archive/html/help-gnu-emacs/2013-04/msg00040.html

16:38 technomancy: lumping together unrelated functionality without any docs encourages cargo-culting without a deeper level of understanding

16:38 SegFaultAX: technomancy: That's exactly my argument against eg janus.

16:38 technomancy: https://github.com/technomancy/emacs-starter-kit/blob/v3/README.markdown <- SegFaultAX, callen

16:38 gfredericks: we need to encourage cargo-culting with a deeper level of understanding

16:38 SegFaultAX: gfredericks: Your talk is next in my queue. ;)

16:39 gfredericks: SegFaultAX: cool, let me know if it's any use

16:39 technomancy: applies to all "starter kits" including prelude, emacs-live, etc

16:39 callen: technomancy: yeah, I tend to agree.

16:40 TimMc: technomancy: Make one that self-destructs. "You have 30 days to grok this example setup before it wipes itself from your computer."

16:40 SegFaultAX: technomancy: Janus is particularly egregious in that it doesn't even function the way normal vim plugins are /supposed/ to function.

16:40 callen: TimMc: me gusta.

16:40 technomancy: TimMc: oh man that would be awesome

16:40 callen: it made more sense back before package.el was usable

16:40 callen: technomancy: sure.

16:40 technomancy: or you just do what I do and have an artisanally crafted Emacs setup.

16:41 I know exactly what's in the path because I meticulously accumulated and installed all the packages and dependencies myself :P

16:41 Brand0: emacs-live

16:41 technomancy: callen: that's the goal of ESK v3

16:41 callen: Brand0: is a bad idea.

16:41 technomancy: callen: a prose guide to encourage people to learn and experiment on their own

16:41 callen: technomancy: anybody using package.el would have considerably less work ahead of them than I put in.

16:41 technomancy: my dotfiles repo is based on ancient tarballs I would update from way back

16:41 SegFaultAX: The biggest heartache for me right now is the lack of hjkl

16:42 callen: and then rsync and install wherever I lived.

16:42 SegFaultAX: evil-mode?

16:42 SegFaultAX: I /really/ hate the arrow keys

16:42 callen: No.

16:42 callen: so use --- okay.

16:42 SegFaultAX: callen: I know there is no correct way to use emacs, but I'd like to have at least basic muscle memory in place before switching.

16:43 callen: SegFaultAX: fair enough.

16:44 SegFaultAX: Plus I feel it'll confuse me if both editors have pretty close but not identical mappings.

16:44 technomancy: uncanny valley

16:44 SegFaultAX: I'll start doing M-x in vim. :)

16:44 callen: SegFaultAX: well at least you're using a real editor now.

16:45 rasmusto: SegFaultAX: evil-mode isn't really that intrusive, so long as you know what default bindings it touches

16:45 SegFaultAX: rasmusto: But I don't know, that's the whole point of not switching until after I get comfortable with vanilla emacs.

16:45 rasmusto: SegFaultAX: I can't do arrow keys, so I use evil-mode

16:46 SegFaultAX: but yeah, I get your motivation

16:46 robink: If I'm doing interop with a Java library that suggests that people write Class.initializer.call.chain(somemethod("Value"), somemethod("Anothervalue"));, how would I correctly call "somemethod" when it's not an explicit method of the current instance (i.e. the last expression evaluated in doto), nor is it a method of its parent class?

16:46 callen: rasmusto: he's walking the golden path, leave him be :)

16:46 rasmusto: callen: M-x golden-path-major-mode

16:46 SegFaultAX: callen: :)

16:47 callen: today is a, "have a beer glass full of tea and whiskey" day because I'm sick. Also I'm writing Clojure. You win some, you lose some.

16:47 Getting weird looks from coworkers because a beer glass full of tea and whiskey just looks like a glass full of whiskey.

16:47 gfredericks: robink: what is it a method of? your code doesn't look like valid java anyhow

16:48 robink: gfredericks: It's paraphrased valid Java for a Java library.

16:48 hiredman: robink: they are most likely static methods and they expect you to do a static import

16:48 robink: gfredericks: and I probably need to know what somemethod is a method of before I even ask this question

16:48 hiredman: Ahh, OK, thanks :-)

16:48 hiredman: http://en.wikipedia.org/wiki/Static_import

16:49 robink: hiredman: Indeed, that's the first thing the documentation page has you do in Java. I wrongly assumed that (ns user (:import [com.tutego.jrtf Rtf])) would suffice.

16:49 callen: hiredman: how is there a whole wikipedia article about one language feature?

16:50 gfredericks: hiredman: yeah how did you let that happen

16:53 hiredman: gfredericks: huh?

16:54 gfredericks: hiredman: nm, just ineffective levity

17:00 llasram: "ineffective levity" would make a great name for a band/tumblr

17:02 sandbags: only 3 hits on Google... prime territory!

17:05 futile: Released 0.1.0 of my testing lib :)

17:05 https://github.com/sdegutis/nevermore

17:06 wooooo

17:08 SegFaultAX: How can I make all my splits the same width in emacs?

17:08 technomancy: SegFaultAX: M-x balance-windows

17:08 SegFaultAX: technomancy: Thanks!

17:09 technomancy: np. the #emacs channel is pretty good too.

17:09 rasmusto: there's always something interesting going on in #emacs

17:09 technomancy: though it's more recommended for overall hilarity and jocularity than on-topic advice

17:12 futile: i dunno, they didnt take too well to my trolling

17:20 callen: futile: don't troll #emacs, they're good people :)

17:20 * ucb joins #emacs

17:21 technomancy: also they get so many trolls that they have a strong immune system

17:21 futile: then i probably should have tried harder than saying "emacs sucks!" and /parting quick

17:22 to be fair though, emacs is a breath of fresh air compared to having healthy fingers

17:22 buh dum tshh!

17:22 rasmusto: futile: stop jk'ing

17:23 futile: ok

17:23 technomancy: http://technomancy.us/62

17:23 futile: ^

17:24 rasmusto: technomancy: man 6 vi

17:24 futile: technomancy: :( that only makes me feel inferior about my trolling skills

17:25 technomancy: you gotta take your game to the next level with that crowd

17:25 futile: you know us trolls are so insecure about our ability to make people feel insecure

17:25 technomancy: trolls within counter-trolls

17:25 maybe a twist ending

17:25 oh crap he's doing it

17:25 shoulda kept my mouth shut

17:26 <_>

17:26 oops

17:26 >_<

17:26 rasmusto: technomancy: i prefer the disappointed/sad eyes in this case

17:33 futile: that wasnt very fun

17:33 technomancy: you need to operate in stages

17:34 where up front it seems completely reasonable, and as people dig deeper and deeper new levels of insanity present themselves

17:34 while attempting to maintain plausibility through the whole thing

17:35 * danielglauser says "bah" to plausibility

17:36 futile: but i was doing that

17:37 technomancy: too implausible too soon

17:37 needs to be more gradual

17:38 * ucb sees technomancy is well versed in the dark arts of the trolls

17:38 callen: technomancy: nice :)

17:40 technomancy: I spend a lot of time on IRC

17:41 it is an art

17:44 futile: technomancy: wat? its totally plausible

17:46 technomancy: no, this one is better but you'd have better luck parting and rejoining with a different nick

17:47 futile: hmm maybe

17:48 technomancy: no, theres a whole history here you're not seeing

17:48 technomancy: im a computer collector and i know my stuff, thats why i can write a better emacs that works efficiently on old hardware

17:48 technomancy: ah I see; it's part of a master plan coming together

17:48 more than meets the eye

17:49 * ucb suspects a two-way trolling going on

17:49 futile: ucb: i can only hope

17:49 ucb: don't reel me in man, I'm not here

17:50 technomancy: «like racket, except "done right"» <- now you're cookin'

17:50 hyPiRion: technomancy: haha

17:51 «Like Clojure, but with a focus on immutability»

17:54 futile: :'(

17:55 technomancy: its a long term project

17:58 bbloom: is it just me, or does everybody else's usage of deftype/defrecord, etc seem to follow a sine curve?

17:58 futile: I've.. never used it.

17:59 technomancy: do_not_want.jpg

17:59 bbloom: i tend to write a lot of code that looks kinda like product types by stuffing stuff in to a vector [:like this with args]

17:59 then i write multimethods with dispatch function first

18:00 but occasionally, i need to interface w/ a protocol somewhere & that kinda sucks

18:00 hyPiRion: I just use multimethods and get over with it

18:01 futile: There's one multimethod in my code and I'm regretting it and looking for a way to get rid of it.

18:01 Just because these 2 things have a similar property doesn't mean they can be grouped together :/

18:02 ToxicFrog: multimethods \o/

18:03 bbloom: the biggest issue i have is when you kinda have two-phase things

18:04 like if you have some data structure & then want to "compile" that in to some other shape, then run your program against the compiled structure

18:04 if both the source and destination structures are just trees of maps/vectors, then you have to be careful to have strict phase separation

18:05 like you can't have a phase 2 thing inside your phase 1 tree, unless you add some kinda of wrapper [:pre-compiled phase-2-stuff-here]

18:05 or you have to have totally disjoint sets of keywords for that 0th vector position

18:06 hiredman: bbloom: macro expansion

18:06 the output of a phase should be valid input for any phase

18:07 bbloom: hiredman: that's not realistic if the phases have different features. that works for "expand" or "simplify" phases, but not for "translate"

18:08 hiredman: why not?

18:08 bbloom: b/c the output of phase 2 might be totally nonsensical as input to phase 1

18:08 hiredman: well, that is what I am saying, don't do that

18:09 bbloom: lol, yeah, i realize you're saying that: i'm saying that's not realistic. phase 1 might be macro expand but phase 2 might be translate to some language which doesn't have macros, but has some other thing that phase 1 doesn't understand

18:10 hiredman: I am not saying literally use macros, I am saying the process can be modeled like macro expansion

18:12 bbloom: hiredman: i understood that. my point is that given two schemas A and B, you can't necessarily rely on the fact that B is a subset of A, which is the case with macro expansion

18:13 hiredman: in my case, i have two phases and 3 schemas. the relationship between schemas A, B, and C are defined by transforms 1 and 2. the process is not circular nor does any part iterate to a fixed point, like a macro expander

18:15 futile: technomancy: besides, who says all that stuff wasnt true? who says im trolling?

18:15 hiredman: bbloom: why not? you are basically writing an interpreter/compiler with 3 phases, why not do them as an expander

18:16 mgaare: futile: what are the system specs for your new editor? I'm looking for something I can run on my Tandy 1100HD

18:16 callen: mgaare: lol

18:16 futile: mgaare: yes.

18:16 bbloom: hiredman: macros are interpreted by implicit expansion and iterated to a fixed point. my data must be explicitly transformed, which also precludes fixed point iteration

18:16 futile: mgaare: my new editor will be much more efficient therefore it requires a retina MBP

18:16 technomancy: futile: yeah, that one had some nice touches

18:17 the hare-brained "I know I'm right" scheme implementor schtick has legs

18:17 futile: technomancy: you're only saying that because you havent seen my implementation. if you saw it youd agree.

18:17 technomancy: if you want to join the venture as a profit-sharing LLC then i can show you

18:18 technomancy: but i require a minimum 20+hours a week and you get 35% profits after first 12 months

18:18 hiredman: bbloom: it just means instead of a single transform you need a transform and a predicate to determine if the transform is valid to be applied to a given tree

18:18 * futile sighs

18:18 technomancy: futile: where do I sign the NDA?

18:18 MisterSinister: Hi everyone! I thought this would be a good place to ask: I wanna check if a string contains a matched number of parentheses. I know I can do this with loop-recur, but I was wondering if there was a way to do it with the Clojure sequence stuff that didn't involve loop-recur. Could someone help me out?

18:18 futile: technomancy: youll have to fly to my office. does tomorrow work?

18:19 technomancy: also pack enough things, theres no time to lose adn we'll need to get started tomorrow so youll be away for a while.

18:19 justin_smith: MisterSinister: this is a 4clojure puzzle I just did the other day!

18:19 technomancy: futile: can you squirt it to my zune?

18:19 MisterSinister: justin_smith: OK. How did you do it?

18:19 justin_smith: loop

18:19 hah

18:19 MisterSinister: Figures.

18:19 hiredman: technomancy: no, he'll mail you a flier you can scan with your cuecat

18:19 futile: technomancy: im getting the feeling you arent taking this business proposal very seriously. im having second thoughts about hiring you on.

18:19 MisterSinister: That's what I'm using, but I was wondering if there was something less ugly.

18:19 * futile sighs

18:20 justin_smith: MisterSinister: reduce should be able to do it

18:20 * futile cries defeatedly "what have i become!?"

18:20 justin_smith: now I am thinking of translating...

18:20 MisterSinister: Actually, that's a *brilliant* idea.

18:20 Let me just try it now.

18:20 technomancy: hiredman: had to hit up wikipedia for that one

18:21 edw: I am utterly perplexed by the following Java-ism, and I have no idea how to interop with it. Could someone help me out? Given a DbxAccountInfo instance, how do I use Reader? http://bit.ly/15qOpdB

18:22 amalloy: DbxAccountInfo/Reader

18:22 it's a global

18:23 hiredman: technomancy: they were great

18:23 futile: technomancy: just because you dont trust my expertise and experience in silicon valley doesnt mean a thing. ive been around the block son i know my stuff. but anyway sounds like you have other more lucrative opportunities (were it possible) so good luck to your enddavors

18:23 * futile writes some Datomic

18:23 justin_smith: MisterSinister: the trick is immediately returning false if you have too many close tokens without opens

18:24 MisterSinister: Yeah, that was pretty much what I was thinking. I'm just trying to code it right now.

18:24 But thanks for the suggestion - I never even *considered* reduce, for some strange reason.

18:24 mgaare: can't really do that in the reduce though can you?

18:24 MisterSinister: I've only been working with Clojure for a year, and I come from a Java background.

18:24 mgaare: Yes you can.

18:24 Have reduce return an integer.

18:25 I think it can be done, anyway.

18:25 mgaare: MisterSinister: I think regardless of what you return in your reduce function, reduce is gonna keep plodding on through the rest of the input collection

18:25 MisterSinister: mgaare: Have some kind of 'dummy' value that basically ignores all subsequent input and returns itself.

18:25 False would be a good candidate.

18:27 mgaare: yes, I agree that you do some stuff to handle the situation, but it seems somewhat wasteful in the face of a string like this: ")abc123 ..." followed by 2 billion characters :D

18:31 justin_smith: there is "reduction

18:31 "

18:31 in clojure 1.5+

18:32 jkkramer: ,(doc reduced)

18:32 clojurebot: "([x]); Wraps x in a way such that a reduce will terminate with the value x"

18:32 justin_smith: immediately jumps out of the reduce

18:33 MisterSinister: Ah, that would be easier.

18:37 OK, got an answer.

18:37 But not using reduced.

18:37 justin_smith: why not reduced?

18:37 MisterSinister: Just wanted to make sure my original code worked. Now I wanna try and do it with reduced.

18:37 But you are right - reduce *can* do it with the right function.

18:38 Is there an example of using reduced somewhere?

18:38 I've never actually used it before, and I learn best from examples.

18:39 (Also, why the hell didn't I come here before?)

18:39 dissipate__: what's the best way to validate an email address in clojure?

18:39 justin_smith: MisterSinister: my kind of ugly version https://www.refheap.com/18275

18:39 MisterSinister: dissipate_: What do you mean 'validate'?

18:40 justin_smith: the only true way to validate an email address is to send mail and not fail

18:40 dissipate__: MisterSinister: that it conforms to the RFCs for a well formed address

18:40 justin_smith: email is weird

18:40 MisterSinister: justin_smith:Yours is more thorough than mine. Here's what I have: https://gist.github.com/anonymous/6430320

18:40 dissipate_: Regular expression?

18:40 Isn't that how pretty much everyone does it?

18:41 dissipate__: justin_smith: no, aren't there parsers?

18:41 justin_smith: have you ever seen the actual rfc for valid email? it is fucking insane

18:41 qz_: heya, is pmap doing anything super-special compared to normal map? i hava jdbc throwing 'java.sql.SQLException: No suitable driver found' when running with pmap and its all fine with map

18:41 justin_smith: http://en.wikipedia.org/wiki/Email_address#Syntax

18:41 dissipate__: justin_smith: i have. believe me, i don't want to code that.

18:41 justin_smith: http://en.wikipedia.org/wiki/Email_address#Valid_email_addresses

18:41 dissipate__: justin_smith: what's the best way in clojure?

18:42 justin_smith: good luck with a re that matches the good ones and not the bad ones

18:42 MisterSinister: justin_smith: Point taken.

18:42 justin_smith: send an email, if it goes to recipient, address is good

18:42 "!#$%&'*+-/=?^_`{}|~@example.org" is a valid address

18:43 dissipate__: justin_smith: that's not good to send an email to every address. you can get black listed as a spammer. you know that right?

18:43 ToxicFrog: dissipate__: don't. Just don't. If you try to valid the email addresses as well formed, you will reject valid addresses and then your users will be unhappy and send you angry emails from addresses your software claims are invalid.

18:43 mgaare: I think google made a java library for this dissipate__

18:43 MisterSinister: Now to figure out how the hell reduced works...

18:43 dissipate__: mgaare: right, but is there a 'clojure' way of doing it, or does everyone just call the java function?

18:44 MisterSinister: But in any case, thanks for the suggestion - never would have figured it.

18:44 justin_smith: MisterSinister: (reduced value)

18:44 inside the body of the function called by reduce

18:44 MisterSinister: Oh, is that all?

18:44 OK... let me try something.

18:45 justin_smith: one sec, checking, my main clojure is 1.4 for lib versions

18:45 *lib reasons

18:45 MisterSinister: I use the latest, because I just have Leiningen build me stuff.

18:45 mgaare: dissipate__: SOP in clojure is to hop on a mature java library :D

18:45 justin_smith: MisterSinister: some libs don't work with 1.5 yet, ones I use

18:46 dissipate__: mgaare: SOP?

18:46 MisterSinister: justin_smith: I guess we do rather different code. I'm a Master's student, and my code is all algorithm implementations.

18:46 dissipate_: Standard Operating Procedure.

18:46 justin_smith: MisterSinister: backend web dev

18:46 MisterSinister: justin_smith: That would make sense.

18:46 dissipate__: MisterSinister: i see. that can potentially generate side effects though.

18:48 justin_smith: MisterSinister: oh, it is not reduction, it is reduced

18:48 MisterSinister: Reduced gives the intermediate steps, right?

18:48 justin_smith: nope

18:48 MisterSinister: No, wait, that's reductions.

18:48 Derp.

18:48 justin_smith: short circuits if called

18:48 ends the loop

18:48 ,(reduce (fn [arg _] (reduced arg)) (range))

18:48 clojurebot: 0

18:49 justin_smith: yay, reduce on an infinite list

18:49 MisterSinister: So that just halts on 0?

18:49 dissipate__: justin_smith: is that a lazy reduce?

18:50 MisterSinister: OK, thanks for that. That'll give me what I need to work with.

18:50 justin_smith: dissipate__ it just short circuits

18:51 bails out of the loop

18:51 coventry: Is there an existing tool which will identify which subforms of a fully macroexpanded form will not get evaluated? (E.g., the contents of quoted lists or the bound symbols in binding forms)

18:51 dissipate__: justin_smith: isn't that a feature, not a bug?

18:52 justin_smith: yup

18:52 that is why short circuit was a bad choice of words

18:52 dissipate__: coventry: sounds like a macro could do that

18:52 MisterSinister: I'm still so noob at macros.

18:52 But then again, I come from a Java background, and have only been using Clojure for a year.

18:53 And even then, I only really do it for algorithm implementations.

18:53 justin_smith: MisterSinister: we should follow each other on 4clojure, we would probably both learn a few things

18:53 I am noisesmith on there

18:53 MisterSinister: I'm mistersinister, I *think*. Haven't logged in for a while, though.

18:53 Let me just check.

18:54 dissipate__: justin_smith: you haven't solved all of the problems on 4clojure?

18:54 coventry: dissipate__: It's not obvious how a macro would help here.

18:54 justin_smith: not yet, only started a month ago

18:54 dissipate__: you have?

18:54 MisterSinister: justin_smith: mrsinister, as it turns out.

18:54 coventry: I think I can repurpose riddley.walk for this.

18:54 dissipate__: justin_smith: hellll no. i barely started on there. some of those problems only have like 50 people who have solved it.

18:55 MisterSinister: dissipate_: Some of those are really interesting.

18:55 I liked the DFA one.

18:55 (Since I have to do stuff related to automata theory)

18:55 dissipate__: coventry: you have a macro that takes in the macro expanded form and detect the subforms that are quoted etc.

18:56 justin_smith: why make it a macro? just walk the tree, and find calls to quote

18:56 MisterSinister: justin_smith: You're gonna laugh. Look at your 4clojure account settings, and check the code snippet in the formatting box....

18:56 justin_smith: the form is just a list - or would you get the form as arg, not macroexpanded?

18:57 dissipate__: justin_smith: what if the argument is a macro?

18:57 coventry: justin_smith: It's more than just calls to quote. The symbol "a" in (let [a 1] (foo)) does not get evaluated, either.

18:58 justin_smith: ahh, yeah

18:58 MisterSinister: what am I looking for? oh, the default syntax, lol

18:59 dissipate__: coventry: does what i said make sense?

18:59 MisterSinister: Anyways, thanks for your help. I will *definitely* be around more.

19:00 dissipate__: justin_smith: are you taking into account the fact that macro expansion order is the reverse of function call order?

19:01 justin_smith: dissipate__ not at all, but what about writing the function to take the fully expanded form as its input? any reason not to do it that way?

19:02 because the problem doesn't seem like one of creating syntax, but of investigating some form

19:03 coventry: Sorry dissipate__, you're not making much sense to me. Macros have no obvious role in the problem I've described. I do want this function in order to make a macro, though.

19:05 justin_smith: I wish it was easier to browse a followed person's answers on 4clojure

19:07 SegFaultAX: justin_smith: Submit a patch!

Logging service provided by n01se.net