#clojure logs

2014-03-19

00:00ddellacostanoprompt: okay
00:01ddellacostanoprompt: sorry to keep you waiting. So yeah, one of things I think would be useful would be to have a lookup function or functions for routes
00:07ddellacosta$seen seangrove
00:07lazybotseangrove was last seen quitting 4 hours and 50 minutes ago.
00:08ddellacostahmm, how do I send messages to folks?
00:08amalloy$help mail
00:08lazybotamalloy: Send somebody a message. Takes a nickname and a message to send. Will alert the person with a notice.
00:08ddellacostaamalloy: thanks
00:09nopromptddellacosta: i think by having IRouteValue and adding the "raw" route as a third element in the vector is good enough for now w/o breaking the current API
00:10ddellacostanoprompt: okay, gotcha--so, basically, leave the locate-route modifications roughly as is, but move the route-spec fn to its own IRouteValue protocol? Seems reasonable
00:29ddellacostanoprompt: wondering what I should call the function that returns the actual route value...I have "route-spec" now, but maybe something like "get-original" or "original-route" or..."route-value?"
00:29nopromptddellacosta: right.
00:29ddellacostanoprompt: the one inside the IRouteValue protocol I mean
00:30noprompt(defprotocol IRouteValue (route-value [route] "Return the original route value"))
00:32nopromptddellacosta: basically, i'm trying to make sure we avoid adding too much functionality at one.
00:32nopromptddellacosta: if that's enough to help you solve your problem while not assuming too much i think that's good.
00:33nopromptddellacosta: by creating a separate protocol and returning the "raw" route it's a win for now and the future.
00:33ddellacostanoprompt: absolutely, and I definitely am on the same page with that--my goal with this is to "disturb" the codebase as little as possible.
00:33ddellacostanoprompt: alright, will make those modifications and push
00:33nopromptddellacosta: lol did you see the shit i pushed yesterday?!
00:33ddellacostanoprompt: no, which? Will check it out
00:33nopromptddellacosta: i added like 100 lines just so we could serialize/deserialize vectors/maps etc. for query strings.
00:34nopromptlol, it doesn't break anything and no one will notice but it's there.
00:34dissipatenoprompt, what is there?
00:35ddellacostanoprompt: oh, yeah, I did see that now that you mentioned it. Nice stuff. :-)
00:35ddellacostadissipate: ^
00:36nopromptddellacosta: somehow we've ended up in this space where query params turns out to be useful.
00:37ddellacostanoprompt: you know, it's interesting how the use-cases shift when you are doing client-side routing actually. Although maybe you weren't being tongue-in-cheek...
00:38nopromptddellacosta: it's a weird nasty place.
00:38ddellacostanoprompt: hahaha
00:38nopromptthe client sucks. but it's getting better all the time.
00:38ddellacostanoprompt: "the client..." web clients in general?
00:39nopromptddellacosta: i just meant the front end. it's a mixed bag.
00:39ddellacostanoprompt: definitely agreed on both counts if that's what you mean.
00:39ddellacostanoprompt: yeah. Absolutely. But having done this since around 1998 I can say definitively we are both better off and worse off, depending on how you look at it.
00:40nopromptddellacosta: considering that we might've had a chance at scheme i really don't know.
00:40ddellacostanoprompt: there are things you can do now that were inconceivable ten years ago. And the compatibility story has gotten a *lot* better, all my complaints about IE aside. However, the amount of complexity involved is astounding, when you take web development as a whole.
00:41ddellacostanoprompt: you mean, as opposed to what JS turned out to be?
00:41nopromptddellacosta: well, legend has it, that javascript was supposed to be a scheme like language but netscape changed it at the last minute.
00:42dissipatenoprompt, and we have been stuck with it ever since. :(
00:42nopromptyou know, because java.
00:42danielszmulewiczHas Datomic memory requirements changed? I'm trying to upgrade to the latest version (0.9.4609), but I get an out of memory error. I have 1GB of memory on my VPS where datomic (0.8.something) worked flawlessly.
00:42ddellacostanoprompt: right, I remember that B. Eich was big into scheme, wasn't he...and Self?
00:42ddellacostanoprompt: well, good thing he was able to include at least some parts of it, conceptually
00:43dissipateddellacosta, yes, and a guy named Douglas Crockford tried to convince us that there are actually 'good' parts of javascript
00:43ddellacostadissipate: well, when you have to use a language, there have to be ways to cope
00:43nopromptddellacosta: from what i've read. i've never met the man though. he could be a serial rapist serving time in prison and a robotic stunt double programmed to speak/write/tweet on his behalf is filling his role as a human until his release.
00:44nopromptdissipate: yeah but he gave us the term "dog balls" (function () {}()) <-- dog balls
00:44dissipateddellacosta, and there in lies the problem. javascript should have never existed. it should all be byte code, and no i am not talking about the JVM
00:45ddellacostahahaha
00:45ddellacostayou guys
00:45nopromptdissipate: yes and it would have been "cool" if money never existed to create classes and social problems but hey, what can you do?
00:45dissipatenoprompt, that's hawt. :O
00:46nopromptlol
00:46dissipatenoprompt, well, i suppose the USSR tried that. but even they still had money.
00:47nopromptddellacosta: i've only been programming for around 4.5 years so i can't speak to the horrors prior to my arrival on the scene.
00:47nopromptcss is pretty horrible i'll say that.
00:47ddellacostanoprompt: I remember Netscape 4
00:47ddellacostanoprompt: and DHTML
00:47ddellacostanoprompt: I barely escaped with my life
00:47noprompti remember it too, but probably not the way others did.
00:48dissipatenoprompt, the horrors continue
00:50nopromptddellacosta: one day i'm gonna have enough money saved up to go to japan. :-/
00:51ddellacostanoprompt: well, if I'm here you can crash at my place. :-)
00:51nopromptddellacosta: i *really* wanna shop for vinyl therer. ;_; it's too much on ebay.
00:51ddellacostanoprompt: oh, seriously, the Japanese are nuts about that stuff
00:51ddellacostanoprompt: like in an awesome/scaryw ay
00:51nopromptddellacosta: those guys sell me a record for like 20 bux in yen and then it get's here with a price tag in yen for half the price.
00:51ddellacosta*scary way
00:52nopromptddellacosta: there's so much good 60s/70s pop from japan.
00:52noprompt<3 it
00:52dissipatehow is the clojure scene in japan?
00:53noprompti only open iterm to spawn another instance of emacs
00:59ddellacostadissipate: not much of one
01:00dissipateddellacosta, well, i guess japan has bigger problems than programming languages. their entire race is pretty much dying out.
01:00jph-dissipate, slow population growth, not dying out
01:01dissipatejph-, slow as in negative?
01:01noprompt"race" lol
01:01jph-dissipate, im not sure what the latest figures are, but it could be in negatives atm
01:01dissipatejph-, it is indeed negative
01:02ddellacostanoprompt: I'm a bit confused as to how to do this, as the only place I can get ahold of the original route is in compile-route
01:25jph-im looking at some clojure 1.4.0 code
01:25jph-and i see (defn somefunc [_] ...)
01:26jph-what does _ mean? or has that been superceded since 1.4?
01:28SegFaultAXjph-: If that's exactly what was written, it's probably just a placeholder for the arg list.
01:29SegFaultAXOr rather, the parameter list.
01:29jph-so like
01:29jph-(defn f [& args] ...) equivalent?
01:29jph-this is the exact line: (defn get-iso [c _] (:iso-code c))
01:30SegFaultAXNo. [& args] is variadic (it collects all unbound args into a single list)
01:30jph-i've not encountered _ before so i'm not sure how it's used
01:30SegFaultAXSo [a b c & rest] binds the first three arguments to parameters a b and c, then everything after that to args.
01:31SegFaultAX_ isn't meaningful in any way, it's universally used as the "I don't care about this value" name.
01:31jph-oh
01:31jph-got it
01:31jph-devnull of parameteres
01:32SegFaultAXIf you saw a function whose parameter list was literally [_], that makes no sense at all.
01:32jph-yep
01:32jph-itd be (fn [] ...)
01:32SegFaultAXRight. And the fn would be side-effecting.
01:33jph-just not sure what has changed between clojure 1.4 and 1.5
01:33jph-whether stuff i've looked at is deprecated or not
01:56amalloySegFaultAX: why would a function whose parameter list is [_] make no sense?
01:56amalloyit's perfectly reasonable to write something like (defn always-3 [_] 3) for passing to map
01:56amalloylike, of course you can use constantly, but defining a named function is fine too
01:56SegFaultAXMaybe if constantly didn't exist.
01:57SegFaultAXWell ok, it makes sense in a very limited context I suppose.
02:00SegFaultAXamalloy: Are you saying it's common to have functions that take a single argument which is never actually used?
02:00amalloyno, i would expect it to be more common to use constantly. but to say that it doesn't make sense at all? that's very different from uncommon
02:02SegFaultAXI mean a nullary function that is purely side-effecting is fairly common. But a unary function that never references its argument?
02:06xuserI have seen (let [x (fn) _ (println x) x (some other fn)]...
02:07SegFaultAXWell that's strange, why put it in the let at all? Let forms have implicit do-blocks.
02:07SegFaultAXOh rebinding it, yea.
02:16amalloySegFaultAX: it's a unary function because it's being passed to something else that expects a unary function
02:16amalloyyou wouldn't define it that way if you never passed it around
02:17xuseramalloy: how long have you being doing clojure?
02:17amalloyfor like...4 years?
02:17amalloyish
02:19xuserold school ;)
03:09seangrove,(let [x (atom {}) y (atom {})] (swap! x assoc :y y))
03:09clojurebot{:y #<Atom@118712b: {}>}
03:09seangrove,(let [x (atom {}) y (atom {})] (swap! x assoc :y y) (swap! y assoc :x x)
03:09clojurebot#<RuntimeException java.lang.RuntimeException: EOF while reading>
03:09seangrove,(let [x (atom {}) y (atom {})] (swap! x assoc :y y) (swap! y assoc :x x))
03:09clojurebot{:x #<Atom@135371: {:y #<Atom@cb3966: {:x #<Atom@135371: {:y #<Atom@cb3966: {:x #<Atom@135371: #>}>}>}>}>}
03:10seangroveI feel like I pulled a hiredman
03:10petehuntwhat did i just see
03:11petehuntmy emoticons are confusing me :P sec
03:11seangroveHeh, x => y => x => y...
03:12seangrovealso...
03:12petehuntso it worked
03:12petehuntor are they pointing to the wrong versions of x and y
03:12seangrove,(let [a [(atom nil)]] (reset! (first a) a))
03:12petehuntor am i not making any sense
03:12clojurebot[#<Atom@45d316: [#<Atom@45d316: [#<Atom@45d316: [#<Atom@45d316: [#<Atom@45d316: #>]>]>]>]>]
03:13seangroveSeems like clojure allows it, it just sensibly stops printing the structure after a bit
03:13seangroveHadn't really come across this before
03:14petehuntseangrove: so how would you model a mutual friendship in an om app
03:14petehuntwhat would your state atom look like
03:15seangrove{:users [{:id :pete :name "Sam"}{:id :aaron :name "Aarom}] :friendships [[:pete :aaron]]} ?
03:16seangrovewoops, [[:sam :aaron]]
03:17petehuntso you would refer to them by id
03:17seangroveOr if I needed fast lookups {:users [{:id :sam :name "Sam" :friends [:aaron]}{:id :aaron :name "Aarom} :friends [:sam] :friendships [[:sam :aaron]]}
03:17petehuntgot it
03:17seangroveYeah, I think so
03:17seangroveJust guessing off the top of my head though, and it's way past my bedtime
03:18seangroveI'm off, best of luck out there ;)
03:50sm0kewhen i do a lein with-profiles repl, i get 'nrepl not in classpath' error?
03:50sm0kewhy is that?
03:51sm0kelein with-profiles myprofile repl
03:59sm0ke+myprofile
04:50borkdudeIs there a way to get all possible keyword paths from a nested map (as in json-like thing), like: {:a {:b "d" :c "f"} :b nil} -> [[:a :b] [:a :c] [:b]] ?
05:11szymanowskihello, is there a way to add a keyval to an array-map and be sure that it doesn't become a hash-map?
05:17mpenetszymanowski: I don't think so. You can always use a LinkedHashMap instead if that's absolutely necessary
05:18szymanowskithank you, i don't know LinkedHashMap, i will look at it
05:18clgvszymanowski: no. it will automatically change if a certain threshold is reached
05:19clgvszymanowski: you can use a sorted-map though if you require a certain order defined by a comparison predicate
05:21szymanowskiyes i've tried with sorted-map but it doesn't really fit my needs very well, maybe https://github.com/amalloy/ordered
05:21clgvszymanowski: ah you want to have insertion order
05:21szymanowskiyes
05:21clgvwell then go ahead and use amalloy's lib
05:22szymanowskiyes it looks nice
05:33jph-and the penny drops for defrecord/defprotocol
05:33jph-this stuff is sweet
05:43mskoudTrying to use eval (know its evil) using a ring webserver. When run in the repl it ok and in the correct namespace, but when run through webserver the eval evaluates in the clojure.core namespace. How do i avoid that?
05:47clgvmskoud: despite you probably dont want to hear this. you are very likely doing something wrong by using "eval"
05:48clgvmskoud: you can fix it if you put an "(in-ns 'my.desired.target.ns)" in the code you pass to `eval`
05:48hyPiRionyeah, a `(do (in-ns 'my-ns) ~body) should work
05:49clgvmskoud: could you please report here when that part of the code backfired at you? ;)
05:50mskoudim trying to interpolate a string which can contain sexprs
05:51clgvmust be a huge advantage compared to templating otherwise I'd use the latter
05:52rstandywhat libraries do people use to implement authentication in clojure web applications?
05:53hyPiRionfriend
05:54jph-rstandy, im just using noir session
05:55rstandyhyperboreean, jph-: thanks
05:55rstandywill check that
05:56rstandyjph-: does noire already manage authentication then?
05:56rstandynoir, I mean
05:56jph-if you look at a basic luminus template (lein new luminus blah +site) it does the utmost basics
05:56rstandyjph-: ah ok
05:56jph-the session stuff is relatively mature
05:57jph-but it's up to you to do the registration and login verification
05:57jph-you could drop in various hashing algorithms, or maybe something fancier
05:57rstandyjph-: ok, got it
05:58rstandyI would like to use something to extends for implementing authentication over LDAP or via oauth
05:58clgvrstandy: I used "friend"
05:58jph-i'd start with friend if you need something more full-featured
05:58rstandyclgv, hyPiRion: do you use it in production?
05:58clgvrstandy: for webform-based authentication it did not need much customization to get it running
05:59hyPiRionrstandy: no, not in production.
05:59hyPiRionWell, unless you mean my private websites-production.
05:59rstandyhyperboreean: ok, thanks
05:59clgvrstandy: since I am working at a university "use in production" likely does not have the same meaning as for you. but yeah, it is in production
06:00rstandyclgv: do you have a certain number of people using it daily?
06:01rstandyclgv: is the login page accessibile from the web? Just to see an real example of friend auth
06:01clgvrstandy: since it is no classical website. no. 2-3 people use it when the application is running
06:02rstandyclgv: ok, thanks for the info
06:03rstandyoh, nice, there is a friend-demo at herokuapp.com
06:04rstandywill try it
06:04clgvyeah right, there are demos for several authentication workflows
06:06rstandyclgv: really interesting library, from a very smart guy, I see (cemerick)
06:09clgvrstandy: yeah. though some people complained in IRC that it would be to complicated to get started with it. but I do not agree with that
06:20rstandyclgv: will definitely take a look at friend (which is also intriguing for its clever name)
06:24myguidingstarhi all, is there any way to call a function from project's dev dependencies from a leiningen plugin?
06:25xsynmyguidingstar: look at https://github.com/zcaudate/vinyasa
06:26xsynor you can use the full path
06:26myguidingstarlet's see
06:26xsynhttp.async.client/function
06:26xsynas an example
06:34mskoudclgv: works in repl (eval `(do (clojure.core/in-ns 'cms.core) (+ 1 3))) but returns "java.lang.IllegalStateException: Can't change/establish root binding of: *ns* with set" when run through ring server.
07:04honzadoes anyone have a post with how to set up piggieback + vim-fireplace with the clojurescript repl?
07:14clgvmskoud: (binding [*ns* 'cms.core] ...) could be an alternative
07:15clgvmskoud: but you see that you are already shooting yourself in the foot, right?
07:16jph-how do i case the class of a var? (case (class var) java.math.BigDecimal "yay!" "nope") doesnt seem to work
07:17clgvjph-: you cant literally with case
07:17jph-what's the right way to do it?
07:18clgvjph-: it is the same issue as with static constants
07:18jph-i know i can do (instance? ...)
07:18jph-but that's not case
07:18clgvjph-: yeah, (cond (instance? java.math.BigDecimal v) ...)
07:18jph-oh yeh i'd forgotten about cond
07:19clgvjph-: you could also use the helper macro that was suggested for static constants ( I think that was on the mailing list lately)
07:21clgvjph-: depending on whether that dispatch happens in a hotspot you might want the case behaviour instead of cond which expands to nested ifs
07:43mskoudclgv: yes maybe. trying to make some content able to pull info from some data in the code.
08:28voldymanwhats the best method of getting xml data from a url?
08:29jcromartiedepends on a lot of factors
08:29voldymantried slurp but it converts '<' to &lt; etc.
08:29jcromartieslurp does not do that
08:29voldymanit does for me.
08:29jcromartie,(slurp "http://www.w3schools.com/xml/note.xml&quot;)
08:29clojurebot#<SecurityException java.lang.SecurityException: denied>
08:30jcromartiewell anyway
08:30jcromartieit doesn't
08:30voldymanjcromartie: you are right, only half of the tags are escaped
08:30jcromartiecan you share the URL to the XML document?
08:31voldymanhttps://itunes.apple.com/us/rss/topsongs/limit=10/explicit=true/xml
08:32voldymanoh fish, solved the problem, i think
08:34voldyman(clojure.data.xml/parse "<a><b>a</b><b>c</b></a>")
08:34voldyman,(clojure.data.xml/parse "<a><b>a</b><b>c</b></a>")
08:34clojurebot#<ClassNotFoundException java.lang.ClassNotFoundException: clojure.data.xml>
08:36voldymanerror in clojure.data.xml/parse https://www.refheap.com/61821
08:41hyPiRion,(require 'clojure.data.xml)
08:41clojurebot#<FileNotFoundException java.io.FileNotFoundException: Could not locate clojure/data/xml__init.class or clojure/data/xml.clj on classpath: >
08:50jstewI think that clojurebot doesn't like it because it's an external lib
08:51hyPiRionyeah
08:51hyPiRionnot bundled with vanilla clojure
10:10Bronsa,(defrecord x [a])
10:10clojurebotsandbox.x
10:10Bronsa,(x. 1 nil {:a 2})
10:10clojurebot#sandbox.x{:a 1, :a 2}
10:10Bronsavoila`
10:11jcromartieWhat do most of y'all use for blogging platforms? Is Tumblr ever a good choice for code-related blogs? I don't see many technical posts there.
10:12jcromartieI should probably host it myself :) I have no excuse
10:12edbondjcromartie, I vote for github pages
10:12jcromartieedbond: yeah, not a bad idea
10:14jcromartierockin'
10:19jstewTumblr would be awesome for a tech related blog. Make animated gifs of nrepl.
11:04luxbockI have two protocols that implement largely the same functionality
11:04luxbockat first I wrote them as normal functions for both cases, but then I decided a protocol would simplify things
11:04luxbockbut now I'm wondering how I should organize my namespace around this new change
11:05luxbockerr. I have just one protocol that is implemented by two different records I should say
11:06luxbockis it standard practice to throw all of that stuff in a separate my-proj.impl.X namespace and then just build an outward facing API from those bits later?
11:07mpenetluxbock: it's not unusual yes
11:07luxbockalright, guess that's what I'll do then
11:07luxbockglad I found clj-refactor.el
11:17shep-werkluxbock: thanks for mentioning that, now I'm going to use it :-)
11:36jcromartielet's say I want to do x y and z
11:36jcromartieand I want to stop and return the first case where some pred returns a truthy value for any of those
11:36jcromartieI say "do" because these are side-effecty functions
11:37jcromartiethey all return a map of either {:success …} or {:error ...}
11:37jcromartiecondp?
11:37jcromartieno
11:40dnolen_(some #(%) [x y z])
11:40jcromartieah ha, yes, and wrap up the side effects in fns
11:40jcromartiethanks
11:41jcromartieexcept I really want first filter
11:41jcromartiebut yes
11:42jcromartieI was *about* to write a macro :)
11:42jcromartielike, filter-forms
11:45cemerickhyPiRion: are you using double-check post-test.check-merge, or an older SNAPSHOT?
11:48jcromartiednolen_: how stupid is this? https://gist.github.com/anonymous/9644556
11:50dnolen_jcromartie: I don't really have an opinion, looks fine if that's what you want to do
11:52dnolen_jcromartie: though if I think about it not sure why you can't just use `or`
11:52jcromartiegood call
11:59dsayusing shoreleave http-rpc for remote call. response is returned.
11:59dsayperform reset! in callback function on a defined atom but when use atom it doesn’t have new value. what need to do to set var with remote response?
12:01clgvI have a seldom event S and very frequent events F that operate on a reference. it seems that the transaction of S never succeed while F events are running. after I stop the F events another event S succeeds. how can I fix that?
12:02augustlso, I extracted jdk8 to a folder. How can I make "lein" use it? Tried setting JAVA_HOME to $HOME/local/jdk1.8.0 to no avail.
12:03clgvaugustl: linux/unix?
12:03augustljust found LEIN_JAVA_CMD :)
12:03augustlclgv: yeah
12:03clgvaugustl: google for jdk and "update-alternatives"
12:03clgvaugustl: if you want to use it for more then just one try
12:05shep-werkclgv: As a Gentoo user, I feel I should be indignant :-)
12:05rasmustogentoo -O3 erryday
12:05augustlclgv: I don't want to change my system java :)
12:05augustlLEIN_JAVA_CMD=$HOME/local/jdk1.8.0/bin/java seems to have worked
12:05shep-werkrasmusto: oh, are we going to get in a CFLAGS war? Oh yeah!
12:06jjl`anyone got a good example of as-> usage? it's very hard to google for
12:06rasmustoshep-werk: those days are over for me, I'm in arch now
12:07clgvshep-werk: stop using gentoo to save our planet ;) :P
12:07shep-werkrasmusto: well, we are still above the Ubuntu rabble, right? /s
12:07shep-werkclgv: Why would I want to turn off my space heater? It's cold here!
12:08clgvshep-werk: there are heaters with a better efficiency :P
12:08shep-werkmy heater has the side effect of producing nice terminal text
12:08rasmusto,(-> 3 inc dec (as-> b [b (- b)]))
12:08clojurebot[3 -3]
12:09rasmustojjl`: does that clarify it?
12:09jjl`rasmusto: not really
12:09rasmusto(doc as->)
12:09clojurebot"([expr name & forms]); Binds name to expr, evaluates the first form in the lexical context of that binding, then binds name to that result, repeating for each successive form, returning the result of the last form."
12:10rasmusto"expr" is what gets passed in with the threading macro
12:10hyPiRioncemerick: I'm using 5.6-SNAPSHOT. (5.7-SNAPSHOT weren't out when I tried to compile)
12:10clgvjjl`: as-> is most useful when you have different postions where to insert the result of the previous calculation
12:10rasmustoname is a name you pick, and forms are expressions that use that named var: [b (- b)] for example
12:10jcromartiehmm… don't rely on lazy operations, e.g. map, for fine-grained control over side effects
12:11jjl`clgv: *nod* i've just done a macroexpand in repl to try and make sense of it. but i'm not completely sure i get it
12:12rasmusto,(macroexpand `(-> 3 inc dec (as-> b [b (- b)])))
12:12clojurebot(let* [sandbox/b (clojure.core/dec (clojure.core/inc 3)) sandbox/b [sandbox/b (clojure.core/- sandbox/b)]] sandbox/b)
12:13clgv,(as-> 10 x (range x) (reduce + x) (/ x 10))
12:13clojurebot9/2
12:13jjl`i think i get it
12:13hyPiRion(-> a (b c) (d e f) g (h)) is the same as (h (g (d (b a c) e f)))
12:14cbpjjl`: http://blog.fogus.me/2009/09/04/understanding-the-clojure-macro/
12:15jjl`i don't have a problem with -> (which i find very useful)
12:15cbpah sorry then
12:15jjl`it's just as-> that i'm struggling with. but i think i've got a grasp
12:16cemerickhyPiRion: OK. If you have any troubles with it (aside from the namespace renaming :-/), let me know. Probably going to cut a 0.5.7 release this week.
12:16cemerick(first "real" release)
12:17rasmustojjl`: hyPiRion's example shows what as-> can do by itself, mine was more showing that -> and as-> can work together if you need a named binding partway through the threading macro
12:17rasmustojjl`: er s/hyPiRion/clgv
12:17hyPiRioncemerick: will do – no worries
12:18jjl`rasmusto: yeah, i think your example solves a problem ive had down the line, where one of the things that needed threading needed threading to another point in the sexp
12:18jjl`naturally i rewrote it as a let and suffered the ugliness
12:18cbpjjl`: the point of as-> is to remove nesting -> and ->>. So you can define where the placeholder is instead of depending on first or last position
12:19jjl`*nod*
12:21honzadoes anyone have a post with how to set up piggieback + vim-fireplace with the clojurescript repl?
12:30jcromartieis there a better way to write this side-effecty loop thing? https://gist.github.com/anonymous/a51f8d487fbdeca53cbe
12:31bbloomjcromartie: doseq?
12:31jcromartiedoseq can't short circuit
12:31jcromartiethis is pure bikeshedding :)
12:31bbloomah, how about reduced ?
12:31jcromartieslash golf
12:31rasmusto:while isn't short-circuity?
12:31bbloom,(doc doseq)
12:31clojurebot"([seq-exprs & body]); Repeatedly executes body (presumably for side-effects) with bindings and filtering as provided by \"for\". Does not retain the head of the sequence. Returns nil."
12:32bbloom(doc for)
12:32clojurebot"([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 ...], :while test, :when te
12:32jcromartiehm
12:32jcromartieok
12:32bbloomyeah, i think let+while will do what you want
12:32bbloomrasmusto: thanks, i always forget doseq does taht
12:33jcromartieno, doseq returns nil
12:33jcromartieI want to return the first value for which :error is truthy
12:33bbloomjcromartie: use reduced
12:33jcromartiewithout evaluating any more
12:33jcromartiechunked seqs are right out
12:33jcromartiehm
12:34bbloom(reduce (fn [_ task] (let [result (task)] (when (:error result) (reduced result))) nil tasks)
12:34jcromartiewoah, an escape from reduce?
12:34bbloom(doc reduced)
12:34clojurebot"([x]); Wraps x in a way such that a reduce will terminate with the value x"
12:34jcromartiewhen did that become a thing?
12:34bbloom(doc reduced?)
12:34clojurebot"([x]); Returns true if x is the result of a call to reduced"
12:34bbloom,(meta #'reduced)
12:34clojurebot{:ns #<Namespace clojure.core>, :name reduced, :arglists ([x]), :column 1, :added "1.5", ...}
12:34bbloom1.5 :-)
12:34Raynesjcromartie: Clojure has a changelog. You should poke around in there every once in a while :P
12:34RaynesIt's exciting.
12:35clgvafter the releases is sufficient ;)
12:36jcromartieRaynes: yes, thanks
12:36jcromartie:| I've just been cruising since 1.2
12:36cbpjcromartie: you can use some
12:37jcromartiecbp: are you sure some won't chunk?
12:37jcromartieyeah, some *looks* safe
12:37jcromartiebut it's not explicit
12:38jcromartiesome appears to be the winner :)
12:38jcromartie (some #(let [result (%)] (and (:error result) result)) tasks)
12:38cbpjcromartie: it uses first & next, no chunked-cons so i dont see why it should
12:39RaynesAnd you can easily find out if it will
12:39RaynesThrow some side effects at it.
12:39cbp,(some #(do (print %) (when (:error %) %)) [1 2 3 {:error 4} 5])
12:39clojurebot123{:error 4}{:error 4}
12:40jcromartiebut that's not an explicit guarantee, just an implementation detail
12:40augustlis there a way to set java-cmd in a leiningen project without hardcoding it into the project.clj?
12:41cbpsome is supposed to short circuit so i dont see any reason for it to do any more work than it should by chunking
12:41clgvaugustl: the question contradicts itself
12:41technomancyaugustl: might be able to set it in .leinrc
12:41augustltechnomancy: trying to make leiningen use java 8 extracted to a folder, so I don't have to install it as my system java to play around with it :)
12:42technomancyaugustl: why not just put it on your $PATH?
12:42augustltechnomancy: that's all leiningen needs?
12:42Raynesjcromartie: If you're concerned about that, you're probably going to need to get Rich to put it in writing that it'll never change, or copy the source of some so that you know it'll never change. :P
12:42Pate_any Clojurists from South Africa?
12:42technomancyaugustl: sure
12:43augustlsetting PATH worked fine, great :)
12:43rasmustofamous last words
12:46augustlbooyah https://gist.github.com/augustl/9645871
12:46augustlthe beauty of JS, easily accessible right from Clojure ;)
12:49technomancyhaha
12:49technomancynice
12:49sdegutisYeah, I was thinking of how they should have named the Java utility to run scripts "java-script".
12:50augustlsdegutis: haha, a missed opportunity
12:50sdegutisThey named it "jrunscript" :/
12:50austinhHow can I test that a value is a MapEntry in Clojurescript?
12:50augustlthere's a bin named jjs though :)
12:51augustlaustinh: isa?
12:51jjl`'beauty of js'. sorry, got me giggling
12:52jjl`i'm amused by the idea of running clojurescript on the jvm though
12:52augustlwill attempt to make it easy to create single page web apps with fb react and render initial page from the server, without much extra work
12:52augustland without the need to run a separate node process for that
12:53augustljjl`: full circle :) What's the use case?
12:53tbaldridgeIt'll be interesting to see how that whole thing works out in relation to Graal and Truffle. Last I heard the JS Truffle VM is quite a bit faster than nashorn
12:53jjl`augustl: oh i don't have a good use case, i'm just amused :)
12:54austinhaugustl: Thank you.
12:54jjl`augustl: i'm daft enough to have tried porting perl to the jvm so amusement from craziness comes easily
12:54augustlFUD time.. I remember reading somewhere that v8 is optimized for crashing. After all, if a chrome tab crashes, just reload, no big deal. So comparing that to nashorm might be interesting.
12:55augustljjl`: perlj.am would be the domain name for that project
12:55jjl`php is certainly optimised for short runtimes (memory leaks etc.) which is actually a valid design decision if you know youre scripts are supposed to execute in a second or so
12:56jjl`i'm pretty sure nashorn is optimised for long runtimes. that's the only way they'll get the full benefit of hotspot
12:56augustlyeah, seens like nashorn is oracle saying "we're good at doing dynamic languages now"
12:56jjl`actually i think it's their way of saying "yeah, okay, rhino is a bit crap"
12:56technomancyaugustl: nashorn is "see, invokedynamic isn't just for jruby!"
12:57augustl:D
12:57augustljjl`: isn't rhino a mozilla project though?
12:57jjl`because jython uses it as well? :)
12:57jjl`yes, rhino is mozilla. but it also means there was no great jvm js implementation
12:57jjl`i think they're just hopping on the bandwagon more than anything
12:58jjl`"oh yeah, javascript is cool. we've always thought it. look here! we wrote one!"
12:58jjl`i think it'll get remarkably interesting once clojurescript is self-hosting
12:59augustlthere's also a node.js implementation for nashorn btw
12:59augustlwhich uses libuv, the cool part of node
12:59jjl`the other interesting thing is vert.x
13:00jjl`http://vertx.io/
13:00tbaldridgeAnd then Truffle just goes off the deep and and says "let's do a tracing JIT on the JVM"
13:00tbaldridge*deep end
13:00augustlhttps://avatar-js.java.net/
13:00tbaldridgehttp://lafo.ssw.uni-linz.ac.at/papers/2014_CGO_OneVMToRuleThemAll.pdf
13:00augustlvertx is a completely separate implementation of the event loop
13:00augustlavatar is just a wrapper around the very same library that node uses internally
13:01augustlnot sure which is a better idea.. Would make sense to do a node.js implementation on top of vert.x too
13:01jjl`that would certainly help get people ported over
13:04dnolen_jjl`: nashorn is not optimized for long runtimes, I've been following along since very relevant for Clojure(Script) narrative. They seems very interested start up fast, optimize fast - like the other JS engines.
13:04jjl`interesting
13:05dnolen_tbaldridge: pretty sure that isn't true w/ respect to Truffle / Nashorn
13:05dnolen_tbaldridge: invokeDynamic rewritten for Nashorn far as I know
13:05jjl`i think the day is fast approaching that i'll have to give up programming and become a farmer. when every tech stack has javascript
13:06dnolen_tbaldridge: and Nashorn is now as fast as SpiderMonkey and w/in shooting distance of JSC/V8
13:06jjl`it can't be long until someone writes a build system in javascript designed for building java, that takes the form of a DSL
13:06hiptobecubicIt's really a shame that javascript is such an abomination
13:07austinhaugustl: Actually, are you sure about using isa? to test MapEntry in cljs? I can't get it to work.
13:07augustlaustinh: hmm, not sure what a MapEntry is
13:09lockshiptobecubic: ur just jelly
13:15dnolen_austinh: there is no concrete MapEntry type in CLJS, just the IMapEntry protocol
13:16dnolen_austinh: when seq'ing maps you just a get a seq of vectors, and vectors satisfy IMapEntry
13:16dnolen_can test IMapEntry with (satisfies? IMapEntry foo)
13:16austinhdnolen_: Thanks!
13:16tbaldridgednolen_: that could be, the talk I was thinking of was both biased (presented by a lead Truffle researcher) and older (~1yo)
13:17dnolen_tbaldridge: yeah Nashorn was a dog a year ago
13:25seangroveNashorn definitely seems like ti could open up some very cool possibilities
13:55jstewAnyone know if I can run code after a ring response completes? (using compojure).
13:57jstewI generate some temp files, and want to clean them up.
13:57technomancyjstew: middleware can do that
13:59jstewtechnomancy: If I remove the file in middleware, won't it be gone by the time I try to serve it as the response?
13:59jjl`you misunderstand middleware
13:59jjl`your function receives the next function in the chain and you call it
13:59jstewindeed I may :)
13:59jjl`so you can do things both before and after
13:59amalloyjstew: are you trying to serve the temp files themselves as the response?
13:59jstewamalloy: Correct.
14:00jjl`oh, like sendfile() or something?
14:00jjl`which plugin are you using to send it?
14:00amalloyso he probably can't (straightforwardly) clean them up in a middleware - ring needs to be able to see the files in order to serve them, after his handler/middleware stack is done
14:00jjl`because it could just be a case of ordering your middleware if it's one that will just slurp the file and pass the content back
14:01amalloyjjl`: he doesn't need a plugin, really - ring can accept java.io.File as the :body
14:01amalloyand slurping it isn't much good if it's too big to fit in ram
14:01jstewThat's what I am doing. Serving the file directly and setting content-Disposition in the headers
14:02jjl`amalloy: in that case, it's a bigger problem than it first appears :)
14:02amalloyjstew: in most (all?) modern operating systems, you can delete a file while you have it open, and handles to it will stay valid
14:02amalloyso you can open an InputStream on the file, then delete it, then pipe that stream to ring
14:02jstewAhh... Yes, that will work. Thank you! Forgot about that.
14:02amalloy(ring is happy to accept streams)
14:02jjl`this only works of course if you haven't taken a flock()
14:03amalloyjava probably doesn't even let you
14:03jjl`hah
14:03amalloyright, it doesn't. since not every OS in the world supports that
14:04jjl`this is, incidentally, why perl's core file handling stuff is awful. it *does* support VMS
14:05`szx(into [] lazyseq) vs (vec lazyseq)? surprisingly, google didn't have the answer
14:06amalloy`szx: amazingly, there's no easy answer. vec seems like it *should* be right, and i'd use it because it's most readable, but i think into/[] is actually a bit faster
14:07`szxamalloy: alright, so vec it is till i run into performance issues
14:07amalloy`szx: and when you do run into performance issues, there will be better places to fix them :)
14:08jcromartieinto is definitely faster
14:09jcromartieIMHO into is a bit of an underrated gem of the collections interface
14:12cbpinto is faster because it uses transients
14:13stuartsierraaustinh, augustl: remember `isa?` compares 2 classes. `instance?` asks if an object is of a particular class.
14:15amalloyjcromartie, cbp: into is *usually* faster. it is definitely not the case that it's always faster
14:16austinhstuartsierra: Thanks!
14:16cbpamalloy: I imagine into gets faster the more items there are
14:17amalloyfor example, consider (let [a (into-array (range 30))] (vec v))
14:17amalloyvec has optimizations for array inputs
14:17amalloyinto has to seq over the array
14:17cbpah
14:18amalloy(in the example above is about 10 times faster than into)
14:19amalloyin practice, into will "always" be faster, but it just doesn't really matter
14:19amalloyi suggest using vec, because it's more specialized, and eventually someone will get around to implementing the same transient optimizations for it that work with into, as well as the other vector-specific ones it already has
14:21technomancyyeah, imo into makes most sense when you're pouring into something that's not empty
14:22technomancyyou use it to pour into {} too, but only because there's nothing like vec for maps for whatever reason
14:23Bronsatechnomancy: my guess is simply because `map` was already taken
14:23cbpran out of names :-D
14:25rasmusto,array-map
14:25clojurebot#<core$array_map clojure.core$array_map@1e9bfd3>
14:26technomancyyeah, but you have to apply it
14:26rasmustooh yeah, how is array vs hash map picked?
14:27jjl`apply is my usual frustration with ->
14:27technomancyjjl`: (partial apply f) =)
14:27technomancydon't actually do that
14:27jjl`quite
14:28jjl`come to think of it, i'm not sure why i haven't written a wrapper that switches the arguments
14:28cbprasmusto: I believe the cutoff is around 8 items
14:28jjl`that would solve it
14:29rasmustocbp: okay, so nothing to do with the types of keys used or anything
14:29cbprasmusto: no I don't think so
14:33AverellIs recur a kludge or motivated by no TCO on the JVM? Or am i paranoid?
14:33bbloom~recur
14:33clojurebotCool story bro.
14:33bbloom~tco
14:33clojurebotyes please
14:33bbloomlol
14:33bbloomAverell: this has been discussed many times here
14:33TimMcAverell: Paranoid? Who's out to get you?
14:33Averellany faq?
14:34Averellby natural suspicion
14:34Averellmy*
14:34bbloomAverell: in short, TCO is useful for many problems, but far from critical b/c you can always use a trampoline
14:34bbloomAverell: recur is tail RECURSION optimization, which is different than general TCO
14:35tbaldridgeAverell: TCO isn't supported on the JVM....so there that, but also recur covers almost everything so I don't see much of a problem
14:35Averellyes, but lets say there was, would recur still exist?
14:35amalloytechnomancy: at one point i did (def ap (partial partial apply)), to make it easier to squeeze apply forms into -> chains
14:36bbloomAverell: if the JVM supported proper tail calls, it's likely that clojure would have still needed something like recur, since clojure was simultaneously developed for the CLR, which also doesn't have general TCO
14:36justin_smithit's nice to have something that throws an error if not in the tail position
14:36tbaldridgeprobably for backwards compatibility. But also I think recur is really nice since it fails to work if its used in a non tail call position
14:36amalloyi don't remember if i ever actually used it, though - it looks knida awkward
14:36bbloomAverell: nor does javascript, for the clojurescript backend
14:36tbaldridgebbloom: sure it does, just not on x86-64....or x86....one of those, not sure
14:36bbloomAverell: so yes, host constraints led to the addition of the "recur" form, but it's still useful in much the same was as static type checking or runtime assertions are useful
14:37technomancyAverell: also: most uses of tco in scheme are better served by laziness in clojure
14:37bbloomtbaldridge: the CLR *can* do TCO, but doesn't promise it
14:37amalloyi imagine if we did have general tail calls we'd have something like (tail f x args), meaning "act like (f x args), but throw an exception if you can't do this without using stack space"
14:38amalloyor rather, don't compile if you can't do this
14:39bbloomamalloy: and that's practically exactly what i do in my interpreter: https://github.com/brandonbloom/eclj/blob/03bbe44dfb355930ff341b742b3b74c78325ca5d/src/eclj/core.clj#L583-L586
14:39augustlanyone here happen to know how you provide your own classes to a jdk8 nashorn runtime? :)
14:39bbloomamalloy: i implement normal recursion with the y-combinator, but i implement recur as an effect that enforces tail position on the continuation
14:40cbphmm, if I have some manner of (zipmap (keys m) (vals m)) I would have to rewrite that for clojure 1.6?
14:41jcromartiecbp: why? aren't keys and vals consistent?
14:41bbloomtbaldridge: clarifying: the CLR supports explicit tail calls, but the JIT may or may not perform tail call OPTIMIZATION for non-tail calls. the JVM supports neither explicit nor optimized tail calls
14:41jcromartiehttp://dev.clojure.org/jira/browse/CLJ-1302
14:41jcromartiethis is in 1.6
14:42bbloomtbaldridge: or i guess not for "non-tail calls", i mean for implicit tail calls. ie normal calls in tail position
14:42bbloombig difference as far as debuggers are concerned...
14:42Averellwhy is that apparently so much harder than detecting tail position?
14:42rasmusto(doc keys)
14:43clojurebot"([map]); Returns a sequence of the map's keys."
14:43cbpjcromartie: there were some hashing changes and in that ticket Stuart Sierra says you should not rely on it
14:43bbloomAverell: reality is more complex than the lambda calculus? :-)
14:43Averelli suppose :)
14:43bbloomAverell: exception handling, especially finally blocks, for example
14:43jcromartie"The absence of this property in the docs is correct. You should not rely on this."
14:43jcromartie(other stuart)
14:44cbper
14:44cbpyes other stuart
14:44cbp:-P
14:44bbloomAverell: the comp sci community genuinely didn't understand the nature of exception handling until the last few years
14:44jcromartiebut rich hickey says "keys order == vals order == seq order"
14:44tbaldridgejcromartie: cbp: "keys order == vals order == seq order"
14:44jcromartiei.e. /thread
14:44cbpOh but at the end Rich says that yeah
14:44amalloyyeah, i'm amazed to hear that from stuart
14:44cbp*joy*
14:44jcromartieWHAT AN IDIOT, GOD, PFFFFT
14:45amalloybbloom: does the CS community understand it now?
14:45stuartsierraI remember this discussion now. Stuart Holloway was incorrect. The order of keys and vals is the same.
14:46bbloomamalloy: much better than they did, that's for sure
14:48bbloomAverell: question answered? happy to provide further references
14:52dnolen_Averell: the reason Clojure and ClojureScript don't offer TCO is very simple - it makes interop problematic.
14:53Averellno, i'm good. thanks :)
14:53Averellif you have any links to better understand exception handling, that sounded interesting.
14:55bbloomAverell: i gave a talk on algebraic effects on monday night, it should be on youtube later this week. follow @papers_we_love on twitter. some background materials are linked to from here: https://github.com/papers-we-love/papers-we-love/issues/9
14:55bbloomAverell: in short, exceptions are now best understood in terms of delimited continuations
14:56boreHi guys. Just a quick one for a clojure newbie. How do I replace the last character of the String most efficiently?
14:57boredo I need to dip into java?
14:57technomancycan't you just use lasts?
14:57technomancylast
14:58maxthoursie(apply str (butlast some-string))
14:58maxthoursiewouldn't say it's efficient
14:58technomancyoh, misread
14:58cbpIs there an alternative to compiling protocol buffers from clojure than lein-protobuf?
14:58cbpMaybe I should do it manually..
14:59bbloom(doc re-replace)
14:59clojurebotCool story bro.
14:59maxthoursiebore: (clojure.string/replace "foo" #"o$" "b")
14:59bbloomah, d'oh not re-replace
14:59bbloombore: yeah what maxthoursie said
15:00jcromartiecbp: I'd think your protocol buffers should be a separate project
15:01cbpjcromartie: That's a good idea. But separate from the need to compile them
15:02borewell what maxthoursie said sounds a bit inefficient and I'll need to call str twice. Once with apply to get string back and then once to add the replacement character
15:02boreotherwise makes sense
15:03maxthoursiebore: the second one
15:03justin_smithmatching on #".$" should be fast, strings in the jvm are counted
15:03maxthoursiebore: use clojure.string/replace
15:03boreSo far I have (str (.substring foo 0 (dec (count foo))) bar)
15:04boreaha OK that sounds more like it
15:04borethanks a lot
15:05maxthoursiebore: if you want it faster i guess you should store it in a mutable way so you can just replace the character directly
15:05maxthoursiebore: but if you can aviod that -> cleaner code
15:05maxthoursiestrings are the only thing that java got right (wrt immutability)
15:06boreno I think copying into byte buffer would make things worse - I do not intend to reuse the base string much
15:06borebut thanks for the idea
15:06boreI'll go with regex solution
15:06boreit strikes a good balance
15:07maxthoursiefails on the 'aviod regexes when you can' guildline though :)
15:09justin_smithI guess you could use a StringBuilder or something if you wanted to super optimize it
15:10justin_smithhttps://www.refheap.com/61951 .substring is a little faster than the re solution
15:12justin_smithhttps://www.refheap.com/61951 updated to show the def of input
15:13Averellis count walking the full string?
15:13justin_smithno, strings are counted
15:13justin_smiththey store their size
15:14Averelloh that's what that meant. duh.
15:14gtrakcount uses seq functions, pretty sure
15:15gtrakso it doesn't matter if strings are counted
15:15justin_smithoh, so you want .length
15:15gtrakeat the cost of the reflection warning :-)
15:16justin_smiththe book "clojure high performance programming" claims count is O(1) on counted collections
15:16gtrakaha, actually I see a special case for CharSequence
15:16pyrtsagtrak: count delegates to RT/count on the JVM: https://github.com/clojure/clojure/blob/master/src/jvm/clojure/lang/RT.java#L528-L558
15:16jcromartieclojure.core/count is optimized for CharSequence
15:16jcromartieoh yeah
15:16gtrakso count should be fine
15:16jcromartie:)
15:17jcromartiehow many people were just on that file
15:17gtrakit's almost as if they thought of that
15:17justin_smithgtrak: according to this book, it is O(1) on list, hashmap, arraymap, vector, queue, treemap
15:17justin_smithand if I am reading that source right, it agrees
15:18gtrakerr.. I think it could be wrong for list
15:18clojurebotexcusez-moi
15:18gtrakI remember reading it delegating to the rest, if that's a cons then you've got problems
15:18gtrakbut in practice it's probably negligible
15:18Averellhehe. so at least it works for very short lists.
15:19pyrtsacount is O(n) for lists. Unless there's a tail that implements Counted. Then it's O(n_head).
15:20gtrakthe class of the head is not a testament to the rest of it
15:20pyrtsa:)
15:21pyrtsagtrak: But indeed it is when the head is Counted. ;)
15:21gtrakerr, hmm, actually looks like persistentlist manages the count for every case.
15:21gtrakas long as you start there when you cons you should be fine
15:22augustlisn't (defn ^:static -myMethod [] ...) the way to create static methods for a :gen-class ns?
15:22pyrtsaOh, PersistentList does implement Counted. But lazy seqs don't.
15:22gtrakconj, rather.. grr
15:23gtrakif you call cons, you break it, if you conj onto a list, you're fine
15:23pyrtsaFunnily, the result of (range n) does not implement Counted.
15:24justin_smithI guess because lazy things in general do not
15:24justin_smithit seems like it would be so trivial though!
15:24pyrtsaYeah, but it could be implemented with an own class.
15:24justin_smithalso, (nth (range) n) is O(n) though one could naively imagine it being O(1)
15:26Averellbut nth on a counted thing would be O(1)?
15:27pyrtsanth for Indexed will be O(1) or O(log n) or something like that, I guess.
15:27BronsaAverell: lists are counted, nth is still O(n)
15:29pyrtsaOh, I wasn't quite accurate with that. I meant that Counted doesn't affect nth. Again, the impl is found in RT.java.
15:30Averellstatic public. it's distracting :)
15:42AverellMan browsing that is kinda cool. although the language suddenly loses some mystique, just seeing it there, how simple stuff is.
15:56hyPiRionMost of it is simple
15:57hyPiRionBut when you attempt to answer the question "is this symbol/keyword legal?" by reading the Reader, you're gonna have a bad time
15:59Averellhehe. i already have a bad time moving out of simple collections, but still much more approachable than i thought.
16:00akurilinDoes anybody have a solution to this: I have 2 local libs my project depends on, I'm using "checkouts" folder in development. When building the uberjar though I need to be sure that the git repositories are up to date and that I ran lein install or I might be shipping the uberjar with outdated libs
16:00gtraki don't think checkouts has much to do with artifacts
16:01gtrakunless you're relying on bad AOT behavior
16:01akurilinCheckouts lets you not notice that the local .jar repo is not up to date, right? Everything will work just fine until you build and ship
16:01gtrakcheckouts will add the subdirs to the classpath is my understanding
16:02akurilinThat's correct.
16:02akurilinlein uberjar uses the repo though.
16:02gtrakright.
16:03gtrakyou probably want to mvn install the dependency jars, it's worth the trouble.
16:03akurilinWhat does that mean?
16:04gtrak'lein install', just like you said
16:04gtrakyou need actual releases and maven artifacts for the deps
16:05gtrakif you don't want to go through the trouble, ie you are the author of those checkouts, why not just add the source to your project's source-paths?
16:05tbaldridgepyrtsa: in ClojureScript I think it does
16:05gtrakmaybe I'm misunderstanding what you mean by 'local libs'...
16:06tbaldridgepyrtsa: bleh, stale irc window
16:06gtrakis this clojure source in a clojure project that's not released anywhere?
16:06akurilinyes it is
16:06akurilinit's just shared across multiple projects
16:06gtrakah, yea. well.. maybe a more convenient way to share it is :source-paths :-)
16:07akurilinAdmittedly the lein install approach is a pita
16:07gtraklike this: https://github.com/technomancy/leiningen/blob/master/sample.project.clj#L244
16:07gtrakthrow "../my-lib/src" in there
16:07gtrakand don't worry about it
16:08gtrakunless you actually want to start releasing the shared code
16:08akurilinLet me try that, that sounds really useful :)
16:08gtrakthen you can remove it from checkouts, too
16:09jcromartieI'm really finding a lot of places where "for" is much more readable than "map"
16:09jcromartiefun fact: (if [pred x] …) will allways be true :)
16:10gtraklol yes
16:10rasmustofor + :when/:let/:while is a lot nicer than map + filter/take-while/???
16:10lazybotrasmusto: Oh, absolutely.
16:11gtrak~for + :when/:let/:while
16:11clojurebotPardon?
16:13rasmustonrepl.el question: why does it not switch modes when I C-c M-j?
16:14rasmustooh, it was something in my config... hm
16:15justin_smithrasmusto: using emacs now? woah
16:15brehautis there anything analgous to sql subselect in core.logic ?
16:15rasmustojustin_smith: trying it out, vim is giving me pains recently
16:16rasmustojustin_smith: more specifically, BLOCKING highlighting of matching parens causing many ms of lag
16:16justin_smithweird
16:17zspencerIs there a clojure idiomatic way of injecting a dependency?
16:17rasmustoHad to start dumping out profiling information, and yeah, thousands of hits to the highlight function
16:17technomancyakurilin: I'd recommend setting :target-path to "target/%s" to avoid that problem
16:17technomancyakurilin: your checkout deps should be stripped from the classpath when creating the uberjar, but class files compiled when they were on the classpath could still be included with the default :target-path setting
16:18technomancyakurilin: see the last Q on https://github.com/technomancy/leiningen/blob/master/doc/FAQ.md
16:19seangroveAh, I miss vars sometimes in cljs
16:20jjl`you've paid for paradise, put up a parking lot?
16:22TimMcjjl`: I can't tell if you're punning, or if that's how you think the lyrics go.
16:25gtrakIt took me 3 years to hit a problem where metadata was the right solution, but it made a hard thing pretty trivial.
16:26gtrakavoided changing a ton of code around.
16:27akurilintechnomancy: so you'd not recommend the source-paths approach?
16:27gtrakhad to validate a data structure, but the information that was needed to do it was no longer there, so it was either attach it via metadata, or pass around an extra argument everywhere or change the structure and everything that uses it.
16:27akurilinor is that still cool?
16:27technomancyakurilin: checkouts is just a wrapper around source-paths and a few other things to begin with
16:28technomancyakurilin: but yeah, changing source-paths won't actually fix the problem if you have classfiles bleeding over across profile boundaries
16:34akurilintechnomancy: so to be clear, would I still want to run lein install there on my deps, or are they somehow going to be built for me during lein uberjar
16:34akurilin?
16:34gtrakthat looks like a different problem than the one you're trying to avoid
16:34gtrakthat's how to avoid AOT in general except when you're making uberjar
16:35technomancyakurilin: checkout deps are off the classpath when uberjarring no matter what, so yeah. stuff is going to come out of ~/.m2.
16:36akurilinOk got it, thanks
16:36technomancyright, so ensuring what goes into the jar is up-to-date is bigger than just this
16:36gtraktechnomancy: I just suggested he avoid a project boundary for code-sharing if he's not committed to doing releases.
16:37technomancybut you can't get that right if you're leaking across profiles anyway
16:37gtrakand mess with sources paths instead
16:37akurilinSo the idea is that if I use source-paths then I simply can't use profiles correctly?
16:37gtraktotally unrelated
16:37technomancyakurilin: sorry, to be clear checkouts are only enabled through profiles
16:38technomancythe base profile is what turns checkouts on
16:38technomancybut only the uberjar profile is active when cerating an uberjar
16:38technomancyso you're using profiles whether you're doing it explicitly or not
16:40akurilinSo the point is that once you add a source-path directive to project.clj, you always have that path on regardless of profile, riht?
16:41akurilinit becomes an extension of the project folder
16:41gtrakprofiles can do anything, but pretty much
16:42gtrakthe uberjar/checkouts stuff is irrelevant, it's a source folder for your project.
16:42gtrakyou could write a profile that kills it, but that wouldn't make much sense :-)
16:42technomancyoh, sure
16:42technomancyor you could add checkouts to the defproject directly
16:42akurilinWell the impression I'm getting is that checkouts is a "magical folder", as in it's ignored when building the uberjar
16:43akurilinas opposed to something you'd add with source-path
16:43technomancy:checkout-deps-shares [:source-paths] will make it active during uberjar if that's what you want
16:44gtrakcheckouts implies you want something with artifacts, I thought.
16:45technomancywell if you're using it for something other than "Convenience during development" then you're beyond using it for what it's intended for =)
16:47technomancyanyway, everyone should use profile isolation regardless, and if you also do this :source-paths thing it might also solve different problems
16:47gtrakhacking checkouts to give custom behavior on libraries you don't control is probably bad.
16:48gtrakif you control the deps, then you don't need checkouts except for convenience, and maybe it's more convenient to do other things.
16:48gtrakto avoid having to install/deploy that stuff in the first place.
16:49gtrakwe had a massive shared library that was shared across 3 products, and the artifact was AOT'd, which meant that they all had to use the same clojure version among other complexities.
16:49gtrakI think we could have avoided some problems by doing it this way.
16:51technomancythe simplest thing to do is just not create deployable artifacts on the same machine you do dev on
16:51gtrakthe fact that clojure AOT tries to AOT the world means you'd get all the dependency classes in the artifact, so we filter those.
16:51technomancypoof; no more staleness problems
16:51gtrakall to distribute a proprietary shared jar without source in it.
16:52jjl`TimMc: it was never one of my favourites. they're probably wrong but i'm willing to accept the more flattering alternative
16:53gtraktechnomancy: that doesn't solve this problem.
16:53jjl`TimMc: ohh, now i look them up it makes a lot more sense
16:53gtrakrather, the one we had.
16:55technomancygtrak: ah yeah, well AOTing a library is never going to be pretty
16:55gtrakhttp://dev.clojure.org/jira/browse/CLJ-322
16:56technomancywow, this was once on the list for 1.6??
16:56lazybottechnomancy: Definitely not.
17:08hugodpprint doesn't seem to print metadata, even if *print-meta* is true
17:11hugodI wonder if fipp does…
17:12bbloomhugod: nope, but it should be pretty easy to add
17:12bbloomhugod: take a look at edn.clj
17:13hugodbbloom: ok, will have a look
17:16TimMcjjl`: :-)
17:18mikerodWhen processing unevaluated Clojure forms with a goal is to fully-qualify all Symbols that are non-local
17:18mikerodwith a goal of fully-qualifying**
17:18mikerodis there any good strategy? :)
17:19stuartsierratools.analyzer?
17:19mikerodLooks like it becomes quite a trick to detect locally Symbol bindings that the unevaluated code may produce.
17:19mikerodstuartsierra: I haven't looked much at it before. I suppose I should look a bit.
17:21stuartsierraWithin a macro, you can get the current local symbols from &env I think. You can look up global symbols with `resolve`.
17:21mikerodIf you just blindly qualify any Symbol that can be qualified in the current *ns*, I think the only issue is it would ignore local shadowing of those Symbols.
17:22mikerodYeah, &env is an option I explored. I couldn't come up with a reasonable way to use it though when I haven't actually evaluated the binding forms. So there really is no "env" at the time, unless I reproduce it.
17:23mikerodFor example, if I have some code like '(let [x 5] (for [y [1 2]] x y z); I want to see '(let [x 5] (for [y [1 2]] x y ns.name/z) returned
17:24mikerodWhat the code does doesn't matter, it is assumed to be useful later in another context.
17:24mikerodI just want to store it off with qualified Symbols. It is simple I think, if there are no locals shadowing global Symbols.
17:33mikerodI believe that locals only come from let* and letfn* when it comes down to the special forms right?
17:34mikerodNvm I think I answered myself. I'll keep digging. :P
17:35justin_smithmikerod: don't forget fn / (defn) bindings
17:37mikerodjustin_smith: yep, just thought about them. then I thought, maybe I would have to consider recur and catch as well. I don't know for sure, but they stood out as possibilities.
17:38justin_smithloop (recur would bind for either fn or loop)
17:39mikerodhmm yeah
17:40rasmustovabC-cC-r for evaling a region? or is there a better way to eval an inner expression in emacs
17:40rasmusto(this is an evil-mode hack btw)
17:44dsrxrasmusto: if the point is at the end of a sexp C-x C-e will evaluate just that sexp in cider
17:44rasmusto(blah (foo bar)|) + C-X C-e ?
17:44dsrxyeah
17:45dsrxwell, idk if C-X will do anything different than C-x :p
17:45rasmustois there a way to do it from (blah (foo| bar)) ?
17:45rasmustotypo :)
17:48aaron_hi
17:49fu86I want to use enlive to fetch the content from an url which is not html
17:50fu86enlive-html/get-resource seems the right way, but I don't know how to use it :(
17:50brehautfu86: look at clj-http for general purpose http requests
17:51brehautfrom memory enlive-html/get-resource will always try to consume the resourse as html
17:51fu86thanks
17:51fu86i've tried to use an "custom" loader which simply return the content but it does not work
17:52fu86i will use clj-http for such stuff, thanks
17:57amalloyrasmusto: (blah (foo| bar)) there's not really a good way to define how far up you want to go - should it eval (foo bar), or (blah (foo bar)), or the context surrounding that, or...?
17:57amalloyor indeed just foo
17:57amalloyinstead, use C-x C-e as-is, and if you want to go up N levels first use paredit-forward-up N times (or with a prefix argument of N)
17:59amalloyi have paredit-{forward,backward}-{down,up} on the C-M-{WESD} keys, although in practice i mostly use backward-up
18:02rasmustoamalloy: hm, ok.
18:11rasmustoahh, emacs has cider now
18:11rasmustosomething must have pulled it in as a dep
18:15cbpmagnars: ping
18:39seangrovednolen_: Any from the Om instrumentation, I'd like dynamically swap the render method on a component before passing it to om/build* - e.g. to have a preview render method and an actual render method that otherwise uses the same methods for everything else
18:39seangrovednolen_: Any suggestions on how I'd go about that?
18:44stormehello
18:44stormeanyone use yokogiri before?
18:45RaynesI bet devn has.
18:50stormeI'm trying to make an image scraper with clojure
18:51stormewould yokogiri be useful for this?
18:51SegFaultAXHaha, is that a thing? yokogiri?
18:51stormeyep lol
18:51storme<-- coming from ruby
18:51SegFaultAXThat's an awesome name.
18:51stormeso not sure what clojure libs are out there
18:52SegFaultAXstorme: Are you scraping html?
18:52stormeyep
18:53SegFaultAXenlive can do that. I haven't used yokogiri so I don't know how good it is.
18:53stormeah thanks
18:57rasmusto"defun" indentation isn't working for me in clojure-mode, is there something I have to set?
19:01rasmustough, I had lisp-indent-offset set somewhere :<
19:05Cr8I usually use Jsoup for scraping
19:06Cr8It can do css-like selectors, and its types mostly participate in the java collection interfaces, so you can seq over them and such
19:13devnstorme: oh hello there
19:14devnyokogiri is really, really simple. enlive and all of those others things can do scraping, but I got annoyed with how much other stuff they brought to the table that I simply didn't need
19:14devnyokogiri is named after yoko harada, who did the JRuby implementation for Nokogiri
19:15stormeso for an image scraper, would you recommend yokogiri over enlive?
19:15devnstorme: i mean, you're asking me if i'd recommend it? I wrote it, so yeah! It's great! :)
19:15devnit's pretty darn easy
19:15devnin fact, let me dig up a snippet for you
19:16stormeoh haha
19:26devnhmph, thanks for asking about it storme -- i just was whipping up an example for you, and found that I'm getting an exception from org.apache.httpclient
19:30stormedevn working for me
19:34devnyeah, i think i just had a blocked outgoing connection for emacs
19:36SegFaultAX1.6 is RC... oh snap.
19:44devnstorme: https://gist.github.com/devn/9654084
19:45devnstorme: hopefully that speeds things along for you.
19:45SegFaultAXdevn: That's slick. Nokogiri is such a useful library, thanks for making a Clojure variant. :)
19:46devnyeah dude, no problemo. it's just a wrapper around a couple libs. There's a lot Nokogiri will do that yokogiri won't at the moment
19:47devncontributions would be much appreciated
19:47SegFaultAXI'm assuming that's the node building side?
19:47SegFaultAXIt seems like the query side is pretty fleshed out.
19:47devnyeah, i mean, on the other hand
19:47devni think tools like enlive and laser and so on already have that
19:47SegFaultAXYup.
19:48devnthey all sort of seemed to have more complicated screen scraping stories though IMO
19:48devni just wanted a thingy to query really, so *shrug*
19:48muhooscraping with emlive ia pretty painless
19:48stormethanks a lot devn!
19:49devnyeah no problem, also, welcome :)
19:50devnmuhoo: yeah? It was a long time ago, i remember like 3 tutorials were written for it
19:51devnwhich to me was not something i was very interested in, since i just wanted to, as i said above, do some basic screen scraping
19:51muhooit worked for me
19:52devnlike, the fact that tutorials needed to be written to understand how to get a page and find an element was kind of crazy
19:53devnmuhoo: actually, i take that back i guess. i think i just wanted to use xpath and css out of familiarity
19:54devnmuhoo: i'd rather not need to find a fn called 'first-child' when i already know how to do that with xpath
19:54devnbut meh, to each their own. i should give enliven another look
19:57justin_smithfirst-child, not to be confused with firstborn-child - (promise firstborn-child)
20:14TimMcjustin_smith: It really is too bad promise doesn't take any arguments.
20:17xeqiseangrove: have you done any perf check on java8's new js engine for server side rendering?
20:18seangrovexeqi: No, dnolen has been battering away on it for the past month though
20:24justin_smithTimMc: (let [offering (promise)] (deliver offering firstborn-child))
20:25arrdemhahaha
20:26arrdemthe gods of pointer arithmetic find your offering pleasing
20:26arrdemyour application may run
20:26arrdemfor now
20:26TimMc:-D
20:26TimMc&(let [p (promise)] (deliver p p))
20:26lazybotjava.lang.StackOverflowError
20:26brehautwait wat? surely only if its dereffed?
20:27brehaut&(let [p (promise)] (deliver p 1))
20:27lazybot⇒ #<core$promise$reify__6153@3827c3: 1>
20:27brehautoh right
20:28TimMcIt's just print silliness.
20:28TimMc&(pst)
20:28lazybotjava.lang.RuntimeException: Unable to resolve symbol: pst in this context
20:28gfredericks,(deftypo Foo [] java.util.Map clojure.lang.IDeref)
20:29clojurebot#<CompilerException java.lang.RuntimeException: Unable to resolve symbol: deftypo in this context, compiling:(NO_SOURCE_PATH:0:0)>
20:29gfredericks,(deftype Foo [] java.util.Map clojure.lang.IDeref)
20:29clojurebotsandbox.Foo
20:29cbplol deftypo
20:29gfredericks,(Foo.)
20:29clojurebot#<IllegalArgumentException java.lang.IllegalArgumentException: Multiple methods in multimethod 'print-method' match dispatch value: class sandbox.Foo -> interface clojure.lang.IDeref and interface java.util.Map, and neither is preferred>
20:29TimMcbrehaut: Interestingly, the overflow is in java.util.regex.Pattern$BmpCharProperty.match or so.
20:29justin_smiththat is an awesome typo
20:29gfredericksdeftypo is the weirdest feature of clojure
20:29rasmustois that a core.logic thing? deftypeo?
20:29TimMcThat's from the Intercal side of Clojure's history.
20:29gfredericksI did core.logic for a month and now I can't stop putting o's at the end of things
20:30Bronsahere's a funny one
20:30Bronsa,(deftype x [a])
20:30clojurebotsandbox.x
20:30Bronsa,(x. 1 nil {:a 2})
20:30clojurebot#<CompilerException java.lang.IllegalArgumentException: No matching ctor found for class sandbox.x, compiling:(NO_SOURCE_PATH:0:0)>
20:30Bronsauh
20:30Bronsaderp
20:30Bronsa,(defrecord x [a])
20:30clojurebotsandbox.x
20:30Bronsa,(x. 1 nil {:a 2})
20:30clojurebot#sandbox.x{:a 1, :a 2}
20:31TimMcoooo
20:31arrdemo0oooooh
20:31TimMcBasis and extra attrs?
20:31Bronsayeah
20:31justin_smith(leto [wiki "http://dune.wikia.com/wiki/Leto_Atreides_I&quot;] wiki)
20:31arrdemjustin_smith: har har
20:31gfredericksis there a ticket for that one?
20:31cbp,(update-in (x. 1 nil {:a 2}) [:a] inc)
20:31clojurebot#sandbox.x{:a 2, :a 2}
20:32Bronsagfredericks: not that I know of.
20:32gfredericksI guess it would be pretty low priority
20:32Bronsagfredericks: there's to say that that ctor is an implementation detail
20:32gfredericksI didn't even know about it
20:32Bronsa__meta + __extmap
20:32rasmusto,((x. 1 nil {:a 2}) :a)
20:32clojurebot#<ClassCastException java.lang.ClassCastException: sandbox.x cannot be cast to clojure.lang.IFn>
20:32rasmusto,(get (x. 1 nil {:a 2}) :a)
20:32clojurebot1
20:33Bronsawatch this
20:33gfredericksfun fact: you can't add metadata to a lazy seq without forcing it
20:33Bronsa,(map->x (x. 1 nil {:a 2}))
20:33clojurebot#sandbox.x{:a 1}
20:33arrdemBronsa: this is absurd. thanks for sharing :D
20:33Bronsaoh damn
20:33arrdemgfredericks: that doesn't make sense...
20:33Bronsathat returns #user.x{:a 2} in my repl
20:33Bronsaw/e
20:33rasmustoprobably not a big deal
20:34gfredericksarrdem: it makes good sense after digging into the impl for a while
20:34cbp,*clojure-version*
20:34clojurebot{:interim true, :major 1, :minor 6, :incremental 0, :qualifier "master"}
20:36Bronsaarrdem: I "discovered" this behaviour while investigating for CLJ-1323
20:36Bronsathat's a funny one too
20:36gfredericksarrdem: basically you don't want two objects holding onto the same thunk
20:36arrdemBronsa: I'm so jelly of the fun you have playing with the core
20:36gfrederickscuz that would require a lot more coordination
20:36arrdemBronsa: one day I'll catch up, but not this semester :c
20:37arrdemgfredericks: hum... that makes sense but I'd have to read it myself.
21:02amalloygfredericks: you also can't conj onto a lazy-seq without forcing it, as i recall
21:02amalloyforcing the first element, anyway; of course you don't have to force the whole thing
21:11hyPiRiongfredericks: that would just force the first element, right?
21:11hyPiRionunless that's exactly what amalloy said.
21:12amalloywell, i was saying it about conjing; you're saying the same thing about metadata, which is also true
21:12hyPiRionYeah, I was unsure whether you only meant conjing or both
21:26Steveo_where can I find the ant colony code that rich refers to in his concurrency talk?
21:27gfredericksamalloy: that one is not obvious to me
21:28gfredericks,(let [a (atom false) l (lazy-seq (swap! a not) nil)] [(first (conj l 3)) @a])
21:28clojurebot[3 true]
21:28gfredericks,(let [a (atom false) l (lazy-seq (swap! a not) nil)] [(first (cons 3 l)) @a])
21:28clojurebot[3 false]
21:28gfredericksweeeeird
21:29cbpo_O
21:29amalloygfredericks: because cons just creates a Cons object, but conj dispatches to .cons on the collection
21:29amalloyand lazy-seq delegates most of its operations to (.seq this)
21:30gfredericksooh okay
21:30gfredericksso the lazy-seq impl is just lazy
21:30amalloyyes. it definitely could be better. instead it's lazily not being lazy
21:31rasmustoheh
21:31amalloygfredericks: they're laughing lazily. only if you force them will you hear the sound
21:32arrdemhaha
21:32brehautgfredericks: no need to be so strict
21:33gfredericksby "glaring at" of course I meant "forcing"
21:35storme(reduce + (range 16 128))
21:35storme,(reduce + (range 16 128))
21:36clojurebot8008
21:36storme,(/ (reduce + (range 19 173)) 11)
21:36clojurebot1337
21:37gfredericks,(take 5 (for [x (range) y (range x) :let [z (range y x) s (seq (str z))] :when (= s (reverse s))] [y x z]))
21:37storme,(str (/ (reduce + (range 19 173)) 11) (reduce + (range 16 128)))
21:37clojurebot"13378008"
21:37clojurebotExecution Timed Out
21:37storme,(str (/ (reduce + (range 19 173)) 11) " " (reduce + (range 16 128)))
21:37clojurebot"1337 8008"
21:37gfredericks,(take 2 (for [x (range) y (range x) :let [z (range y x) s (seq (str z))] :when (= s (reverse s))] [y x z]))
21:37clojurebotExecution Timed Out
21:37gfredericksoh whops
21:38gfredericks,(take 5 (for [x (range) y (range x) :let [z (reduce + (range y x)) s (seq (str z))] :when (= s (reverse s))] [y x z]))
21:38clojurebot([0 1 0] [0 2 1] [1 2 1] [0 3 3] [1 3 3])
21:38gfredericks,(take 5 (for [x (range) y (range x) :let [z (reduce + (range y x)) s (seq (str z))] :when (> z 10) :when (= s (reverse s))] [y x z]))
21:38clojurebot([5 7 11] [4 8 22] [3 9 33] [2 10 44] [0 11 55])
21:38amalloygfredericks: what on earth
21:38gfredericksstorme made me wonder how often (range x y) is a palindrome :P
21:39gfredericks,(take 5 (drop 50 (for [x (range) y (range x) :let [z (reduce + (range y x)) s (seq (str z))] :when (> z 10) :when (= s (reverse s))] [y x z])))
21:39clojurebot([9 34 525] [33 34 33] [0 35 595] [1 35 595] [5 35 585])
21:39stormelol gfredericks
21:39gfredericks,(take 5 (drop 50 (for [x (range) y (range 10 x) :let [z (reduce + (range y x)) s (seq (str z))] :when (> z 10) :when (= s (reverse s))] [y x z])))
21:39clojurebot([31 45 525] [32 45 494] [44 45 44] [12 46 969] [34 46 474])
21:39amalloyah, i see
21:39gfredericks,(reduce + (range 34 46))
21:39clojurebot474
21:40gfredericks,(take 5 (drop 50 (for [x (range) y (range 10 x) :let [z (reduce + (range y x)) s (seq (str z))] :when (> z 1000) :when (= s (reverse s))] [y x z])))
21:40clojurebot([53 102 3773] [80 102 1991] [74 103 2552] [27 104 5005] [16 106 5445])
21:40gfredericks,(take 5 (drop 50 (for [x (range) y (range 10 x) :let [z (reduce + (range y x)) s (seq (str z))] :when (> z 10000) :when (= s (reverse s))] [y x z])))
21:40clojurebot([91 192 14241] [85 194 15151] [26 197 18981] [50 197 18081] [86 197 15651])
21:40gfredericksso much math I'm making clojurebot do
21:40storme,(:require [yokogiri.core :as html])
21:40clojurebot#<CompilerException java.lang.ClassNotFoundException: yokogiri.core, compiling:(NO_SOURCE_PATH:0:0)>
21:40stormeis clojurebot open source?
21:41arrdem$source
21:41lazybotSource not found.
21:41arrdem~source
21:41gfredericks$google clojurebot
21:41lazybot[hiredman/clojurebot · GitHub] https://github.com/hiredman/clojurebot
21:41stormety
21:41arrdemclojurebot: source |is| $google clojurebot
21:42gfredericks,(println "$google clojurebot")
21:42clojurebot$google clojurebot\n
21:42arrdemgfredericks: bots ignore each-other, remember?
21:42storme,(println "I'm a bot")
21:42clojurebotI'm a bot\n
21:42arrdemwell.. ours do.
21:42rasmusto,(print "$google clojurebot")
21:42clojurebot$google clojurebot
21:42rasmusto##(print "$google clojurebot")
21:42lazybot⇒ $google clojurebotnil
21:42storme,(println "$google clojurebot")
21:42clojurebot$google clojurebot\n
21:43storme,(println "$google lazybot")
21:43clojurebot$google lazybot\n
21:43arrdemstorme: what did I say about the bots ignoring each other...
21:43stormeah, missed that arrdem
22:26amalloylazybot ignores clojurebot
22:26amalloybut not vice versa, as i recall
22:26amalloy&(symbol ",1")
22:26lazybot⇒ ,1
22:27amalloyoh, right. he prefixes his output so that clojurebot doesn't interpret it
22:27rasmustoprint a backspace character
22:40xeqiecho ,(println "&(+ 1 2)")
22:40lazybot,(println "&(+ 1 2)")
22:40clojurebot&(+ 1 2)\n
23:19gfredericks$mail clojurebot ,(println "hello")
23:19lazybotMessage saved.
23:19gfredericks$mail clojurebot ,(def sent true)
23:19lazybotMessage saved.
23:20gfredericks,sent
23:20clojurebot#<CompilerException java.lang.RuntimeException: Unable to resolve symbol: sent in this context, compiling:(NO_SOURCE_PATH:0:0)>
23:33TimMcgfredericks: clojurebot would have to ask for mail.
23:52amalloyoh my god. now lazybot is going to be /msging clojurebot all the time
23:52amalloyi'm glad i added $unmail for admins