#clojure log - Mar 14 2013

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

0:00 arrdem: (defun foo (a b) (+ a b)) -> (defn foo [a b] (+ a b))

0:01 there's also the obligatory comment about excessive use of macros providing ubfuscation rather than clarification.

0:06 yunfan: oop, i noticed that the premium user of newsblur has just incr by 100+ in the past hour

0:26 pr3d4t0r: Greetings.

0:28 I'm debugging the integration/bindings layer between a Spring application and a simple Clojure script. The script is defined as a <text>(def hello (fn [] "Hello"))\n(hello)</text>

0:28 When I try to run it, I get this error:

0:29 Could not locate (def__init.class or (def.clj on classpath

0:29 It looks like I'm missing a driver/wrapper to call this. Not a Clojure coder, sorry. Just need to know which M so I can RTFM and finish the integration. Thanks in advance.

0:34 If this were a Python script, for example, I dould be able to just write <text>def hello():\n print 'hello'\n\n</text> The script between the tags would be executed verbatim.

0:39 brehaut: pr3d4t0r: you'll need to be much more specific about the Spring/Clojure bindings you are using. i doubt its core clojure code, so its off the beaten track for a lot of us here.

0:41 pr3d4t0r: brehaut: Agreed.

0:42 brehaut: The scripting engine factory is old - 2011, and it makes reference to clojure-contrib.

0:42 brehaut: yikes

0:42 pr3d4t0r: brehaut: I believe that's what's calling def.clj

0:42 brehaut: avoid that

0:42 pr3d4t0r: brehaut: Yup.

0:43 brehaut: def.clj is probably gone in 1.5.1 -- correct?

0:43 brehaut: It's not in the .jar -- maybe no longer needed in 1.5.1 at all.

0:43 brehaut: that smells like old contrib muck

0:43 pr3d4t0r: brehaut: Correct.

0:44 brehaut: I just need to figure out what needs to be called (or ignored) for this to work, as if I were in the interactive interpreter.

0:44 brehaut: def.clj seems to just set up a bunch of I/O stuff.

0:44 brehaut: pr3d4t0r: the basics of calling into clojure from javaland is to go via clojure.lang.RT/var

0:45 the var method takes a namespace (as a string) and a var name (also a string) and returns a Var object

0:45 you can then call .invoke on the var to call the function it references

0:45 pr3d4t0r: brehaut: Understood.

0:46 brehaut: I'm looking at the JSR-223 package -- I bet that's where they call that def.clj

0:46 brehaut: the most basic way to use that to eval ad hoc clojure is to get vars for clojure.core/read-string and clojure.core/eval, then feed the text into read-string and the result of that into eval

0:46 pr3d4t0r: brehaut: OKi.

0:46 * pr3d4t0r takes notes.

0:48 * brehaut handwaves

0:48 brehaut: theres a bunch of details that kinda ignores

0:50 its probably worth looking at clojail and clojurebot for seeing how they treat ad hoc clojure code

0:51 TEttinger: is there a good example case of where a program distributed to general audience end-users, using clojure 1.5.1, would not benefit from using the new reducer library?

0:51 (assuming nobody is on less than a dual-core, and not targeting android)

0:52 like if I decided to switch every map with r/map

0:52 pr3d4t0r: Ah, he left.

0:52 bbloom: TEttinger: small collections are likely to result in a performance decrease when you add coordination overhead

0:52 TEttinger: unless work is CPU bound

0:53 TEttinger: bbloom, I guessed that might be the case -- is small in this case 100 items or 10,000 items?

0:53 bbloom: TEttinger: depends on CPU workload per item

0:53 TEttinger: ah

0:53 bbloom: TEttinger: profile profile profile

0:54 (doc time)

0:54 TEttinger: pr3d4t0r, yeah, clojail is awesome

0:54 danneu: arrdem: yeah, right. i guess i mean to say i'm just ready for a new kind of spaghetti code. :) i suppose the common spaghetti of lisp would be a bunch of macro indirection?

0:54 clojurebot: "([expr]); Evaluates expr and prints the time it took. Returns the value of expr."

0:56 TEttinger: danneu, maybe a lib that requires metadata on arguments, or assigns metadata on its return values for its own later use without telling you... that could be bad

0:56 I don't know if people actually do that, but it could be a devious obfuscation

0:58 danneu: oh man

0:58 haha

1:09 pr3d4t0r: Awesome -- thanks!

1:11 danneu: nice, another WeeChat user.

1:14 Is there a better repl workflow than (use 'mynamespace.core :reload-all) every time you make a change?

1:15 jeremyheiler: danneu, There's C-c C-k If you're using Emacs with nrep.el

1:17 yacin: can you (flush) without forcing a newline to be printed?

1:19 jeremyheiler: yacin, To standard out, or...?

1:23 mjc: yacin: yes

1:23 danneu: it's time i try emacs finally. evil mode looks sharp

1:24 jeremyheiler: danneu, Late last year I switched from vim to emacs, and so far I am pleased. I forced myself to ignore evil mode and really learn emacs, though.

1:27 danneu: i might take a break from work for a week just to play with some new technology

1:27 there's just so much pressure to be immediately productive

1:28 jeremyheiler: I hate that. It's not healthy.

1:28 yacin: jeremyheiler: yes to *out*. i have a (while ...) with a (print ".") inside it

1:29 but it doesn't show up without (flush), but adding (flush) causes a newline to be printed afterwards

1:29 Raynes: danneu: I'm a big evil-mode advocate.

1:29 mjc: flush doesn't do that for me

1:30 yacin: hmm, guess it's me then

1:30 mjc: e.g. (do (print "hi") (flush) (Thread/sleep 5000) (print "bye"))

1:30 Raynes: danneu: I'm an interesting case. I used Emacs originally, then used Vim for two months, and then I went back to Emacs and added evil-mode. I don't use evil-mode because I'm too attached to Vim keybindings, I can use Emacs keys just fine. I use evil simply because I enjoy the shortcuts in some cases more than I do the Emacs alternatives.

1:31 yacin: i get

1:31 pdns.gza> (do (print "hi") (flush) (Thread/sleep 5000) (print "bye"))

1:31 hi

1:31 bye

1:31 nil

1:32 ,(do (print "hi") (flush) (Thread/sleep 5000) (print "bye"))

1:32 clojurebot: hibye

1:32 yacin: must be my emacs setup or something then

1:32 hrmm

1:33 jeremyheiler: I get what clojurebot says in a regular repl, but in nrepl.el, I get the extra new line.

1:34 yacin: ah, nrepl is the culprit for me too then

1:34 arrdem: tyler__: dude... that was an epic talk thanks for the lunk

1:37 danneu: he gave the same talk at railsconf last year

1:38 that's where the clojure seed was first planted in my head

1:39 Raynes: cool. i'm not married to vim, but im addicted to modal editing!

1:42 arrdem: Raynes: put him onto evil?

1:43 jeremyheiler: yacin, I haven't looked at the nrepl.el code, but my guess is that it inserts a new line whenever *out* is flushed. So that the returned value is always on a new line, as opposed to a regular repl. https://www.refheap.com/paste/12525

1:44 grothendieck: Other than 'i,j,k,l' instead of 'C-f, C-b, C-n, C-p', I find emacs keybindings to be more intuitive and efficient than vim

1:44 mjc: if you flush twice, does it add a 2nd newline ?

1:44 jeremyheiler: mjc, hmmm no

1:45 mjc, then perhaps only when something else has been written to the buffer.

1:45 mjc: not sure what that means, but suspected it's an interesting data point :)

1:45 jeremyheiler: definitely

1:46 mjc, updated the examples in the paste

1:48 danneu: grothendieck: i'm happy with a pretty small subset of vim's keybindings. dd ciw . p P o O A I.

1:51 mjc: jeremyheiler: yeah. looks like an odd hack

1:56 ivan: I've seen spurious newlines in the middle of a big pprint with nrepl.el

1:59 jeremyheiler: ivan: I have, too.

2:15 amalloy: yeah

2:15 sorry, wrong channel

2:21 yunfan: ok newsblur total down, what about other service provider?

2:25 ivan: yunfan: Reader is still up for at least 3.5 months ;)

2:27 Raynes: Newsblur seems to be up for me.

2:29 yunfan: ivan: the json file export from google cause problem when i use the python's json library, hope i could ignore it in clojure

2:30 ivan: hm, what problem?

2:31 python 2 json.loads(open("starred.json", "rb").read()) works for me

2:34 yunfan: ValueError: Expecting object: line 37187 column 3 (char 4430674)

2:34 this is the error

2:34 maybe my starred file size bigger thant the default limitation?

2:34 python2.7 BTW

2:34 ivan: check the end of it for truncation

2:35 yunfan: its not the end

2:37 ivan: strange. maybe the high volume of exports triggered some bug in Takeout.

2:38 yunfan: well maybe its just the bug to chinese char :[

2:52 ivan: they eats the last ]}

4:00 grebus: hrm - (instance? clojure.lang.ILookup {}) returns true, but in clojurescript (instance? cljs.core/ILookup {}) throws an error...

4:02 MacCoaster: Can I do a partial application with a Java method? something like (partial .equals "") ?

4:03 or in other words, how do i use .equals for drop-while ? or maybe I should be looking at clojure.strings, derp

4:03 ivan: &(#(.equals "" %) "")

4:03 lazybot: ⇒ true

4:05 ivan: &(#(= "" %) "")

4:05 lazybot: ⇒ true

4:05 MacCoaster: ivan: huh, # denotes that % is being partially applied somehow?

4:05 sorry, i'm new to clojure

4:05 amalloy: MacCoaster: for your specific case of using .equals, i'd point out: .equals is just a really bad version of =, unless you need to do some kind of weird java interop

4:06 #(foo (bar %)) is a lambda, equivalent to (fn [x] (foo (bar x)))

4:06 MacCoaster: aha so it's a macro

4:07 amalloy: yes i'm just trying to understand clojure more specifically with java interop, equals was just an easy example

4:11 danneu: can anyone think of a topic for a beginner-oriented tutorial that you think would've helped you learn clojure had it been there?

4:25 lpetit: danneu: not really, but at any costs I would avoid trying to be "meta" like people under the "curse of knowledge" do too often AFAICT. That is, don't try to present a Clojure interpreter in Clojure. The language is foreign for beginners, the topic/examples should be common.

4:35 noidi: danneu, you might want to show how in Clojure most problems can be solved by composing simple standard library functions

4:35 that's something that's really painful to do in Java

4:36 and not as idiomatic in Ruby/Python

5:03 Glenjamin: danneu: some sort of cli-driven quiz might be good

5:05 michaelr525: hello folks

5:14 Glenjamin: Can anyone point me to an up-to-date guide to setting up emacs + whatever the latest suggested environment is?

5:14 I've seen lots mentioning swank, but now I've just read something that says nrepl deprecates swank for clojure

5:21 ucb: Glenjamin: are you on emacs 24.x?

5:21 Glenjamin: Aquamacs, so 23 - but i've got package.el in

5:21 ucb: oh, I see. IIRC it should be as easy as installing clojure-mode and nrepl.el via packages.el

5:22 I believe you'll get nrepl-jack-in and stuff

5:22 Glenjamin: i've got that far, not really sure what to do with it though!

5:22 ucb: well, open a project.clj file and then M-x nrepl-jack-in

5:22 Glenjamin: oh cool

5:22 i have a repl

5:25 ucb: cheers for that, i'll rtfm a bit more now :)

5:26 ucb: Glenjamin: no bother; glad to help

5:26 shriphani: hello everyone. I have a question about load-file

5:27 I am using load-file to load some routines I have defined in another file. After I added another file to it, lein doesn't see the new definitions. How do I make lien update whatever it has done with that file ?

5:27 leon * sorry.

5:28 leon sorry about the autocorrect.

5:28 oh my god…I give up.

5:29 so. is using load-file not the way to go? Should I do something else?

5:35 ejackson: shriphani: is there a reason your not using (use ...) or (require ...)

5:35 these are the standard functions to load up other namespaces

5:35 shriphani: ejackson: not particularly. I have a warc-clojure.java in the same directory that I want to use in core.clj.

5:36 ejackson: .java ?

5:36 shriphani: ejackson: no clojure

5:36 .clj sorry

5:36 ejackson: ok

5:36 shriphani: wow, I am really not helping myself..

5:37 ejackson: two things

5:37 rename warc-clojure.clj to warc_clojure.clj

5:37 and make the namespace in that file whatever.warc-clojure

5:37 then use or require that from core.clj

5:37 and you should be golden

5:38 the underscore thing is nasty gotcha

5:38 shriphani: so now (require warc_clojure)

5:38 ?

5:39 ejackson: when I do that, "can't resolve symbol warc_clojure"

5:40 ejackson: (require 'warc-clojure)

5:41 clgv: happy pi day :D

5:43 shriphani: ejackson: my project name is scraper and warc_clojure has (ns scraper.core ..) and I get the error saying it can't find that namespace. what am I doing wrong now ?

5:43 ejackson: you're in a repl ?

5:43 shriphani: ejackson: no lein run.

5:44 ejackson: easier to do from a repl

5:44 try lein repl

5:44 (use 'scraper.core)

5:45 shriphani: ok when I did lein repl, this happened: FileNotFoundException Could not locate warc_clojure__init.class or warc_clojure.clj on classpath: clojure.lang.RT.load (RT.java:432) wtf is the deal with that ?

5:46 and yet `ls` shows: core.clj warc_clojure.clj

5:47 ejackson: that normal ?

5:47 vijaykiran: shriphani: can you paste the core.clj on pastebin/gist ?

5:47 shriphani: vijaykiran: sure.

5:47 ejackson: are they in the root dir or in the ./src tree ?

5:48 they should be in src/scraper/

5:48 shriphani: https://www.refheap.com/paste/12526

5:48 ejackson: src/scraper

5:49 vijaykiran: that was the core.clj file.

5:50 ejackson: (require 'scraper.warc_clojure)

5:50 sorry, no

5:50 (require scraper.warc-clojure)

5:50 dammit, now its me !

5:50 (require 'scraper.warc-clojure)

5:50 although you really want to put that into the ns declaration

5:50 shriphani: umm you mean an underscore right?

5:50 ejackson: no

5:50 vijaykiran: or use :require form

5:51 ejackson: the filename has an _, but the require needs a -

5:51 its a JVM thing

5:51 shriphani: wtf...

5:51 ejackson: yeah, its an historical wort

5:51 shriphani: ok it worked!

5:51 vijaykiran: shriphani: Java classes can't have - in the name, but clojure namespaces can, so in clojure when you say "-" it is translated to java "_"

5:52 shriphani: vijaykiran: I see.

5:52 can I change the '_' in my filename to a '-' ?

5:52 ejackson: no

5:53 shriphani: ok so no filename can have a '-' but the requires can use it even though the filename has a '_' ?

5:54 ejackson: yes, the filename cannot have a -, but can have a _. Any _ in the filename must be a - in the namespace.

5:54 fun for all the children.

5:55 shriphani: I wasted a few hours last weekend trying to solve that problem :).

5:55 ejackson: shoulda asked here first!

5:55 shriphani: I come from scheme to I have a natural tendency to use '-' and a repulsion to '_'

5:55 although my python is littered with '_'..

5:55 ejackson: the only place you need to see _ is in filenames, and database stuff

5:56 clgv: shriphani: the "_" is probably for naming consistency between clojure source files and generated class files, since classfiles only allow "_"

5:57 shriphani: clgv: i see. that makes sense.

5:58 are question-marks ok?

5:59 like (defn is-quirk? ..) ?

6:00 clgv: in function names and symbols yes. not in filenames though

6:06 shriphani: ejackson: after using (require 'scraper.warc-clojure), do I need to refer the functions using warc-clojure/fn-name ?

6:06 ejackson: yeah

6:06 if you use (use ...) then fn-name is enough

6:07 clgv: shriphani: you can use an alias with the following in your ns-statement "(:require [scraper.warc-clojure :as warc])"

6:08 shriphani: clgv: Caused by: java.lang.ClassNotFoundException: scraper.warc-clojure ....

6:08 lispy_: ejackson: hi, I've just seen your have contributed to raynes/laser… wonder if you are familiar enough with it to help me with something ?

6:08 ejackson: hahaha: I think I literally contributed a backspace :)

6:08 clgv: shriphani: put it in your ns statement

6:08 lispy_: ejackson: no worries

6:08 ejackson: shine your Raynes lamp

6:09 he never sleeps

6:09 clgv: shriphani: you should do all your imports in the `ns` statement. (ns my.ns (:require ...)) instead of (require ...) after the ns statement

6:09 lispy_: I thought Raynes was on US West Coast ?

6:09 shriphani: clgv: and now this : Exception in thread "main" java.lang.Exception: namespace 'scraper.warc-clojure' not found after loading '/scraper/warc_clojure'

6:09 so I should put warc-clojure in its own namespace ?

6:09 it si currently in scraper.core

6:10 clgv: shriphani: every namespace should have its own file

6:11 ejackson: lispy_: correct. he never sleeps.

6:11 lispy_: ejackson: I'll shine the lamp :-)

6:12 raynes: hi, using laser how do I do something like modify all href attributes in a document, based on their current value ?

6:13 I can currently set new values, but not update based on current value

6:14 shriphani: clgv: ok I am confused. I have https://www.refheap.com/paste/12527 which is warc_clojure.clj and https://www.refheap.com/paste/12528 is core.clj… and it can't see is-response-record … I am stumped..

6:16 clgv: shriphani: you need to reload warc_clojure.clj if you changed it after scraper.core was laoded

6:17 shriphani: clgv: lein run won't do it ?

6:19 clgv: shriphani: if you re-ran it it does it

6:19 shriphani: well I reran it..

6:20 No such var: warc-clojure/is-response-record

6:20 ejackson: did you save the file ?

6:20 shriphani: yes..

6:20 clgv: oh maybe you nedd to do "lein do clean, run" since your main is aot compiled

6:21 "need"

6:21 shriphani: that didn't work...

6:21 I can't even tell if there is an error...

6:21 and I am on IRC trying to get 20 lines to compile :_(

6:23 clgv: shriphani: but it works if you replace `warc-clojure/is-response-record` with `identity`?

6:24 shriphani: I suspect you have some general setup problem. what are the proct relative paths of your namespace files?

6:24 *project

6:25 shriphani: btw. you should not use import, use, require as commands in the source but as configuration in your `ns` statement like (ns my.ns (:import ...) (:require ...) (:use ...))

6:25 shriphani: clgv: this happened if I replaced it with identity: Exception in thread "main" java.lang.IllegalArgumentException: No implementation of method: :make-input-stream of protocol: #'clojure.java.io/IOFactory found for class: nil

6:26 where am I even using IOFactory..

6:26 clgv: in scraper.warc-clojure

6:27 in `io/input-stream`

6:27 shriphani: clgv: this is my setup : https://www.refheap.com/paste/12529

6:28 clgv: shriphani: looks good so far

6:28 shriphani: can you try "lein repl" and see if it loads without errors

6:29 shriphani: I am out to lunch now...

6:29 shriphani: yes no errors.

6:29 and yes in the repl, during tab completion it finds all the routines.

6:43 well… that was a bummer. It still can't see is-response-record… Just one of the definitions is not visible…. can anyone help ?

6:49 lpetit: There's a new version of Counterclockwise, Clojure plugin for Eclipse, available

6:49 shriphani: ok this is interesting. If I don't call is-response-type from core.clj, it is can't see it and the repl fails. But if I don't call it, it loads up in the repl fine….

6:49 ejackson: any ideas ?

6:51 wow. I am an idiot. nvm

6:57 lpetit: clgv: hello

6:58 Are there emacs or Counterclockwise users here right now ?

6:58 I need to find sensible defaults for barfage and slurpage

7:00 I've been thinking of something like this: Ctrl+(+RIGHT_ARROW for backward slurp, Ctrl+(+LEFT_ARROW for backward barfage, Ctrl+)+RIGHT_ARROW for forward barfage, and Ctrl+)+LEFT_ARROW for forward slurpage.

7:00 Thoughts ?

7:14 mpenet: lpetit: arrows force to move hands, it might be better to choose some keys closer to the home row

7:16 noidi: on the other hand the selection keys use alt+shift+arrows

7:16 the selection operations + Alt+R are so powerful that I haven't even felt the need for slurp/barf

7:17 lpetit: noidi: agreed, but some have complained about its lack, and it appears that their implementation have been submitted as a patch to paredit.clj, so !

7:18 mpenet: agreed, but as noidi wrote, arrows will integrate more with the current state of the art in Eclipse. but now that I think about it, there's nothing preventing me to overload keybindings with letters only variants

7:19 Such as Ctrl+(+S for backward slurp, Ctrl+(+B for backward barf, etc.

7:20 Pupnik-: what is slurp and barf?

7:22 mpenet: sexp manipulation function for paredit

7:22 functions*

7:22 clojurebot: No entiendo

7:40 lpetit: What would be a good english short description of "forward slurp" ? (< 5 count 10) words ?

7:51 otfrom: lpetit: slurp-several-words ?

7:52 but I've had many arguments about couple = 2, few = 2-5, several = 5-10, lots > 10

7:52 ;-)

7:55 lpetit: otfrom: never mind, I just used "Forward Slurp", "Forward Barf", etc. :-)

8:04 NeedMoreDesu: How do I know that future is still running?

8:06 alexnixon: NeedMoreDesu: realized?

8:06 NeedMoreDesu: alexnixon: thanks :3

8:14 ustunozgur: Is there a function in core that will give me the keys and vals of a map as a vector? e.g. {:a 1 :b 2} => [:a 1 :b 1]

8:16 ambrosebs: ,(mapcat identity {:a 1 :b 1})

8:16 clojurebot: (:a 1 :b 1)

8:16 ambrosebs: ustunozgur: ^^

8:17 ustunozgur: thank you ambrosebs. So is there a more succint way to write this one? (apply (partial priority-map-by (comparator >)) (mapcat identity {:a 1 :b -1 :c 3}))

8:17 Basically I'm trying to get a map ordered by its values in desc order

8:18 ambrosebs: ustunozgur: not sure.

8:19 clgv: lpetit: hello

8:19 ustunozgur: I was previously using this one (apply priority-map-by (comparator >) (vec (flatten (seq {:a 1 :b 3}))))

8:20 clgv: shriphani: what was it? spelling error somewhere?

8:20 shriphani: yup

8:20 and light table didn't draw a squiggly red line (I don't think it does) so I missed it.

8:21 also, I am trying to get my head around enlive's scraping tools. There's a structure like {:tag :div …} .What is that ?

8:21 ustunozgur: That `vec` is redundant I think. (apply priority-map-by (comparator >) (flatten (seq {:a 1 :b 3}))) seems to work as well.

8:22 clgv: lpetit: please not "CTRL+(" thats already 3 keys and hardly reachable one handed ^^

8:22 lpetit: clgv: 3 keys ? you should definitely switch to qwerty or azerty :-p

8:22 clgv: lpetit: CTRL+SHIFT+8 ... :/

8:23 lpetit: :-(

8:23 clgv: suggest smthg else then

8:24 clgv: lpetit: humm... there is a lot of meaningful combinations assigned already as we also noticed with repl history search...

8:24 what does emacs use?

8:25 lpetit: clgv: http://mumble.net/~campbell/emacs/paredit.html

8:26 clgv: lpetit: those "windows keys" are free it seems: CTRL+WIN+RIGHT-ARROW?

8:26 lpetit: clgv: I think they must be left for the OS

8:26 clgv: lpetit: I do not know there general name ^^

8:27 lpetit: search for slurp, you'll get to their block

8:27 clgv: oh, do they? my linux has nothing assigned for this combination it seems

8:27 squidz: does anybody know how to exectute code with nrepl.el in emacs provided prefix arguments? I cant seem to get it to work.

8:29 clgv: lpetit: are "<" and ">" near to CTRL on most keyboard layouts as well?

8:29 squidz: I want to evaluate a function providing the parameter passed to the function for example. It says in the docs that I can use C-x C-e with the prefix argument, but I cant figure out how to use a 'prefix-argument'

8:30 mpfundstein: i have written a clojure worker/supervisor framework which allows me to execute jobs on remote servers. i wonder if it would be cooler to just shell out the scripts or to compile them on runtime and than execute them from within the current VM

8:30 lpetit: clgv: very dependent on the keyboard, I guess

8:30 clgv: dunno for < and >

8:33 clgv: lpetit: ah well. I can remap them anyway...

8:33 lpetit: clgv: sorry :-(

8:34 clgv: lpetit: no problem. I thought I just mention that CTRL+( is pretty complicated for german keyboard layouts

8:34 lpetit: clgv: you were right to do so, it's still important for me to know those things.

8:34 clgv: lpetit: is there a new release planned for today?

8:35 lpetit: including slurp / barf, you mean ?

8:35 clgv: because I already released 0.12.0 today :-D

8:35 clgv: oh I did not notice^^

8:36 gotta update my dev env ^^

8:39 lpetit: clgv: cemerick has strong arguments for reverting cow's behavior changed in https://code.google.com/p/counterclockwise/issues/detail?id=484

8:39 clgv: here are the arguments: https://code.google.com/p/counterclockwise/issues/detail?id=533

8:47 clgv: lpetit: his arguments sound reasonable. turns out the small feature is a problem, I'd say

8:47 lpetit: clgv: yeah, i'll revert the commit, as he suggested

8:47 clgv: lpetit: when defining the function the user can send the whole namespace to the repl to avoid the error

8:47 lpetit: I almost only use send file to repl

8:48 lpetit: avoids consistency problems in a "regular" namespace. sending single forms to repl is more useful for "example" or "test" namespaces

8:49 lpetit: clgv: sold ! I revert the feature :-)

8:49 clgv: 0.12.1 ? ;)

8:50 oh I mean "0.12.1 today?" ;)

8:50 otfrom: hugod: when do we get a new nrepl-ritz? ;-)

8:50 lpetit: clgv: dunno

8:50 otfrom: now that kingtim has released nrepl.el 0.1.7

8:51 clgv: quoting: when the sun rises in the west and settles in the east

8:51 hugod: otfrom: today I hope

8:52 clgv: damn, narrowly missed ;)

8:58 otfrom: excellent hugod :-)

9:03 jcromartie: in nREPL, sometimes *1 works, and sometimes it doesn't

9:03 what's the deal

9:14 edoloughlin: What's the best practice for error handling in Clojure? E.g., I've got multiple checks to perform if I create/update a database record. I find this nice and easy to do in a functional style until I consider how I report back up the stack if something failed. Should I throw exceptions or use nested if-let statements etc.? Any advice?

9:14 It just seems to get messy...

9:16 clgv: edoloughlin: you could build a pipe which gathers errors as they happen and returns nil if it succeeded

9:17 edoloughlin: This is new to me - what's a pipe?

9:17 i.e., is it a Clojure primitive that I haven't heard of?

9:18 clgv: edoloughlin: a checker like (fn [error-list, data] (if (some-criterion data) error-list (conj error-list {:reason "some criterion failed"})))

9:18 edoloughlin: no primitive. then you can have a collection of checkers which is automatically applied to your data

9:19 lpetit: edoloughlin: there are many validation libraries out there. Worth looking at them, either for inspiration, or for adoption

9:19 clgv: that way the checking is pretty composable

9:19 edoloughlin: Seems reasonable. I'll do some research. Thanks.

9:20 lpetit: edoloughlin: for instance http://blog.clojurewerkz.org/blog/2013/03/12/validateur-1-dot-4-0-is-released/

9:20 edoloughlin: Thanks, guys.

9:21 lpetit: edoloughlin: and also, released open source recently by the company using it internally, there's the promising clj-schema : https://github.com/runa-dev/clj-schema/wiki/Getting-Started

9:22 clgv: lpetit: interesting^^

9:22 lpetit: edoloughlin: with something like clj-schema, you have not only composition, but also, if you take care of internally only managing data as pure clojure data structures (hiiiighhlyy recommended), then you can reapply validations almost everywhere : any boundaries, for regression tests, etc.

9:22 even in ClojureScript code, I guess :-)

9:32 kzar: Package.el isn't listing nrepl like it apparently should, I've refreshed the contents... any ideas?

9:48 hyPiRion: kzar: you have marmalade as a repo?

10:02 Anderkent: Anyone with in-depth understanding of midje? I can't figure out how to make reusable test assertions - I find myself forced to make everything a macro or otherwise midje outputs really weird stuff when something fails... Is there a better way to do this? https://www.refheap.com/paste/12533

10:09 clgv: Anderkent: apart from your minimal example do you really want to test the same again? usually you only need reusable setup code or reusable predicates for function output

10:11 Anderkent: yes, I want the assertions to run every time the action is taken. In the real code, these are selenium tests, and I have a long list of integration tests where actions are taken in different orders / states, and the pre/post conditions should run every time

10:12 i.e. an action might be 'send a new message', and the precondition would be 'the new message button is active', the action would itself have a number of facts within (tell selenium to type in some stuff, verify that the form validation runs etc), then the post conditions will say something like 'redirected to new message'

10:15 clgv: Anderkent: oh, then it seems midje is the wrong tool

10:16 owengalenjones: can anyone help, this macro complains when compiling the file no such vars: core/url and core/session-id... they are arguments scoped to the calling function above but not def'ed to the namespace I guess http://d.pr/i/JicT

10:16 kzar: Yea that was it, I didn't have the marmalade server added. Confusingly I also had an old version package.el included from before I had upgraded to emacs 24! All sorted now heh, thanks

10:17 clgv: owengalenjones: that code makes not much sense

10:19 owengalenjones: you either have to define `url` in the macro or have it as argument of the macro otherwise the compilation is right that i looks for core/url which is missing

10:20 mpfundstein: does someone know how to get this to work ? https://gist.github.com/MarkusXite/5161718

10:20 clgv: owengalenjones: you most likely do not need a macro there anyway. change get-infos to a function if the body remains like that

10:20 owengalenjones: clgv: ok, I thought that since macros execute pre-compile time their compile would happen in a similar way, if I do have to pass them in then yes it can just be a fn, was hoping to avoid having to pass them in

10:21 clgv: I thought that since macros execute pre-compile, they could use vars like this

10:21 clgv: owengalenjones: I do not understand what you mean. who did you want to use `get-infos`?

10:21 mpfundstein: this one is better: https://gist.github.com/MarkusXite/5161728

10:21 its about dynamic jar file loading

10:21 owengalenjones: clgv: get infos is called like: (open-threaded-magento-connection "http://vmdev/magento/api/xmlrpc" "ojones" "password1" 1 (get-infos :increment_id "sales_order"))

10:22 magento API returns different values for a GET versus a GET/:id so I wanted something that would expand to a GET to find all the possible ids and then a GET/:id call per each

10:23 clgv: owengalenjones: I think you misunderstand macros. but judging from the code in the macro you should just implement your task with functions.

10:26 owengalenjones: clgv: yeah I guess since they expanded when they're called they could reference vars from outside their scope, thanks for clarifying

10:26 I guess *I though*

10:27 clgv: owengalenjones: they even can do that, though it is not encouraged. but not like you tried to

10:30 mpfundstein: no one here with experience in dynamic jar file loading?

10:32 clgv: mpfundstein: you can have a look at how pomegranade does it

10:32 mpfundstein: clgv: thanks

10:32 clgv: mpfundstein: https://github.com/cemerick/pomegranate

10:32 or just use it^^

10:32 mpfundstein: clgv: thanks , didnt know about the lib

10:32 clgv: you want add-classpath

10:43 mpfundstein: clgv: add-classpath only returns nil

10:43 clgv: if the file exists or not

10:44 clgv: mpfundstein: after add-classpath you can use the namespaces in that dynamically loaded jar as if they were namespaces of the program via `use`, `require` and such

10:44 mpfundstein: and yes, there is no check if the file exists. you have to check that yourself before adding

10:45 mpfundstein: clgv: ah ok

10:45 clgv: awesome it works

10:45 clgv: thanks

10:45 clgv: is it possible to unload classes?

10:46 clgv: mpfundstein: I dont think so

10:46 mpfundstein: where you the guy who wanted class updates last friday?

10:47 mpfundstein: clgv: can be

10:47 clgv: :-) because i would still want it, but i dont know if i asked

10:47 clgv: clgv: maybe not then, we talked about classlojure and it had a memory leak when used for that purpose

10:47 Anderkent: well, you can unload classes but it's not easy

10:48 clgv: classloadermagic ^^

10:48 but pomegranate has no implementation for that, last time I checked

10:48 mpfundstein: clgv: ok

10:48 well i am quite happy now that i can load jars on runtime

10:48 :-)

10:50 bpr: mpfundstein: be careful with that. from what i understand, dynamic loading of jars is a shotgun pointed at your foot

10:51 clgv: bpr: I think the problems there arise only if you load classes with the same fullqualified name multiple times

10:52 so, for a plugin system where every plugin "plays nice" this should be fine

10:54 mpfundstein: clgv: it would actually be cool if i could reload classes

10:54 clgv: but first test with pomegranate -> nope

10:54 bpr: clgv: ah ok

10:55 clgv: mpfundstein: even if you could, it would be different than you expected.

10:56 mpfundstein: clgv: actually the only thing i want is, that my daemon loads a jar , executes a method and unloads the jar

10:56 clgv: old objects still alive won't be updated to the new class definition. instead they get incompatible with every redefined function as well

10:56 mpfundstein: clgv: i can EASILY do it with spawning a new JVM. but that always takes ages

10:56 clgv: mpfundstein: what is that daemon supposed to do?

10:57 Anderkent: mpfundstein: create a new classloader, load the jar using it, then remove the classloader reference

10:57 mpfundstein: clgv: executing jobs at remot eservers

10:57 Anderkent: if the classloader gets garbage collected the classes will be unloaded

10:57 mpfundstein: Anderkent: do you have a example? I tried a lot with class loaders but no success :-(

10:57 clgv: Anderkent: mpfundstein: that is what classlojure does. but there is a memory leak. clojure core thread locals most likely

10:58 mpfundstein: clgv: the daemon shall run jobs on remote servers

10:58 clgv: at the moment i shell out every job, which works quite good. but i dont want the overhead of launching a JVM for each job

10:58 bpr: does anyone know how to quit the cljs repl if started using piggieback? :cljs/quit doesn't seem to do it

10:58 mpfundstein: clgv: in C i always did it with shared libraries. that was pretty easy

10:59 clgv: mpfundstein: if you do not use java classes you could just reload the concerned clojure namespaces

11:00 "use java classes explicitely"

11:00 mpfundstein: clgv: yes clojure only. can you point me to some information?

11:01 clgv: mpfundstein: just use (require 'my.ns.that.changes :reload-all) (eval '(my.ns.that.changes/run)))

11:02 bpr: nm, :cljs/quit does work. nrepl.el just doesn't switch the namespace back to user

11:03 (or whatever ns you were in prior to starting the cljs repl)

11:05 mpfundstein: clgv: well it doesnt really reload it

11:05 clgv: :-)

11:05 clgv: think i have to dive deeper into the JVM

11:05 clgv: mpfundstein: it definitely should reload that namespace

11:06 mpfundstein: well

11:06 i do (require 'dummy-job.core :reload-all)

11:06 (dummy-job.core/-main "A")

11:06 shriphani: hi. is anyone here using light table as their primary editor ?

11:06 mpfundstein: and same output as 'before' the change

11:06 clgv: add a (println "reloaded!") in the namespace

11:06 mpfundstein: clgv: ok

11:06 Anderkent: mpfundstein: you need to wrap the main in eval

11:07 mpfundstein: Anderkent: yeah same then

11:07 ok i'll try again from beginning

11:08 clgv: mpfundstein: and you can use (require 'dummy-job.core :reload-all :verbose)

11:08 shriphani: wouldnt do that in production^^

11:10 mpfundstein: https://gist.github.com/MarkusXite/5162130

11:10 reloaded doesnt get printed again

11:11 clgv: what is that exception?

11:12 mpfundstein: clgv: ignore that, its in the child prcess because i tried to to shell/sh "echo 'hello'"

11:13 clgv: well it says it reloaded the namespace.

11:13 mpfundstein: yeah but it doesnt that is weird

11:13 maybe the REPL caches the byte code from the jars or something

11:13 clgv: repl restart with previous lein clean?

11:13 mpfundstein: clgv: if i restart the repl than it works of course

11:13 clgv: the new jar gets loaded and everything is fine

11:14 clgv: mpfundstein: no I mean to retry the test in a fresh repl in a clean project ^^

11:14 mpfundstein: clgv: oooh :-) haha, the output i posted in the gist is from a clean process :-)

11:15 clgv: mpfundstein: humm ok. I used :reload-all in a repl some time ago and it worked as it was supposed to

11:15 mpfundstein: clgv: did you also use pomegranate for that?

11:15 clgv: maybe thats the problem

11:15 clgv: mpfundstein: can you try with a namespace from the project?

11:16 mpfundstein: in principle it shouldnt be pomegranate's fault.

11:16 mpfundstein: clgv: mom

11:17 clgv: mpfundstein: if you must me call a parent please use "dad" ;)

11:17 mpfundstein: clgv: lol

11:22 clgv: it works when the file is included immedieatly

11:23 clgv: so without pomegranate

11:23 i think reload doesnt check if a jar changes

11:23 clgv: thats pretty weird. is that clojure <= 1.4?

11:24 mpfundstein: no

11:24 newest clojure

11:25 clgv: i am pretty sure the problem is the jar.. maybe i'll just distribute my job files as clj files

11:26 edw: Just a reminder, I am very excited about hiring one or more Clojure developers in NYC. <http://labs.actionx.com/tech-jobs.html>

11:26 clgv: mpfundstein: but that is not that likely since the first `require` works, any subsequent should too.. you could ask about it on the mailing list

11:27 mpfundstein: clgv: ok, which one?

11:27 Anderkent: mpfundstein: so are you actually modifying the jar or adding a new jar to classpath?

11:27 mpfundstein: Anderkent: i replace the old jar

11:27 Anderkent: with a new one

11:33 clgv: mpfundstein: imo if you force :reload-all there is no check if the file was replaced

11:33 mpfundstein: clgv: yes

11:33 clgv: that is what i assume.

11:34 clgv: mpfundstein: I mean, imo it is reloaded no matter if it was replaced

11:35 mpfundstein: clgv: ok, i'll do it differnet now

11:35 Anderkent: clgv: it may be that jvm doesnt reload the jar, i.e. clojure asks for the resource for this path and jvm says oh i got it cached since it was in a jar

11:35 mpfundstein: clgv: i will make a separate folder which i add to the classpath, in this folder i put .clj files, this ones i can reload on the fly

11:35 clgv: Anderkent: hmm that might be

11:35 mpfundstein: Anderkent: yes, that is what i assumed already. that the JVM caches the byte code

11:36 clgv: Anderkent but then it should work if he extracts the jar in a foreign directory

11:36 mpfundstein: no only the jar contents.

11:36 Anderkent: yes, or adds new jars on to beginning of classpath instead of hot-swapping contents

11:36 (then the resource request will resolve to a different jar)

11:37 http://stackoverflow.com/questions/6477318/updating-a-jar-whilst-running talks about reloading jars

11:37 clgv: "Java™ archive and compressed files are usually locked by class loaders when they are in use. The files can be updated when the JVM shuts down. Because the cache persists beyond the lifetime of any JVM using it, subsequent JVMs connecting to the cache check for Java archive and compressed file updates."

11:38 mpfundstein: well you could deploy as clojure source files in that directory

11:39 mfpundstein: or have your daemon unzip the jars to a different directory

11:40 mpfundstein: clgv: yeah

11:40 clgv: mmh i will think about

11:40 clgv: the clj file loading is cool as well

11:40 clgv: mission accomplished? :D

11:40 mpfundstein: clgv: not completely :D

11:41 yeah but it works pretty cool already :-)

11:45 ok now i guess i need a macro

11:45 clgv: Anderkent: thanks for your help

11:46 clgv: mpfundstein: try to be sure, since you safe yourself some work ;)

11:56 jonasen: dnolen: ping

11:58 dnolen: Is this a bug (in core.logic.unifier): (unifier '[((?x ?y)) ((1 2))]) evaluates to {?x 1} and not {?x 1 ?y 2}

11:58 but (unify '[((?x ?y)) ((1 2))]) works as expected

11:59 also, (unify '[?x 1]) throws IllegalArgumentException.

11:59 dnolen: Should I open issues on jira for these?

12:01 dnolen: jonasen: yes please

12:08 shriphani: hi. When I do leon run blah_blah &. The job auto-suspends itself. Subsequently, when I do fg, Ctrl-Z and bg, it still stays suspended. Any ideas what I am doing wrong ?

12:10 nDuff: shriphani: Most likely it's trying to interact with the terminal.

12:10 shriphani: nDuff: it is just a println...

12:11 nDuff: shriphani: println won't do that, but attempts to read or to use stty will

12:11 shriphani: ...and Java libraries that unconditionally call stty under-the-hood are something I've run into quite recently.

12:12 shriphani: It's easy to check for one of those cases -- when it suspends itself, use ps and see if it has any subprocesses you don't expect.

12:13 shriphani: ...if that doesn't find it, there's strace and friends, though -- have a quick recipe I can use to reproduce locally? (of the form "check out $this_repo and run $this_command")?

12:13 shriphani: nDuff: not really.

12:13 trptcolin: lein run will have a subprocess for the project. lein pipes in/out between that project subprocess and the terminal. not sure of the details when the main lein process is backgrounded

12:14 hyPiRion would know best

12:14 nDuff: Hmm. If lein is polling the terminal, that would explain it.

12:14 hyPiRion: hmm, who called?

12:15 shriphani: definitely not polling the terminal. All I/O is with a file on disk.

12:15 nDuff: shriphani: The point is that it doesn't have to be _your_ code polling the terminal.

12:15 shriphani: if the outer lein process is doing so...

12:15 trptcolin: hyPiRion: see shriphani's backgrounded `lein run` + output question above

12:16 nDuff: shriphani: if it's polling stdin, rather than the TTY, you can avoid that by executing it with </dev/null on the command line.

12:16 hyPiRion: it's not polling the terminal itself, it's currently polling the filedescriptor input

12:16 shriphani: hmm I was doing lein do clean, run <arg1>

12:16 would that cause an issue ?

12:16 nDuff: shriphani: *nod*. Try that with the </dev/null on the end.

12:17 gfredericks: Any good library set for testing a JSON-based ring app? Else I'll be writing helper functions and using clojure.test

12:17 hyPiRion: But it's correctly redirecting, with the exception of reading eof.

12:17 I'm working on a hack for that, but the Java stuff under the covers is messy there

12:17 shriphani: using just lein run works fine.

12:17 doesn't suspend or anything.

12:19 hmm interesting. So I start it and then run "jobs" and it seems to suspend.

12:21 I can't deterministically repro it but it does happen. Should I report this ?

12:21 nDuff: shriphani: The shell doesn't check for whether things are blocking asynchronously

12:21 shriphani: ...it only does so when it's getting ready to re-print the prompt.

12:21 shriphani: ...so, it's nothing specific to ''jobs''

12:21 shriphani: ...just a matter of timing.

12:22 shriphani: anyhow, does the redirection I suggested earlier help? Have you actually tried it yet?

12:23 hyPiRion: shriphani: If you could condense it into a small repro case I could take a look at it

12:23 shriphani: nDuff: with that I can't repro the suspend.

12:23 so yea that is probably it.

12:24 nDuff: so I should lein run with that each time ?

12:26 nDuff: shriphani: Only the times you care more about being able to suspend your processes than you do about being able to interact with their stdin.

12:26 shriphani: If it's really a big burden, I can write you a little shell function that'll do it automatically.

12:26 shriphani: no i can do that myself. no worries.

12:27 nDuff: lein() { if [[ $1 = run && -t 0 ]] ; then exec </dev/null; command lein "$@"; else command lein "$@"; fi; }

12:28 shriphani: Doing it that way will leave stdin alone if it's directed to anything that isn't a terminal, which is pretty much always the right behavior -- if you're piping input to lein run or redirecting from a file, that's not something we want to break.

12:28 shriphani: ok. thanks!

12:29 nDuff: ...actually, that was really unnecessarily verbose.

12:29 lein() { [[ $1 = run && -t 0 ]] && exec </dev/null; command lein "$@"; }

12:30 ...admittedly, that only works with lein run alone, not something like lein clean, run

12:30 hyPiRion: nDuff: it's `lein do clean, run` these days

12:31 * hyPiRion nitpicks to encourage transition to 2.0.0

12:31 nDuff: hyPiRion: Gotta admit I hate -- really, really hate -- the idea of comma-separating argv subarrays without the comma being its own standalone element.

12:31 lein do clean , run <- would be a syntax that would have me a little less spitting mad.

12:31 technomancy: nDuff: at least it's not hard-coded in this time like it was in lein1 =)

12:32 nDuff: ...argv array elements should be passed through wrappers _exactly_ as given, byte-for-byte, damnit! :P

12:33 hyPiRion: nDuff: Is it a solved problem? just wondering if there's a better practise.

12:33 * nDuff isn't really comfortable with , as a sigil, either; in places where it matters, length encoding is the only way to genuinely encode the full range of possible values... but that's cutting into usability just a little much.

12:35 nDuff: hyPiRion: *shrug*. There are only so many ways to skin the cat, and there's surely room for differences of opinion in the tradeoffs

12:35 hyPiRion: I'm surely opinionated. :)

12:36 technomancy: in lein2 the chaining is just another higher-order task. so if you don't like it, you can make your own.

12:36 nDuff: Nice.

12:37 Anderkent: lein dodo? :P

12:37 hyPiRion: nDuff: Yeah, that's why I was asking if there was a standard way of solving the problem

12:37 nDuff: hyPiRion: ...the most common example is probably find's ';' to terminate -exec strings

12:37 s/strings/arrays/

12:38 hyPiRion: ...of course, part of the problem with that is that it can't be nested

12:39 but the nesting-capable approaches tend to get ugly fast (such as having a prefix sigil on each entry to be added to a prior string, or a numeric run-length prefix)

12:39 That said, there's precedent for the prefix approach, too.

12:39 hyPiRion: so like

12:40 * nDuff tries to remember exactly _who_ does that -- something in the GNU compiler toolchain.

12:40 hyPiRion: lein do2 'javac' 'run -m main' 'repl' could work, right?

12:40 nDuff: That puts it in your job to do your own POSIX-compatible wordsplitting

12:40 and almost nobody does.

12:41 The only implementation I've seen that's even close is Python's shlex module

12:41 Also, it isn't easy to generate properly quoted strings from shells.

12:41 bash has printf %q, but that generates bash-compatible quoting

12:41 ...not POSIX-compatible quoting

12:42 mmmm1: i have a datomic attribute that has :db.cardinality/many and :db.type/string .. how should the value look like?

12:42 nDuff: Let's say you have a shell variable with an arbitrary filename you want to pass as an argument to your run command.

12:42 mmmm1: a vector?

12:42 hyPiRion: ... so this isn't really a problem/issue, just an opinion then?

12:43 :p

12:43 nDuff: That filename can have all _kinds_ of interesting characters in it -- POSIX filesystems even allow newlines

12:43 (and certainly allow commas)

12:43 (including trailing commas)

12:44 hyPiRion: ...if a shell wrapper's command-line argument convention doesn't allow arbitrary arguments to be passed to its children, I don't think there's any reasonable argument to be made that it isn't innately broken, and badly so.

12:44 mpfundstein: clgv: still on?

12:44 clgv: mpfundstein: yes

12:45 nDuff: hyPiRion: Anyhow -- I think the arguments I just made about why 'run -m main' is bad were fact-based, not opinion.

12:45 mpfundstein: clgv: this is how i solved it

12:45 clgv: https://gist.github.com/MarkusXite/5162938

12:45 nDuff: hyPiRion: How do you safely escape an arbitrary filenames you have in a variable to be included in such a string?

12:45 mpfundstein: clgv: i think its ok

12:46 remote-job-queue-worker.core=> (exec-clj "jobs" "showdir")

12:46 clgv: for example

12:47 nDuff: hyPiRion: the prefix approach is always safe in that case; in the case of '' -Xrun -X-m -X"$name" , '' there's no ability to misparse; the comma can't be part of the child content because it isn't prefixed with -X.

12:47 mpfundstein: maybe i ll add a check which tests against the last modification date of the clj file. and only if its newer than last checked require new

12:47 mmmm1:

12:47 hyPiRion: nDuff: Well, I think you lost me. :)

12:48 but I get that commas aren't *the* solution to separating tasks

12:48 /s/to/for/

12:49 nDuff: hyPiRion: I'll go a little further than that and argue that commas as their own argv array elements are better than commas on the ends of other things

12:49 clgv: mpfundstein: ah ok

12:49 nDuff: hyPiRion: because it's better to exclude commands from referencing a filename that ends with a comma than it is to prevent commands from being able to reference any filename with a comma on the end -- the domain you're reserving for your own use is smaller

12:49 ...though in both cases, you're removing things from the domain of possible inputs, and that's bad news.

12:51 hyPiRion: nDuff: well, I guess you can quote it with a double comma at the end, if you need to refer to e.g. "file,"

12:52 nDuff: hyPiRion: Can, but that's a pretty significant bit of overhead to add to whatever tools you're invoking from.

12:52 hyPiRion: In particular, it's something that'll only cause bugs when unusual inputs are seen, so it's unlikely to be implemented.

12:52 With my shell-scripting hat on, better to design a convention to be fail-fast.

12:52 ...where things with bugs are caught early, rather than only on unusual inputs.

12:53 technomancy: typically arguments to lein tasks are treated as clojure syntax

12:54 (using :keywords instead of --flags, namespace symbols instead of file paths, etc)

12:54 so the odds of , being actually significant in task arguments are quite small given that it's clojure whitespace

12:54 nDuff: Hmm.

12:54 Arguments to lein being parsed as Clojure syntax wasn't a convention I was aware of.

12:55 technomancy: there are a few places we take --flags in addition to :keywords

12:55 nDuff: If that's the case, maybe just passing them in large strings isn't so awful

12:55 technomancy: but :keywords are preferred

12:55 nDuff: ...one simply needs to give up the idea of being able to reliably get arbitrary data in from shell at all.

12:55 technomancy: nDuff: well, you can get around that with http://p.hagelb.org/lein-update.html

12:55 I mean, as long as it doesn't need to be convenient

12:56 and provided your task can look in the project map in addition to CLI args, which should always be the case for well-designed tasks

12:58 granted that code is ~4m old and has never been run


13:23 dimovich: what libs are there for reading single char input (without pressing enter)?

13:23 in the terminal ie

13:24 nDuff: dimovich: the read builtin is capable of that.

13:24 dimovich: ...see the -n argument.

13:24 dimovich: thx

13:25 nDuff: ("libs"? this is bash; very little functionality is from libraries, and we mostly don't recommend using them)

13:29 zackzackzack: Does anybody know of a library that has an implementation of immigrate in it?

13:29 I keep using it all over the place and copying it around and I'd like to stop

13:30 bbloom: zackzackzack: i think there is one called nstools

13:31 zackzackzack: Hmm looks like that one hasn't been updated in a while

13:31 technomancy: nstools is great

13:32 it doesn't have immigrate, but that's a good thing

13:32 zackzackzack: Great. So it still works?

13:33 technomancy: haven't used it in a while, but I don't think it uses anything that's changed in recent versions of clojure

13:36 bbloom: lynaghk: how has your experienced been working with metadata for the rewrite stuff?

13:36 Scorchin: I have a seq of defrecord values. I would like to map over the records and run a function against all of the records that is implemented as part of the defrecord. However, running (map #(formatted-response %) tags) doesn't seem to work. Anyone have any ideas?

13:37 I get the following error: Exception in thread "main" java.lang.RuntimeException: Unable to resolve symbol: formatted-response in this context

13:37 (the defrecord is defined in another file)

13:37 bbloom: lynaghk: i keep going back and forth on want stuff i want in metadata or in the objects themselves.. i guess the distinction is one of identity & equality, but it's been awkward to reason about & work with, a little bit anyway

13:39 squidz: does anybody here use clostache? I cant seem to figure out if I can have more than one section for iteration. That is, two sections should not run nested, but side by side

13:39 zackzackzack: Looks like nstools still works! Thanks

13:41 Anderkent: Scorchin: how are you importing the function? With use?

13:44 Scorchin: Anderkent: yup

13:45 It's fine, I've probably done something wrong and will figure it out

13:45 Anderkent: so the record fulfills some protocol where formatted-response is defined - is that in the same namespace?

13:46 formatted-response will be defined in the namespace that declares the protocol, not the record afaik

14:07 patchwork: sshj or jsch?

14:25 Roxxi: Hey, can anyone here point me to a project that uses Rake to do things like run tests, and has clojure src code as the meat of the project?

14:27 My question behind the question is, "are there ways to mix ruby code around running tasks an automation co-located with clojure code, in ways that people would expect?"

14:27 Anderkent: I don't know of any - but if you only want ruby for your tasks, you can write them in clojure pretty easily thanks to leiningens plugin system

14:29 technomancy: Roxxi: you mean like JRuby?

14:30 Roxxi: Nope, neither. All the code is in Clojure, and the desired output is in jars.

14:31 But in terms of other applications that need to work with this library, I need rake tasks, so be incoporated with external rake stuff

14:31 so => to.

14:31 technomancy: hm; no idea then

14:34 trptcolin: Roxxi: yes, i have a colleague who likes using rake: https://github.com/8thlight/hyperion/blob/master/Rakefile - it's nothing fancy, just shelling out.

14:35 [to lein]

14:38 Roxxi: Thanks trptcolin

14:39 hyPiRion: trptcolin: For a second there I was asking myself "What? Is trptcolin my colleague? And when did I begin to use rakefiles?"

14:39 technomancy: an impostor!

14:39 ~guards

14:39 clojurebot: SEIZE HIM!

14:40 amalloy: hah, i thought so too

14:40 trptcolin: :)

14:41 hyPiRion: i kind of wish only the capitalization was different to make it extra confusing

14:41 technomancy: hyPiRion: stealth job offer; you started on tuesday

14:41 hyPiRion: technomancy: wohoo

14:43 I should make a repo named 8thlegth, so that I can get my revenge.

14:44 squidz: are people moving from enlive to laze?

14:44 *lazer

14:45 Raynes: Some people are. Not everybody.

14:45 I know several people who are using it, but I don't really have a number.

14:46 squidz: Raynes: youre the author right?

14:46 Raynes: Yes.

14:47 squidz: how do you see the template scenario playing out for clojure in the near future?

14:48 Raynes: The templating landscape has always been pretty varying. All of the solutions tend to be wildly different, so there are always a number of people using all of the options.

14:48 squidz: what do you use personally?

14:48 Raynes: Lots of people will keep using hiccup, lots of people are starting to and will continue to use clabango, lots of people use enlive, and laser is new so people are starting to use it as well.

14:48 Well, laser. Dogfooding and what not.

14:49 Really, there is no best solution. If you're trying to decide what to use, just pick whatever one makes you happiest. All of the libraries are maintained and used.

14:49 squidz: yeah understandable

14:49 creese: Can someone explain why this is not allowed? (def some_string "some_string") ?

14:49 abp: I'm using hiccup because I want to stay writing Clojure all the time.

14:50 Raynes: creese: It is allowed.

14:50 squidz: Raynes: i made several templates using Clostache, but hit a wall where i just didnt have enough flexibility. I'm considering switching beacause of it

14:50 Raynes: You shouldn't name things with underscores though, but Clojure doesn't complain.

14:51 squidz: https://github.com/Raynes/refheap is a large example of laser-based source code.

14:52 squidz: thanks, i know refheap but havent looked at the code and didnt know laser was used

14:52 creese: ah, it's (some_string) that isn't

14:52 thx

14:52 Raynes: creese: You aren't defining a function here, just a name.

14:52 creese: When you try to call it you're calling the string.

14:52 (defn some-string [] "some-string")

14:53 That'd define a function that returns the string and then you could call it.

14:53 That's pretty useless, but just making the point.

14:54 creese: I don't want to call it, I just wanted to check what was getting set (println some_string)

14:54 thanks for pointing out what was going on

14:54 clojurebot: We live to serve.

14:58 Raynes: Hahaha

14:59 ~botsnack

14:59 clojurebot: Thanks! Can I have chocolate next time

14:59 Raynes: No.

15:10 ivan: ~chocolate

15:10 clojurebot: Cool story bro.

15:10 ivan: clojurebot: be more grateful

15:10 clojurebot: excusez-moi

15:12 squidz: clojurebot is pretty cool

15:16 gfredericks: clojurebot: clojurebot is pretty cool

15:16 clojurebot: 'Sea, mhuise.

15:17 gfredericks: clojurebot: what is pretty cool?

15:17 clojurebot: Pardon?

15:18 hiredman: clojurebot: pretty cool?

15:18 clojurebot: pretty cool is not a benchmarking platform

15:18 hiredman: clojurebot: pretty cool?

15:18 clojurebot: pretty cool is a multimap

15:18 hiredman: clojurebot: pretty cool?

15:18 clojurebot: pretty cool is clojurebot

15:19 gfredericks: so "is" is commutative?

15:19 hiredman: yes, the inference assumes it is

15:19 gfredericks: clojurebot: is is commutative

15:19 clojurebot: You don't have to tell me twice.

15:21 bbloom: clojurebot: twice.

15:21 clojurebot: I don't understand.

15:23 llasram: clojurebot: commutative?

15:23 clojurebot: commutative is is

15:26 ivan: clojurebot: not awesome?

15:26 clojurebot: Excuse me?

15:26 ivan: clojurebot: awesome?

15:26 clojurebot: awesome is stuartsierra

15:26 stuartsierra: Oh, that's kind of you.

15:32 tippenein: clojurebot is a charmer

15:33 llasram: clojurebot: charmer?

15:33 clojurebot: Titim gan éirí ort.

15:37 yedi: is there a nanoc equivalent for clojure?

15:37 doubt it

15:38 nDuff: yedi: it'd be a question more likely to get answers if you described it in terms where people who've never heard of nanoc could help.

15:39 yedi: good point, not sure that it's worth it... but it's library for creating static sites

15:39 nDuff: https://github.com/liquidz/misaki https://github.com/nakkaya/static

15:39 and that's just the first two Google hits.

15:40 https://code.google.com/p/molehil/

15:41 yedi: ...or, to have a better idea of where/how to search in the future: http://www.clojuresphere.com/?query=static+site

15:43 yedi: nDuff: thanks a lot

16:02 creese: What scheme should I use when connecting to postgresql via jdbc? Some places I've seen "postgres", other places "postgresql", or are these interchangable?

16:03 technomancy: postgres vs postgresql drives me nuts

16:06 trptcolin: vs. psql

16:06 ;)

16:07 Raynes: technomancy: postgresqelpostgrespsql.

16:07 trptcolin: not to mention all the binaries they drop all over the place. createdb? come on guys, it's a great database, but… come on

16:07 Raynes: Yeah, the binaries are batshit insane.

16:07 technomancy: trptcolin: apt doesn't even put the postgres binary on the $PATH

16:07 don't get me started

16:07 trptcolin: o_O

16:08 Raynes: Ever hear of that cool thing called 'git'? Yeah, they do this right.

16:08 technomancy: Raynes: git used to drop like 120 executables on your path

16:08 git-format-patch, git-pull, git-rebase all directly on your path =\

16:09 pjstadig: psql is on my path, i'm not sure what you mean

16:09 technomancy: pjstadig: I mean "postgres"

16:09 nDuff: creese: "postgresql" is the modern database. "postgres" is the name of the old, non-SQL database it was originally built on top of.

16:09 pjstadig: oh the server?

16:09 technomancy: /usr/lib/postgresql/9.1/bin/postgres

16:09 pjstadig: that's because you set it up weird

16:10 technomancy: pjstadig: sudo apt-get install postgresql-9.1 # <- what's weird about that?

16:10 * nDuff holds that not putting the server binary on the PATH is a feature, not a bug.

16:10 pjstadig: technomancy: no you want to run it as your user or something

16:10 technomancy: sure, for development

16:10 pjstadig: it works fine when you run that commant to install it

16:10 nDuff: If a user is directly invoking the server, they should be controlling exactly which version, from exactly which root, etc etc, and otherwise know _precisely_ what they're doing.

16:10 technomancy: I don't want it running in the background when I only use it 10% of the time; that's dumb

16:10 * pjstadig not gonna get into this argument again

16:11 Raynes: Get out of my internet.

16:11 pjstadig: sudo stop postgres and/or not have it start on boot

16:11 technomancy: everyone I know who works with postgres professionally disagrees with you

16:11 (committers, etc)

16:12 nDuff: technomancy: Who's that directed to -- me? (Lots of folks in this conversation)

16:12 Raynes: stadig.

16:12 technomancy: yeah this is a long running debate with pjs and myself

16:13 nDuff: If someone is a committer, they're likely to have multiple build trees for different versions of the daemon, so relying on the PATH to select the right one seems like a really awful idea.

16:13 creese: nDuff: thanks, I forgot about that

16:14 lynaghk: bbloom: metadata for the grammar of graphics rewrites? Or CLJX?

16:15 bbloom: I'm thinking about backing away from core.logic for a while for the grammar of graphics rewrites and doing all of the walking/rewrites with my own code rather than try to shove it into logic-world.

16:15 pjstadig: technomancy: i have not had any problem running postgres the way i do (which is a straight apt install), so obviously you are correct and I'm doing something horribly wrong

16:15 technomancy: and i'm sure you run mysql the same way

16:15 lynaghk: bbloom: no real feelings on metadata vs. magic symbols---being concise/clear is the only requirement.

16:15 pjstadig: if you're going to make postgres hard to setup, then it is going to be hard to setup

16:15 technomancy: I only run away from mysql.

16:15 typically screaming

16:16 I don't think I'm unintelligent, but I am confused by pg_hba.conf every time I open it.

16:16 pjstadig: it makes me sad that you make it sound like there's something wrong with postgres because of the way you insist on setting it up

16:16 technomancy: there are about three different ways to subtly mess up the base case of "I'm using this for development please shut up about permissions"

16:16 llasram: When people suggest MySQL, I generally suggest that it might be better to use a database instead

16:17 Raynes: lol

16:18 nDuff: llasram: If you didn't have something throw away your data every so often, how would you know that your ops staff actually _worked_ as opposed to goofing off all day?

16:18 pjstadig: i generally just apt-get install, let the server run as postgres, and use ident authentication

16:18 and it works like a charm for development

16:18 but i guess i don't really care

16:19 i don't know why i get so defensive about postgres...it's not like i have any personal interest in it :)

16:19 * nDuff mostly has worked with PostgreSQL when developing ops automation, so if there was ever a problem with permissions, replication, configuration, &c., it was a bug in his code he had to fix.

16:19 technomancy: it's really solid technically, it just has a crappy out-of-the-box experience, especially with apt-get

16:19 nDuff: s/when developing/while owning/

16:20 yazirian: i maintain that is the packaging and not the product

16:20 and yeah pg_hba.conf is an island of mystery, shrouded in shrubbery

16:20 llasram: nDuff: Well, we're devopsing at my company... Non-joke point though *notes to test backups*

16:20 technomancy: yeah, I think expecting people to take the time to understand pg_hba.conf is reasonable for production use.

16:21 maio: I would like to read some interesting/nice real world Clojure code - could someone point me to nice codebases? I would prefer applications to libraries. So far I have read through ring sources and I was surprised how small it is :) (but it's lib)

16:21 technomancy: it's just an obvious gaffe for it to be required for development

16:21 maio: https://syme.herokuapp.com is only 500 lines; nice and juicy. =)

16:22 yazirian: i don't believe it is? or perhaps a more accurate way of saying what i mean is, its the package's fault for installing a database that you can't actually connect to

16:22 i've argued with it over that too, depending on the system and the time in history, usually over whether users were actually created or not

16:23 creese: I installed postgresql on arch, followed the steps in the wiki. I was un and running in 5 minutes

16:23 technomancy: five minutes to start using a database is ridicuolus

16:23 yazirian: and pg_hba.conf adds that weird layer of not always knowing if it expects to map your unix level user somehow or not, which... and my memory may be faulty here... i believe results in a different (and somewhat confusing) error

16:23 technomancy: rabbitmq says explicitly in their tutorial if it takes longer than 5 minutes to file a bug report

16:23 xeqi: I hope when I get to adding postgres in a moment I can just make a pallet recipe for it

16:23 maio: technomancy: seems like nice project :) thanks

16:24 technomancy: maio: I have a few open features if you want to take a shot at hacking on it =)

16:26 * nDuff has never had building a Postgres recipe/module be in any way a quick thing to do -- but both times he's done it, the requirements have included hands-free replication setup.

16:26 nDuff: ...and especially pre-SR, that was something involving some significant heavy lifting.

16:26 hugod: xeqi: there is a pallet crate for postgres - just needs updating to 0.8

16:26 xeqi: hugod: hurray!

16:27 technomancy: nDuff: if it's your job to care about DB configuration that's another story. I'm thinking of the use case of someone like maio who wants to hack on syme and has to spend 5m reading up on a wiki because the apt packaging assumes you're going to be using it in production, so he gets bored and looks for a project that uses mongodb instead.

16:27 no offense maio =)

16:27 nDuff: ...actually, s/both/all/; I think it's been three.

16:28 maio: technomancy: I will certainly look at it :)

16:28 technomancy: I'm just saying it's appropriate for casual contributors to have a short attention span.

16:28 and casual contributors are the best =)

16:29 hyPiRion: I'm not sure how to interpret that

16:29 technomancy: hyPiRion: wait, serious contributors are great too! it's just that the casual contributors have overwhelming numbers on their side.

16:30 nDuff: technomancy: *shrug*. I'm not sure I want people who care so little about correctness as to be happy with MongoDB to be contributing to my projects. :P

16:30 Raynes: I'll keep that in mind nDuff.

16:30 * nDuff is doing work right now where concurrency semantics are critical, and has a few more bones than usual to pick with MongoDB.

16:30 technomancy: actually it's funny you should mention that; syme is a project where correctness is not the highest priority

16:31 nDuff: (Designed for all the cross-node coordination to be done by ZooKeeper, and got pushed into doing it with Mongo for reasons related to ops resources/timeline)

16:31 technomancy: so I picked postgres in this case because I know it, not for any technical reasons

16:32 hyPiRion: technomancy: Yeah, I was about to ask about the quantities of contributors, because I expected that "casuals" are the most common species

16:32 henceforth the most valuable, in a way

16:34 * Apage43 works on a db, and occasionally does dogfood projects. DB in question usually operates in a correct manner, but has a feature where it can .. not do that. I can't come up with a dogfooding project where I don't care enough about correctness to actually try it out.

16:36 Apage43: Suppose I could always use zookeeper over the top of it, but that feels like cheating.

16:58 dnolen: hmm, looks like Dart's output isn't much better CLJS ;) http://blog.sethladd.com/2013/03/i-shrunk-my-dart-to-js-code-by-11x-and.html

17:00 gf3: Do we sourcemap yet?

17:01 dnolen: gf3: nope

17:02 maio: technomancy: wow it actually works :) it started EC2 instance with technomancy/syme :)

17:02 tomoj: I know you were looking for help on that, have you found anyone? I'd be willing to take a look in the next couple weeks

17:02 technomancy: maio: high five! o/

17:02 Frozenlock: ohpauleez: Moving from Noir (and fetch) to compojure and shoreleave-remote-ring. Any 'gotchas' I should be attentive for?

17:03 Raynes: gf3: Some men just want to watch the world burn.

17:03 ohpauleez: Frozenlock: None that come to mine. You can use shoreleave-baseline as a…. baseline … for what your app might look like

17:03 gf3: Raynes: *shakes fist*

17:03 Frozenlock: ohpauleez: Will do, thanks :)

17:04 maio: technomancy: i'm impressed :) BTW it would be nice if one could specify which region should be used for EC2 instance

17:04 ohpauleez: np! Ping me if you hit some snags

17:04 technomancy: maio: yeah, that would be a good improvement.

17:04 ohpauleez: Frozenlock: Will you be at ClojureWest?

17:04 technomancy: feel free to open an issue and/or a pull request =)

17:05 I'm thinking it should let you pick an AMI too

17:05 and those are tied to regions, right?

17:05 Frozenlock: ohpauleez: I will not. I hope everything will be recorded!

17:06 technomancy: ohpauleez: hey I forget; did you want me to bring by touchstream to the conference next week?

17:06 or was it someone else

17:08 ohpauleez: technomancy: No, that would be me. I'd love to check it out, but don't feel like you need to haul extra stuff around

17:08 maio: technomancy: I will try to write some code. I'm EC2 newbie, but I wanted to play with it anyway :) This seems like good opportunity

17:09 technomancy: ohpauleez: I'm taking the train, so no TSA nonsense; will probably have room for it. =)

17:09 maio: technomancy: is it easy to run syme locally or should I prepare for some complications?

17:10 technomancy: maio: I think it should be easy to run locally; I explained in the readme what config is required. let me know if you run into any issues.

17:11 hm; the PUBLIC_KEY stuff is not needed

17:11 maio: technomancy: ah I see it. Seems easy. I'll let you know if I encounter some issues.

17:11 technomancy: I think it's just oauth and postgres that need setup

17:12 maio: I already use local postgres for my stuff so that should be no problem

17:22 TimMc: Do Clojure transactions have any guarantee about *when* a failing transaction is stopped for retry?

17:23 E.g., if I call ensure in a transaction, does it abort right then and there if the ref has been written to from elsewhere, or might it wait until the end of the dosync?

17:24 (Yes, I'm sort of up to no good.)

17:24 gfredericks: you figured out how to dosync in swearjure?

17:24 TimMc: Alas, no. :-P

17:24 gfredericks: "turns out syntax-quote is weirder than we thought..."

17:28 TimMc: Basically, this is about doing mutation to a thing in a ref after all the commute/alter/ref-set/ensure calls in the dosync have completed.

17:29 I'm guessing that I can't rely on a dosync to not fail at the end.

17:29 brehaut: TimMc: have you looked at http://java.ociweb.com/mark/stm/article.html ? i think its still the most detailed look at the imp

17:31 gfredericks: &(let [as (atom (atom (atom 5)))] (swap! as swap! swap! inc))

17:31 ,(let [as (atom (atom (atom 5)))] (swap! as swap! swap! inc))

17:31 clojurebot: 6

17:32 gfredericks: ,(-> 5 atom atom atom swap! swap! swap! inc)

17:32 clojurebot: #<ArityException clojure.lang.ArityException: Wrong number of args (1) passed to: core$swap-BANG->

17:32 lazybot: ⇒ 6

17:32 gfredericks: hm

17:33 ,(-> 41 atom atom atom atom (swap! swap! swap! swap! inc))

17:33 clojurebot: 42

17:33 gfredericks: ^ protip

17:33 amalloy: TimMc: have your dosync block return the committed value of the ref, and then mutate it outside

17:33 brehaut: ,(-> 41 identity identity identity identity inc)

17:33 clojurebot: 42

17:34 gfredericks: brehaut: that's silly

17:34 amalloy: (.mutate (dosync (alter r f args)))

17:34 TimMc: gfredericks: I'll keep that in mind, thanks.

17:34 devth: seems I can't ns-unmap a var that was defonce'd. true?

17:35 TimMc: devth: Maybe you just need a bigger hammer.

17:35 amalloy: devth: that seems unlikely

17:35 TimMc: brehaut: I'd like something that will work with any future implementations of the same abstraction.

17:36 amalloy: TimMc: does my suggestion address your problem, or did i misunderstand the goal?

17:36 TimMc: amalloy: It's a ref of a map of atoms. reset!ing the atoms is the mutation here.

17:36 I could make them all refs... are there scaling issues there?

17:37 devth: amalloy: you're right, it works in my repl. didn't work when evaling in a remote env, not sure why.

17:37 TimMc: I mean, what happens if there are a bajillion refs in a transaction?

17:38 amalloy: TimMc: what does your answer have to do with my question? it seems like you're implying my suggestion doesn't apply because the object in question is an atom instead of a java object

17:39 unless you need to see the atoms' values change while still inside the transaction, this should be a workable approach

17:39 TimMc: amalloy: Sorry, I didn't exactly answer the question you asked. :-P

17:40 hiredman: TimMc: use an agent

17:40 TimMc: I think I've answered my own question: The mutation of the atoms really does need to participate in the transactional logic.

17:41 hiredman: (let [a (agent nil) r (dosync do stuff (send-off a ..))] (await a) r)

17:41 TimMc: (so they should be refs, or values in a map in a ref that keeps getting altered)

17:42 Frozenlock: ohpauleez: does the middleware need to be in a particular position? I'm getting this error "POST https://some-website/_shoreleave 404 (Not Found)". :-/

17:43 TimMc: hiredman: So, send all the atoms to an agent that swaps them?

17:43 hiredman: sure, or any kind of io, or whatever

17:43 agent sends don't happen until the transaction commits

17:44 TimMc: Is there any guarantee of non-interleaving of agent sends from multiple transactions?

17:45 jjido: TimMc: why?

17:45 hiredman: TimMc: if you create an agent just for that transaction, then yes

17:45 each transaction will have its own agent, so no interleaving

17:50 gfredericks: (def foo (partial ...)) is lame for metadata :(

17:52 ,((((((partial partial partial partial partial +))))))

17:52 clojurebot: 0

17:54 amalloy: hiredman: how is (let [a (agent nil) (dosync blah (send a (fn [_] (mutate x))))] (await a)) different from (mutate (dosync blah x))?

17:56 modulo me retying your code badly

17:57 hiredman: amalloy: it is just nicer, if you have a complicated set of actions inside a dosync, together with some arbitrary io based on say, and intermediate result

17:58 amalloy: that's fair. your version can implicitly close over locals, whereas mine requires explicitly marshalling them around the dosync boundary

17:58 ohpauleez: Frozenlock: Middleware *shouldn't* need to be in any order

17:58 but I've found some orders to be problematic

17:59 Frozenlock: ohpauleez: yeah.. I think I've pinpointed the problem. rpc returns a 404 response if it fails to find a function. I've checked the `remotes' atom and everything looks fine, so my problem must be in the cljs side.

18:00 ohpauleez: Frozenlock: Are you using the macro? Or calling the functions by hand?

18:01 and that is correct, you'll get a 404 for remotes that aren't found

18:02 Frozenlock: Doing the same as in the readme "(rpc/remote-callback :remote-fn..." but with a compiled cljs. I might have to fire up the cljs repl to see in details what's happening.

18:06 konr: what UI technology should one use for mobile? Some standalone jquery-mobile clone that doesn't depend on jquery?

18:06 ohpauleez: Frozenlock: That readme is outdated and needs to be updated

18:06 it's encouraged you use the macro because it makes sure that the calls are being formatted correctly

18:07 one second

18:07 Frozenlock: The `rpc' macro?

18:07 ohpauleez: Frozenlock: https://github.com/shoreleave/shoreleave-baseline/blob/kitchen-sink/src/baseline/client/main.cljs#L24

18:08 yep

18:08 the macro by default takes a `success` handler, but you can pass it an optional error handler too

18:09 reference the `kitchen-sink` branch of baseline for more tips // usage

18:09 Frozenlock: Quite a sexy macro :)

18:11 ohpauleez: :)

18:12 Frozenlock: So if I understand correctly, with this macro I don't need to wrap the arguments in a vector? It acts as a normal function?

18:16 ohpauleez: Frozenlock: That is correct

18:22 pocho: does anyone know of a super elegant way to implement cross product in clojure?

18:23 it seems like theres some amazing solution u there

18:23 brehaut: (fn cross [A B] (for [a A b B] [a b]))

18:24 jjido: [a b]?

18:24 brehaut: return a vector of a and b

18:25 whatever operation you want with both elements

18:25 (fn cross [f A B] (for [a A b B] (f a b))) if you wish

18:25 ,((fn cross [f A B] (for [a A b B] (f a b))) * [1 2 3] [4 5])

18:25 clojurebot: (4 5 8 10 12 ...)

18:27 bbloom: lynaghk: yeah, i have no plans to use core.logic for rewrites. predictability is valuable, so carefully planned passes and ordered choice (eg pattern matching) is preferable, if slightly less flexible/extensible

18:27 amalloy: brehaut: i don't think cross product is the same as cartesian product

18:28 like, i have to agree cartesian product is the easier and more common question, but he actually asked for cross product

18:28 brehaut: amalloy: ah i think you may be right

18:29 amalloy: brehaut: i do like your proposed policy of just reinterpreting hard questions as easy ones, though. i think that's practically standard in most irc channels

18:29 pocho: (defn cross [vec-a vec-b] (let [a (cycle vec-a) b (cycle vec-b)] (map (fn [ind] (- (* (nth a (+ ind 1)) (nth b (+ ind 2))) (* (nth a (+ ind 2)) (nth b (+ ind 1))))) '(0 1 2))))

18:29 this is the best I have

18:29 but i think theres something prettier out there

18:30 brehaut: amalloy: however, 'cross product' is a (colloqual) synonym for cartesian product

18:30 pocho: I meant cross product

18:30 with vectors

18:32 jimduey: If you're interested in core.typed, here's my write up of my first day's explorations

18:32 http://www.clojure.net/2013/03/14/Typed-Clojure/

18:33 dnolen: jimduey: nice

18:34 dakrone: jimduey: do the references to (U ...) in your examples need to be (t/U ...) ?

18:34 jimduey: dakrone: Yep.

18:34 brehaut: jimduey, dakrone i dont think they do.

18:35 Apage43: pocho: you might find https://github.com/clojure-numerics/core.matrix interesting, depending on what you're doing.

18:35 brehaut: jimduey, dakrone: in my experimentation i've been only importing the symbols i need and ive never imported U, I or Fn

18:36 jimduey, dakrone: they are part of the type grammer rather than types (such as Option)

18:38 jimduey: Actually, I'm bleary after staring at this all day. I'm pretty sure brehaut is correct.

18:39 dakrone: okay, makes sense

18:39 brehaut: just double checked. U doesnt need to be qualified, and isnt actually a memory of the clojure.core.typed ns

18:40 jimduey: did you see https://github.com/brehaut/re.typed ?

18:40 (one of my experiments with core.typed)

18:41 jimduey: I hadn't. Was it successful?

18:41 brehaut: yeah

18:41 its trivial though

18:41 amalloy: pocho: https://www.refheap.com/paste/04599950ebceed484c8ce05ec isn't any shorter, but it's structured to be familiar in "shape" to the xyzzy mnemonic

18:41 brehaut: i just ported the re-* functions from clojure.core to a more types friendly API

18:42 jimduey: (because the types for core's re- functions return (U nil String (IPersistentVector (Option String)))

18:42 jimduey: my other experiment, https://github.com/brehaut/ring.typed/, is is progressing more slowly

18:43 jimduey: I'll take a look at those tomorrow.

18:58 Frozenlock: ohpauleez: I'm lost :(

18:59 I checked what cljs was sending: it's indeed a post request, but the query-string is nil, without any params.

18:59 Or rather that's what the ring side is receiving.

18:59 tyler__: how do i map different things to something. e.g. (map :tags some-thing) and then have (map :names some-thing) but in one statement

18:59 technomancy: tyler__: comp the two keywords together

18:59 hiredman: statement...

19:00 Frozenlock: or juxt, depending of what you want :P

19:00 brehaut: technomancy: wait, comp? not juxt?

19:00 technomancy: well the question was ambiguous

19:00 brehaut: fair

19:01 tyler__: im not sure whats possible so its hard to frame whats wanted ;)

19:01 amalloy: c'mon, technomancy, you just have to something the something

19:01 brehaut: ,(map (juxt inc dec) [1 2 3])

19:01 clojurebot: ([2 0] [3 1] [4 2])

19:01 brehaut: ,(map (comp inc (partial * 2)) [1 2 3])

19:01 clojurebot: (3 5 7)

19:01 technomancy: amalloy: fsbot in #emacs has a great ,excuse command that generates random technobabble

19:01 <fsbot> We need a new Internal Magnetic Mass Membrane.

19:01 tyler__: i want juxt thnx

19:02 brehaut: tyler__: of course you do. juxt all the things

19:02 tyler__: i have heard of juxt but never groked it until now

19:02 arrdem: (map (juxt inc dec #(* 3 %)) (range 4))

19:02 ,(map (juxt inc dec #(* 3 %)) (range 4))

19:02 clojurebot: ([1 -1 0] [2 0 3] [3 1 6] [4 2 9])

19:02 arrdem: 0.o

19:03 amalloy: aw but it's all star trek flavored. i would have preferred a mix-n-match approach

19:03 ohpauleez: Frozenlock: Just clone shoreleave-baseline and checkout the master and kitchensink branches

19:03 that has all the middleware hooked up, a sane file layout, etc

19:03 if I had more time, I'd make it a line plugin

19:04 tgoossens: Any tips for a 1 hour talk on "why clojure". Audience: people who know nothing about clojure to people who have initiated themselves a bit

19:04 I considered starting to talk about complexity in software

19:04 *consider

19:04 brehaut: tgoossens: juxt

19:04 technomancy: brehaut: (constantly juxt)

19:04 amalloy: oh, brehaut. too funny, and yet i can't bear to (inc) you for such an awful suggestion

19:05 Frozenlock: ohpauleez: Well yeah, if I was starting from scratch...

19:06 brehaut: technomancy: lol

19:06 tgoossens: i think starting about complexity in software is a good start. Then talking about how imperative languages are going in this context.

19:06 then going towards the topic of FP

19:06 technomancy: out of the tarpit! =)

19:06 tgoossens: exactly

19:06 brehaut: tgoossens: careful there, you dont want to put your audience on the defensive

19:06 ohpauleez: Frozenlock: Ahh you're cutting a project over

19:07 tgoossens: that's what i'm basing myself on a bit

19:07 technomancy: it was a great paper (read it recently )

19:07 ohpauleez: Usually, unless I have a really good reason to, I attempt to keep codebases as stable as possible. Including dependencies

19:08 tgoossens: brehaut: its for a clojure meetup. So maybe it is an audience that is open for such talk

19:08 but you have a point

19:08 (first belgian clojure meetup btw :p)

19:08 amalloy: tgoossens: i wrote a blog post about that a couple years ago, which might be useful enough to steal some bits from: http://amalloy.hubpages.com/hub/What-is-Clojure

19:09 technomancy: functions for president!

19:09 brehaut: tgoossens: i like to frame the advantages in terms of tradeoffs (or 'tradeoffs'), like we exchange mutability and side effects for improved reasonability.

19:09 etc

19:10 sure, if you get into FP you realise its generally not actually a tradeoff, but it'll certainly look like it to your audience

19:11 anyway lunch

19:18 ravster: hello all

19:23 tgoossens: amalloy: thanks i'll take a look at it

19:25 brehaut: i'll keep it in mind thanks!

19:25 brehaut: enjoy your lunch!. I'm going to bed( past midnight here :) )

20:00 Frozenlock: ohpauleez: It was indeed a wrapper order problem. I placed rpc in the first position and now it works...

20:00 ohpauleez: splendid

20:00 Frozenlock: Yeah, now I must find which wrapper is responsible for my lost time :P

20:01 * ohpauleez hopes it isn't him

20:02 Frozenlock: I'm seeing that you have a custom anti-ring-forgery. Will it be merged with the 'official' one eventually?

21:24 gadget: using enlive, if i have some html that looks like <th>some words <br /> more words </th> how do i get rid of that br?

21:24 brehaut: substitute nil

21:25 with the apropriate selector

21:25 [:th :br] (substitute nil) perhaps

21:25 gadget: ooh ok i'll try that, thanks!

21:54 Rich_Morin: I'm having trouble finding the slide set for http://blip.tv/clojure/clojure-concurrency-819147 - I don't see any links to them/.

21:55 nm

21:59 akhudek: is there anything like criterium that reports memory?

22:01 dakrone: akhudek: you'll probably need a profiler for that

22:04 akhudek: I was afraid of that. :-/ VisualVM it is I guess.

22:10 dnolen: boom, http://github.com/clojure/clojurescript/commits/master

22:11 source map work merged into master (not ready yet, but it's there for folks to contribute to)

22:11 http://github.com/clojure/clojurescript/commit/5b7623873ff8713a556f3b52fe1912c98ac8bbc5

22:12 akhudek: very cool!

22:17 bbloom: dnolen: nice!

22:18 dnolen: random git-ism: probably should say what branch you're merging in the commit message, since that information is (sadly) lost when you need to edit the merge commit

22:21 dnolen: if you want that automatically, what you can do is to merge from master->branch and then it that commit you can write something like "synced up with master", then when you go to master and merge from the branch, it will automatically get a nice commit message when the merge applies cleanly

22:21 dnolen: kinda shitty that git won't remember that for you tho :-/

22:22 i wish it gave you a default message like "Merged branch 'foo' in to 'master' resolving conflicts"

22:22 technomancy: I think magit does that for you

22:22 bbloom: technomancy: ?

22:22 technomancy: bbloom: the only thing that makes using git bearable

22:23 http://philjackson.github.com/magit/

22:23 bbloom: technomancy: lol. you silly emacs people :-)

22:23 technomancy: I would have given up on git long ago if I were stuck using the CLI

22:23 it's so bad =(

22:23 bbloom: technomancy: i actually quite like git's CLI once i got the hang of it, but i might have stockholm syndrome

22:24 akhudek: I too find it ok.

22:24 bbloom: technomancy: and i used to use Hg, which i quite liked before git clicked for me... and when git clicked for me, i started to view Hg as easy and Git as "simple" in the clojure-y sense

22:25 technomancy: I maintain a git-based service for my day job.

22:25 it is a pile of hacks.

22:25 ToxicFrog: What's the recommended way to do simple TCP networking in clojure?

22:25 technomancy: its only strength is its simple data model

22:25 (and tooling around it like magit and github of course)

22:25 bbloom: i use tpope's fugitive (whose name now makes FAR MORE SENSE TO ME, in light of this foreplay / fireplace fiasco) pretty rarely... almost exclusively for :Gmove so that i can rename a file and not lose my place in the buffer

22:27 johnmn3: So I'm building an IM application using CLJS. Hoping that using CLJS will help make it easy to port it to multiple platforms.

22:27 bbloom: :Gblame, :Gadd, and a few others occasionally too....

22:27 johnmn3: where other platforms == ?

22:27 johnmn3: android, iphone, etc.

22:27 anything with a webcomponent

22:27 for apps

22:27 html5

22:28 bbloom: johnmn3: ah, yeah, CLJS compiles to normal JS, so you can use Titanium or whatever you need

22:28 johnmn3: but you'll probably want to make sure whatever you need cleanly compiles under Google Closure w/ advanced optimizations

22:28 johnmn3: that's pretty much the only thing to watch out for up front

22:31 johnmn3: well, I've made pretty good progress on it so far...

22:31 but I'm hitting a road block with LocalStorage.

22:32 bbloom: dnolen: do you have any notes on what is or isn't done/workign ?

22:32 johnmn3: I need to let the user pick a file and then I want to slice and dice the file, being able to seq over the individual bits in the file.

22:32 I've been scouring the web for two days and I can't figure out how to do it with cljs

22:33 bbloom: johnmn3: can't you just do normal JS interop?

22:34 dnolen: bbloom: there's just not enough information right now for it to be useful. we need column information on symbols

22:34 bbloom: dnolen: ah yes, the dopey reader

22:34 dnolen: then no more emitting strings for vars everywhere, everything must go through emit :var

22:34 bbloom: dnolen: oh yeah, i think i ran into that w/ my experiment JS AST

22:35 dnolen: bbloom: after that we should be solid

22:35 and I think the only language that provides a solution all the way through advanced compilation of some kind.

22:35 compile to JS lang I mean.

22:36 johnmn3: I've found a few js tricks to do it, but I can't figure out how to do the interop

22:36 I get reader errors when trying to read the file.

22:37 bbloom: johnmn3: please provide specific examples of JS you want to emulate and your attempts at interop that have failed

22:37 johnmn3: the more concrete you are, the better we can help you here

22:37 use refheap or gist

22:38 johnmn3: okay, thanks! Lemme go back and find what I was working with

22:40 kzar: I've got my project running with a repl using M-x nrepl-jack-in, but is there a way to reload things after I modify my project.clj? (Other than killing the buffers and doing it again?)

22:40 Frozenlock: technomancy: any opinions on magithub?

22:40 technomancy: Frozenlock: it's on my list of things to try

22:42 TheBusby: kzar: if you're just adding dependencies you can use pomegranate, if not I'd curious if there is a better way as well.

22:42 technomancy: kzar: no good way unfortunately

22:43 kzar: fair enough

22:43 So far nrepl seems quite fancy though, it's nice to not need swank any more

22:43 johnmn3: bbloom: for instance, I'm using shoreleave.browser.storage.localstorage. I store a file in the storage and I can see it in the chrome inspecter as Key: "files" and Value: #<[object Blob]> ... but when I get the object with (storage "files"), I get:

22:43 amalloy: akhudek: you can't really write a "memory criterium" in clojure, since clojure doesn't have access to the internals of the memory-management system (java doesn't either, of course)

22:44 pppaul: i will create life with clojure

22:44 johnmn3: "Error evaluating:" (storage "files") :as "testproject.core.storage.call(null,\"files\")"

22:44 #<Error: Unreadable form>

22:44 bbloom: johnmn3: i don't know anything about local storage, but that looks like to me that it's calling toString or JSON.stringify on your objects

22:45 akhudek: amalloy: I see. I thought there might be more functions like Runtime.freeMemory hiding around.

22:45 johnmn3: I do believe it is actually.. it would be doing that internally, because you have to stringify objects before storing them to localstorage

22:45 so I should JSON.parse the output

22:45 right?

22:45 clojurebot: Equal Rights for Functional Objects is Baker's paper on equality and why it's impossible to define sensible equality in the presence of mutable data structures: http://www.pipeline.com/~hbaker1/ObjectIdentity.html

22:46 ohpauleez: johnmn3: oh no! Storage in Shoreleave?!?!

22:46 You brave soul

22:46 johnmn3: yea

22:46 bbloom: johnmn3: no, it looks like shoreleave is calling read-string for you

22:46 ohpauleez: to the rescue

22:46 :-P

22:46 ohpauleez: it is indeed

22:46 bbloom: ohpauleez: i'll leave him to explain how his library works, heh

22:46 johnmn3: ohpauleez: speak of the devil

22:46 * Frozenlock is watching

22:46 ohpauleez: LS was originally spec'd to store sting values, so shoreleave handles the marshling for you

22:47 it does that by wrapping around Google Closure's Storage prototype

22:47 that it attaches to a bunch of the browser storages

22:47 bbloom: johnmn3: what is the (class x) of the object you're trying to (store x)

22:47 ohpauleez: In the current release, it's very finicking (I was trying to maximize reuse) because of a bug at the prototype chain level

22:48 finicky**

22:48 johnmn3: What are you trying to store, key and value?

22:49 johnmn3: well, I'm able to get something back out of it by doing this: (assoc! store :images (.stringify js/JSON (first files)))

22:49 is the stringify not necessary?

22:50 ohpauleez: not necessary

22:50 it'll read-string back out for you

22:50 kzar: How would you look up Java methods, for example I want to see how to read a BMP and I find myself googling random blog posts etc which I'm guessing isn't the best way

22:50 johnmn3: I'm trying to store an image

22:50 but I want to mangle the bits of the image, and have a seq over the bits

22:51 ohpauleez: johnmn3: Uncharted territory

22:51 johnmn3: I'm firing my environment up right now

22:51 ohpauleez: but, it should be possible. You might have to modify the protocol a bit

22:51 johnmn3: ohpauleez: I don't need access to the bits as they exist in the localstorage

22:51 if I can just get it back out, then much with it in memory

22:52 pppaul: i need to access the bits

22:52 ohpauleez: johnmn3: It would be a HUGE favor if you pinged me if you got it working, so I could recreate it on shoreleave-baseline and add the patch to shoreleave itself

22:52 johnmn3: muck

22:54 ohpauleez: johnmn3: Generally speaking, because of the slowness and size limitations, localstorage isn't ideal

22:54 johnmn3: okay, I changed it to this: (assoc! lstore :images (first files))

22:55 ohpauleez: it's awesome for quick one-off, cross-session book keeping

22:55 I'm about to make dinner, but I'll check in periodically

22:56 johnmn3: and chrome says it has a value in localstorage of #<[object File]> .. but I can't do a (lstore "images").. causes a "Unreadable form" error.

22:57 Is there a better way to store an image? Or would you suggest I use something other than localstorage?

22:57 I noticed webstorage in shoreleave as well. Not sure what the difference is there.

23:00 ah, dinner. so overrated

23:00 anyway, if anyone has advice on how to get a seq over the bits of a file in javascript, I'd appreciate it.

23:16 kzar: johnmn3: Doing bitwise stuff in Javascript is a pain, I wrote https://github.com/kzar/bitratchet-js to make it easier. I've never tried it from Clojurescript though

23:16 johnmn3: thanks kzar !

23:17 kzar: johnmn3: (Actually come to think of it perhaps porting it to Clojurescript / Clojure would be quite a cool project.)

23:18 johnmn3: sounds like it

23:19 kzar: johnmn3: Instead of having an seq of bits I followed the BinData way of dealing with bits which is to define a record and then either read or write it. I mean a seq of bits would be a pain if you then wanted to look at things in terms of a 5 bit number for example

23:20 johnmn3: yea, a seq of bits wouldn't be useful in most cases, I'd imagine

23:21 kzar: johnmn3: You'd have to do the numbers to convert the 5 1 bit numbers into a 5 bit number, I'm not sure how much better that is from just starting with the 8 bit number which is closer to how things work in languages like Javascript anyway IIRC

23:21 johnmn3: I intend on XORing different bits and pieces, of various sizes, and I've built it out to use a string of ones and zeros

23:21 perhaps not the most efficient at the moment...

23:21 kzar: no I shouldn't think so

23:22 my library isn't very efficient in all likelyhood but it's better than that

23:22 ohpauleez: johnmn3: I'd personally store it in an atom

23:22 johnmn3: Its not a high performance, 3d game or anything though.

23:22 ohpauleez: only EDn should go in LS, technially

23:22 johnmn3: ohpauleez: how should I save it between sessions? I'd like to make an app out of it.

23:23 ohpauleez: johnmn3: Look at the HTML5 App Cache

23:23 bbloom: ohpauleez: consider a (assert (= x (read-string (pr-str x)))) heh

23:23 ohpauleez: which I think can easily accept Blobs

23:23 bbloom: good idea

23:23 "here, put things inside of me that you can never get out"

23:23 :)

23:24 bbloom: ohpauleez: i heard a horror story about that, but the details allude my memory at the moment... all i really remember was "yeah, sooo our logs were totally useless"

23:24 lol

23:24 ohpauleez: :(

23:25 yunfan: anyone using enlive on big site?

23:26 ohpauleez: yunfan: For some definition of big?

23:26 zakwilson: nrepl.el shows me the arglist in the repl, but not in source files. Is there a way to enable that?

23:27 ohpauleez: I know of two well traveled sites, one that uses enlive in process and one that uses it as an offline compiler

23:27 yunfan: ohpauleez: M level pv per day

23:27 ohpauleez: and also World Singles

23:27 I *believe* uses enlive

23:27 johnmn3: I'll definitely be using app cache in some capacity at some point

23:28 I think all your resources must be pre-specified in the manaifest, it looks like.

23:28 yunfan: then what about the number of their server? i just hear the story of people reduce their server from 30 to 2 by migrating from ROR to go

23:30 ohpauleez: yunfan: Don't believe everything you read on High Scalability

23:30 most of it is pure hype bs

23:31 akhudek: the thing about rewrites is that they often change the app in more fundamental ways

23:31 ohpauleez: That said, People have handled 100,000+ concurrent connections on well-tuned Jetty instances

23:31 bbloom: ohpauleez: although stories of significant reductions in compute resources when moving off RoR are not uncommon :-P

23:31 ohpauleez: bbloom: that is true :)

23:32 and akhudek point is *very* accurate

23:32 in the re-write, you end up fixing major design flaws from the previous version, by addressing and adjusting the architecture

23:33 That said, I'm more compelled to write serious web systems (especially around services) in Clojure than Go

23:33 dcolish: what's the story for go library versioning?

23:33 * ToxicFrog flails at Saturnine

23:34 ToxicFrog: v0.2 is in clojars, but is for clj 1.2. v0.3 for 1.4 is mentioned on the github but doesn't appear to actually exist!

23:34 yunfan: ohpauleez: its just 30 server to 2 server means huge cost if i deploy service on aws

23:35 ohpauleez: its about money :[

23:39 ToxicFrog: rgrgrgrgrgrgrgrgrgr

23:40 bbloom: yunfan: if you're a startup & you've got employees you've got to pay, then let me tell you: 28 extra servers is CHEAP compared to even a few days of employee time

23:40 johnmn3: how do you get at a specific index of an js array from cljs?

23:40 a Uint8Array, specifically

23:40 bbloom: yunfan: especially if you get a startup deal w/ somebody like rackspace, who will give you significant free resources to try to get you as a lifetime customer

23:41 yunfan: `aget` macroexpands to javascript's indexing operators

23:41 johnmn3: er sorry ^^ that was for you

23:41 johnmn3: okay.. thanks bbloom!

Logging service provided by n01se.net