#clojure log - Oct 16 2014

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

0:17 amalloy: dopamean_: as long as it's hard to mistake an error-response map for a success map, returning a map in both cases seems fine to me

0:22 dopamean_: thanks amalloy

0:35 cddr: With reference to this gist: https://gist.github.com/cddr/ac89b88f93f92b6b913b

0:36 Is there a better way to write encrypt so that the returned value inherits the behavior of the input value?

0:37 for all behaviors except IFn

0:39 Hm, maybe proxy is better for my use-case

0:50 amalloy: cddr: no, you cannot create a forwarding wrapper to an arbitrary object, without knowing what methods to forward

0:52 classes and their methods are static things on the jvm, which must be known at compile time

0:56 cddr: One alternative I can think of is to use metadata to store the encryptor. Does that seem insane?

0:58 wah! you can't add metdata to keywords

0:58 amalloy: cddr: the things you are saying do in general sound insane, but it's hard to be confident without some idea of why you think this is stuff you should do

1:00 cddr: Trying to implement the encryption part of what I describe here: https://github.com/cddr/crud/README

1:01 I thought the elements of the :storage attribute could be either keywords or functions that operated on an input map (as keywords already do)

1:02 It would be nice if when it was a function, it behaved as a keyword in every other way

1:04 Also "the things you are saying do in general sound insane". Have you been talking to my wife?

1:04 :)

1:06 amalloy: i think you should just have a distinction between two things that are different: a keyword for looking things up, a function for encrypting things. why do you wish they were the same thing?

1:07 cddr: I need the name of the attr that the function will wrap for when I'm generating a datomic fact

1:07 It's probably fine to just implement named as I did in the gist

1:09 Thanks for taking the time to look at this. I appreciate it.

1:12 amalloy: cddr: you can also just use a pair, containing a keyword and a function, instead of a function which is named. there's nothing grotesquely wrong with your reify, but it seems simpler to break things apart

1:13 cddr: Yeah that's a good point

1:30 arrdem: is there a way to make lein dump the project booting command?

1:31 trying to find a way (besides uberjar, there are reasons) for getting lein out of the loop in deployment

1:33 nvm got it

1:38 amalloy: arrdem: proposed names for this feature: lein out-of-my-way; lein self-obsolesce; lein never-mind

1:38 arrdem: amalloy: lein cp-and-gtfo

1:45 tomjack: I wonder if a partition transducer is planned?

1:45 justin_smith: arrdem: lein don't

1:45 tomjack: clojure.core.async/partition got the deprecation notice

2:01 arrdem: Grimoire back online, mod DNS update latency

2:01 now on its own VM and subject to less weirdness

2:02 srid: years ago i stumbled upon the blog of a >50 yr old clojure consultant. i can't seem to remember his blog or name. does anyone remember?

2:05 Jaood: Rich Hickey?

2:07 arrdem: so you made the clojuredocs step it up?

2:07 arrdem: Jaood: I don't think so, but it's possible

2:08 Jaood: there was already a rewrite in progress. if anything I just husled it a bit.

2:09 srid: found it. http://www.markwatson.com

2:12 tomjack: ah, I see that partition-all got a transducer, but not with step

3:50 vise890: hi guys, how do you deal with storing and reading secret variables (like an API token) from code that will be in a public repo?

3:51 arrdem: environment variables ftw

3:52 vise890: is there something similar to dotenv for ruby? (https://github.com/bkeepers/dotenv)

3:53 arrdem: I'm sure there isn't

3:55 You could either pass your configuration as Java system properties, as environment variables or have a config file that you don't put in VC

3:55 which one is appropriate depends on your use case

3:55 I'd lean towards the config file, but I've done the shell/environment value thing before as well

3:56 vise890: OK thanks, I've actually just found this http://yobriefca.se/blog/2014/04/29/managing-environment-variables-in-clojure/ which seems to be exactly what I'm looking for

3:56 thanks anyway arrdem!

3:57 arrdem: np

3:57 hyPiRion: I usually prefer config files too, due to ACL.

3:58 `cat /proc/<pid>/environ | tr '\0' '\n'` is surprisingly easy to do.

5:01 cka3yc: Hello, is there an easy way to zip folder with all its content?

5:22 mping: cka3yc: you mean with clojure?

5:24 cka3yc: yes

5:27 TEttinger: cka3yc: you could use the JVM's built-in .zip support http://www.java2s.com/Code/Java/File-Input-Output/CompressfilesusingtheJavaZIPAPI.htm

5:28 there's some convenience methods here http://stackoverflow.com/a/17966479 cka3yc

5:30 cka3yc: thanks

5:38 visof: hi

5:38 i'm trying to use lein s4-deploy from this page, i got 's4-deploy' is not a task. See 'lein help'., what should i do ?

5:38 https://github.com/antoniogarrote/clj-s4

5:38 is there anybody tried clj-s4

5:43 TEttinger: have you followed the steps at https://github.com/antoniogarrote/clj-s4#running-the-sample-application , visof?

5:43 lein deps may be needed to download the plugin first

5:44 visof: hi?

5:45 visof_: i'm trying to use lein s4-deploy from this page, i got 's4-deploy' is not a task. See 'lein help'., what should i do ? https://github.com/antoniogarrote/clj-s4

5:45 is there anybody using clj-s4

5:45 ?

5:46 weavejester: It looks very old

5:46 Seems like it predates Leiningen 2

5:47 You could try putting it in “plugins” rather than “dependencies” but it might be too old to work with modern versions of Lein

5:48 visof_: weavejester: but clj-s4 as plugin in ~/.lein/profile.clj ?

5:49 weavejester: visof_: Why put it in profile.clj?

5:50 ddellacosta: visof_: I think weavejester was suggesting to put it in the plugins section of your project's project.clj file (vs. the dependencies section of that file)

5:50 weavejester: Yep

5:50 visof_: okay

5:51 weavejester: But don’t know whether it will work. It might, but the plugin/library is very out of date

5:51 ddellacosta: yeah, Clojure 1.2, last update Jan 2011? Good luck...

5:51 you never know I guess

5:55 weavejester: Is the latest melpa cider broken for anyone else?

6:01 CookedGryphon: cider is always broken

6:02 I found one that is not quite as broken as the others in a snapshot about a month ago, and haven't dared update since

6:03 weavejester: I think mine might be broken because I don’t have the GNU ELPA repo explicitly mentioned in Cask

6:04 Maybe I should use melpa-stable as well :)

6:04 CookedGryphon: don't think that helps, 0.7.0 is in melpa-stable, and I couldn't get that to work at all

6:04 I was better with the snapshots

6:05 weavejester: Every so often I check out alternative editors, but they don’t have good vim keybindings

6:05 martinklepsch: When I have a ":profiles {:dev {:env {:yolo "abc"}}}" in my project.clj and a profiles.clj containing: "{:dev {:env {:test "test"}}}" — only the content of the :env key in the profiles file will remain in the merged result right?

6:07 weavejester: have you seen this: http://martintrojer.github.io/clojure/2014/10/02/clojure-and-emacs-without-cider/

6:08 weavejester: martinklepsch: I think my problem is more with emacs generally

6:08 martinklepsch: I love it’s functionality

6:08 martinklepsch: Hate its slowness and general iffyness

6:09 martinklepsch: do you use it in a terminal?

6:09 weavejester: Nope

6:10 martinklepsch: Hm, it's fast for me but my setup is "young" as well

6:10 my vim takes 5 seconds to start :D (probably very bloated setup)

6:12 clgv: martinklepsch: profiles are merged by leiningen

6:12 martinklepsch: you can check with "lein pprint"

6:14 martinklepsch: the documentation said it'd merge recursively, that's why I was expecting both keys to be in the :env map

6:17 weavejester: Lein profiles are merged recursively, though if you have the same profile declared in two locations, only one version is used.

6:19 noncom|2: does anyone use overtone here?

6:21 daniel__: noncom|2: i've dabbled

6:21 clgv: weavejester: really? that's unexpected when everything else is merged and ^:replace metadata can be used as well

6:22 noncom|2: when i require overtone, it first says "--> Loading Overtone..." and then "CompilerException java.lang.Exception: Can't connect to native server - no compatible libraries for your system are available., compiling:(overtone/live.clj:4:38)

6:22 "

6:22 though i have sc installed

6:22 weavejester: clgv: Yeah, it’s a bit of a gotcha

6:22 noncom|2: sc 3.6.6 on win

6:22 weavejester: clgv: For example, if you have a :dev profile in your project.clj and a local profiles.clj

6:22 clgv: noncom|2: some path problem?

6:23 weavejester: indeed

6:23 weavejester: So I tend to have :local/dev and :repo/dev profiles

6:23 clgv: weavejester: and then aliases in the project.clj?

6:23 weavejester: Though maybe I should call them :profiles/dev and :project/dev

6:23 Yeah, :dev [:repo/dev :local/dev]

6:23 clgv: ok

6:24 weavejester: Then I keep profiles.clj out of source control and use it for local overrides

6:24 clgv: weavejester: we should come up with a project.clj programming challenge - sometimes just the configuration options seem almost turing comlete ;) :P

6:24 noncom|2: clgv: probably... i just dont see anything about paths in the getting started man.. looks like i am to investigate more then.. :)

6:25 weavejester: hi! what's about your jmonkeyengine project? how is it going?

6:25 clgv: noncom|2: it was probably written from a linux/mac user(?) ;)

6:26 noncom|2: clgv: that is for sure :) everybody around uses linux or mac :) that's... umm... funny :)

6:26 weavejester: noncom|2: Oh, I realised that the 3D work I was doing wasn’t the problem I wanted to solve.

6:26 noncom|2: So I switched to a ClojureScript/Clojure architecture.

6:26 noncom|2: weavejester: so you have continued with reagi but not with jme ?

6:27 weavejester: noncom|2: For a while, yes. But I couldn’t find a good way of coordinating timing in a reactive system

6:28 noncom|2: So I built Ittyon instead, which is an in-memory database a little inspired by Datomic, but designed for realtime work

6:30 clgv: weavejester: you didn't announce it, yet?

6:31 weavejester: clgv: It didn’t seem like something that would be that useful beyond my usecase, and the API was a little in flux.

6:31 clgv: weavejester: ok ;)

6:31 weavejester: clgv: I was planning on announcing it sometime though

6:33 noncom|2: weavejester: ah, so you have gone to a completely different project.. wow, Ittyon looks interesting! will take a look into it.. just recently was thinking of a in-memory db to use :)

6:33 weavejester: But I imagine those who need a Clojure/ClojureScript distributed database designed for communicating game state across a client/server architecture are kinda niche

6:33 I mean, it might have other uses

6:33 But it was made so I could have a multiplayer game on a website :)

6:36 martinklepsch: weavejester: in a project.clj with :env {:is-dev true} it wouldn't make much sense to go the :profiles/dev :project/dev route, right?

6:37 you could just commit profiles.clj with that single entry and add it to .gitignore afterwards

6:39 weavejester: martinklepsch: Well, you really only need to go down the :profiles/dev route if (a) you want to have local overrides to your project that aren’t in source control, and (b) you already have a :dev profile you don’t want to overwrite, but merge into

6:41 martinklepsch: ok, thanks

6:44 CookedGryphon: is there a reason there's a keep-indexed transducible but map-indexed isn't?

6:44 or is that just a "it hasn't been done yet"

6:45 clgv: CookedGryphon: ah well these consistencey issues are all over clojure.core

6:45 CookedGryphon: but probably you can raise attention to it right now (Jira ticket)

6:46 CookedGryphon: though maybe a separate `index` transducer would be great...

6:48 TEttinger: map-indexed is a weird fn to even have because it's equivalent to map with an extra collection passed to it, (range)

6:48 clgv: TEttinger: but then keep-indexed is weird as well (at least to some extent)

6:49 TEttinger: does keep take multiple collections?

6:49 I rarely use it

6:49 CookedGryphon: TEttinger: that's true, I'd never thought of it like that... it's not implemented like that though

6:49 and no it doesn't take multiple collections

6:49 clgv: TEttinger: no

6:49 CookedGryphon: I might just stop using it and start doing map (range) ... instead

6:50 TEttinger: map-indexed may be more efficient

6:50 who knows

6:50 CookedGryphon: yeah probably is if you're feeding in a vector

6:50 clgv: how would you see an index transducer working?

6:50 clgv: well for an eager mapv it makes sense to have a specialized mapv-indexed which does not need a (range) seq since that would destroy the performance improvements of the eager variant...

6:51 CookedGryphon: would it make tuples, or actually call the next thing with multiple arguments

6:51 clgv: CookedGryphon: that was just a thought since it would avoid the combinatorial explosion of adding indexed to multiple seq functions. I am not sure if it is really realizable

6:52 CookedGryphon: I'd prefer it to work somehow similar to partial with respect to the mapping function

6:53 CookedGryphon: that's maybe a puzzle challenge for this evening ;)

6:53 CookedGryphon: clgv: could be fun when applied to chans

6:53 shouldn't take long to do and make itwork like map with multiple args

6:53 you'd get a unique id for each message passing through a chan... could be useful

6:54 clgv: CookedGryphon: ah right. the multi arity impl for map transducer is probably the blue print for that

6:54 CookedGryphon: then all you need is a volative incrementing integer

6:55 martinklepsch: Are there any great ways to test leiningen templates?

6:55 CookedGryphon: and bob's your proverbial

6:55 clgv: humm are you sure? when you have something like that as goal (def map-indexed (comp (map f) (indexed)))

6:56 you can't really access `f` that way

6:56 CookedGryphon: it would need to be the other way round

6:56 clgv: yeah more like (comp (map (indexed f)))

6:57 scratch the comp ;)

6:57 CookedGryphon: that's still not right though

6:57 clgv: huh why?

6:58 what is your idea?

6:58 CookedGryphon: well, it could work, you'd just be implementing a function which adds an index rather than fitting teh transducer pattern

6:58 i don't know whether that matters as a distinction

6:58 clgv: true, but maybe it's only realizable like that. how'd you do it?

7:00 CookedGryphon:I have to admit that I did not try to implement any transducer so far - so I have a lack of intuition for that ;)

7:00 CookedGryphon: I have only implemented one, so I'm not much better off

7:02 yeah, dunno

7:02 my concern with yours is when the index would get set to 0

7:02 or rather when it would be called and start counting again

7:21 clgv: CookedGryphon: I guess I'll take that as learning exercise ;)

7:25 CookedGryphon: cool, I'd be interested to know how that goes, composable indexed would be much nicer to use than having all the different variations

7:34 justin_smith: noncom|2: https://github.com/overtone/overtone/issues/277

7:36 noncom|2: justin_smith: thanks! for some reason google did not show this page when i was searching... i will try it out :)

7:37 i wish i could help with 64 bits thoug, but i am not really a c/c++ man...

7:39 justin_smith: noncom|2: it was the top google hit for "supercollider native server" - because I remembered there being such thing as internal, and external servers from my time using sc, but the term native server was unfamiliar

7:40 turns out it is a terminology specific to overtone

7:42 noncom|2: justin_smith: alright, that clears things up :) but ther is one more issue - i have installed sc into a non-default folder and (boot-external-server) cannot find it.. is there any way to make it look in a different location?

7:42 or i could just make some invasive surgery on overtone..

7:43 justin_smith: frankly, I have used supercollider but I have never used overtone - I assume there is some configuration available either to your $PATH variable or directly in overtone which would fix this

7:43 noncom|2: well, ok, this problem is much simpler anyway :)

7:53 martinklepsch: hey weavejester, maybe you have any thoughts on this: https://github.com/plexus/chestnut/pull/30 — we're trying to find a good env var setup for a leiningen template..

7:56 weavejester: martinklepsch: Sure

7:56 Let me add a comment

7:57 Kototama: Hi, any idea how to access context parameters with ring?

7:58 weavejester: Kototama: context parameters? Like via a servlet?

7:59 Kototama: weavejester: yes, tomcat context parameters

8:00 https://tomcat.apache.org/tomcat-6.0-doc/config/context.html#Context_Parameters

8:01 I would like to access them when the servlet is initialized

8:01 weavejester: Kototama: If compiled as a servlet, a Ring handler has access to the ServletContext via the :servlet-context key

8:01 Kototama: but this is accessible only in a request

8:01 weavejester: Initialisation is outside the scope of Ring. Lein-Ring has an init method, but I don’t think that currently includes the ServletContext.

8:02 Kototama: yes, i think that's the problem

8:02 i need that before the first request, to configure the app

8:04 justin_smith: Kototama: what about using a promise to hold the configuration, and delivering to it when the first request is received?

8:04 less than ideal, yes

8:06 Kototama: justin_smith: i need to dynamically give a pathfile to the servlet from the external environment

8:06 so that the app can read the configuration file

8:09 justin_smith: wouldn't you also see that info vi (System/getenv "key")?

8:10 if you are in a container's vm, you should see it's env right?

8:10 CookedGryphon: when using transduce... you always have to define an arity-1 version of the function as well as the one which takes the accumulator? reduce doesn't do that does it? I found this surprising

8:10 Kototama: it would be a solution but that's not super clean as it pollutes the env

8:11 mdrogalis: CookedGryphon: I think Rich talks about that during his SL talk. I can't recall why though

8:11 justin_smith: Kototama: maybe I misunderstood what you meant by "from the external environment" - I thought you meant the config would already be in the env

8:13 Kototama: anyway, my initial proposal using a promise for the config is basically late binding: you get the info needed with your first request, and that fills in your config (of course this would likely need to happen before routing happens)

8:14 Kototama: justin_smith: thank you , i will see if i can do this solution with our system

8:14 there is also this https://github.com/laurentpetit/ring-java-servlet

8:14 not sure if it's compatible with ring

8:15 justin_smith: well, it's a ring servlet - it may not be compatible with your container, but it implements ring

8:15 weavejester: Kototama: It should be. That might be your best solution.

8:16 Kototama: it's a bit overcomplicated, maybe i'll try to just use java env parameters

8:17 justin_smith: you mean system properties? changing env in java is non-portable and hackish

8:17 Kototama: the thing you pass with -D :-)

8:17 justin_smith: yeah, properties

8:17 Kototama: thanks :-)

9:19 sudodoki: Hello channel, sorry to bother, but have really simple vector iteration question: how to apply operation to each element in vector & collect the result? Have this gist not working: https://gist.github.com/sudodoki/5f61b4decfe3445b6cf2#file-vector_stuff-cljs-L6

9:20 As result I get the sum vector without operation being applied

9:22 justin_smith: sudodoki: I recommend a basic clojure intro

9:23 sudodoki: Okay, nvrm, just missing parens

9:23 justin_smith: ,(let [v [1 2 3]] mapv println v)

9:23 clojurebot: [1 2 3]

9:23 justin_smith: ,(let [v [1 2 3]] (mapv println v))

9:23 clojurebot: 1\n2\n3\n[nil nil nil]

9:24 justin_smith: ,(mapv + [1 2] [3 4]) ; sudodoki: your addVector could be #(mapv + %&)

9:24 clojurebot: [4 6]

9:24 sudodoki: justin_smith: I did some clojure/clojurescript koans & have started with clojure for brave, just doing some novice errors when learning to write code on my own.

9:24 justin_smith: sure

9:25 just making sure you are checking out basic level materials if you have a mistake like that

9:26 sudodoki: Thanks, appreciate your time.

9:26 justin_smith: ,(#(mapv + %&) [1 2 3] [4 5 6] [7 8 9])

9:26 clojurebot: #<ClassCastException java.lang.ClassCastException: Cannot cast clojure.lang.PersistentVector to java.lang.Number>

9:26 justin_smith: oops

9:26 ,(#(apply mapv + %&) [1 2 3] [4 5 6] [7 8 9])

9:26 clojurebot: [12 15 18]

10:06 dysfun_: is there a renaming import macro somewhere

10:07 something like (import-renaming '[foo.bar :refer [bar :as baz]])

10:08 er, s/import/require/

10:09 oh, :rename

10:09 right, it's not documented

10:10 where's the correct place to report that?

10:10 Bronsa: dysfun_: (require '[foo :refer [bar] :rename {bar baz})

10:10 dysfun_: it's documetned in refer

10:10 vijaykiran: http://clojuredocs.org/clojure.core/refer

10:10 dysfun_: ":refer takes a list of symbols to refer from the namespace or the :all keyword to bring in all public vars.

10:10 Bronsa: dysfun_: in the refer function

10:10 dysfun_: it's not documented in 'require'

10:11 yes, i understand what you're saying, but it sounds like it can't be done

10:11 it makes no reference to the refer function

10:11 it just says it refers them

10:11 Bronsa: ok

10:11 dysfun_: open a ticket on dev.clojure.org/jira then

10:11 dysfun_: okay, thanks both

10:12 Bronsa: dysfun_: if you have signed the CA you can attach a patch yourself

10:12 if not, it takes a minute to do it

10:12 dysfun_: is it all online or do i have to print one off?

10:12 Bronsa: it's online now

10:12 dysfun_: brilliant. got a link handy?

10:13 Bronsa: https://secure.echosign.com/public/hostedForm?formid=95YMDL576B336E

10:14 dysfun_: thanks

10:15 Bronsa: np

10:17 dysfun_: and signed

10:17 right, let's get this patched then

10:21 TimMc: Haha, that e-sign thing is so funny.

10:21 dysfun_: the ui is...tedious

10:21 but less tedious than anything involving printers

10:21 TimMc: You know what makes it official? When you type in your name, it renders it in cursive!

10:21 dysfun_: the point where software has to touch hardware is where it all goes horribly, horribly wrong

10:21 hahaha yeah

10:21 TimMc: Oh god yes, I'm not complaining -- it's better than printing and mailing.

10:22 dysfun_: they've added a drawing option now

10:22 TimMc: I just find it highly amusing.

10:22 dysfun_: you can draw it on yourself

10:22 you know, they probably paid someone a lot of money to do that crappy handwriting font

10:23 TimMc: And to be honest, that's what makes it official: Money changed hands, so it must be more binding, official, and reliable than any other e-signature.

10:23 vijaykiran: or just used - http://www.myscriptfont.com

10:23 dysfun_: yes, but this is adobe. they don't just use someone else's font

10:23 they've churned out more fonts over the years than just about anyone

10:29 i'm not clear exactly what to update these docs to, to be honest

10:29 clgv: ,(require '[clojure.string :rename {join magic} :refer [join]])

10:29 clojurebot: nil

10:29 clgv: ,(magic "," (range 5))

10:29 clojurebot: "0,1,2,3,4"

10:29 clgv: dysfun_: did you mean that use case? ^^

10:30 dysfun_: yes

10:30 clgv: it's weird that you need to refer `join` although you already added it to `rename`...

10:30 dysfun_: i'm not entirely clear what to put in the docs, because it doesn't just pass it to refer

10:32 clgv: dysfun_: it does transitively https://github.com/clojure/clojure/blob/master/src/clj/clojure/core.clj#L5666

10:32 dysfun_: i would have thought it would do something like (require '[clojure.string :refer [join :as magic]])

10:32 that would make more sense

10:33 you've already got :as for aliasing namespaces

10:33 clgv: but that holds as reason not to use ":as" as well

10:34 dysfun_: you don't think it's more confusing to choose two different words for the concept of aliasing?

10:34 clgv: dysfun_: I wouldnt use that syntax with keywords there

10:34 dysfun_: why?

10:34 clojurebot: why is the ram gone

10:35 dysfun_: that too :)

10:35 it's got a nice analogue with destructuring bind

10:36 clgv: I'd stay with the :rename approach but make it work such that in the above example `join` is not needed in :refer

10:37 minimal and backwards compatible change ;)

10:37 dysfun_: make it reliant on positioning?

10:37 that sounds awful. you're putting two related pieces of data separately

10:37 clgv: huh what?

10:38 can you state again what exactly you want to achieve. maybe I misunderstood something

10:38 dysfun_: well we're now in the realms of 'how could that look nicer?'

10:38 i've already got the solution to my problem

10:39 clgv: I find the redundant use of `join` in my example suboptimal and would just fix that

10:39 dysfun_: yes, but how would you fix that?

10:40 clgv: dysfun_: adding a new syntax is not very likely to succeed if the current syntax is pretty minimal and suffices

10:40 dysfun_: think of it less as a matter of practical interest and more a theoretical thing

10:40 clgv: easiest fix is to add they keys in :rename to the :refer list internally within load-lib

10:41 done ;)

10:41 dysfun_: oh i see, so you'd just not have to specify them in :refer ?

10:41 clgv: yes.

10:41 dysfun_: that sounds like a reasonable option

10:41 i might look into it when i've finished updating these docs

10:41 clgv: and one that has a high chance to be merged ,)

10:42 sveri: Hi, when creating a new project with luminus I get the reload feature for free, in code it looks like this: http://pastebin.com/NXmD8fBr Now, what I want is to pass some params to my routes, but I don't know how to do that give the current structure, how can that passing of arguments be achieved in this case?

10:42 clgv: sveri: instead of (def app ...) you need a function (defn app [...] ...)

10:43 dysfun_: there are some examples here that show how the destructuring bind works https://github.com/weavejester/compojure/blob/master/test/compojure/core_test.clj

10:43 clgv: sveri: but maybe that fails if luminus is automagically starting your application and expects a value

10:44 sveri: clgv: yea, that's what I tried, but its not working when it loads the app

10:44 clgv: sveri: maybe you can specify a custom startup handler?

10:44 sveri: otherwise you wont be able to achieve that...

10:45 dysfun_: yeah, i'm not fond of frameworks where they expect to control startup and just call back into you

10:45 sveri: clgv: I am not sure how to do that without loosing the ability to reload the code

10:45 dysfun_: javafx is hell to use through clojure

10:45 AeroNotix_: Caused by: java.lang.IllegalArgumentException: Not a file: jar:file:/home/xeno/dev/gat/target/uberjar/gat.jar!/VERSION I'm having a problem when using lein-ver. It can't find the file inside the jar, but when I `jar -tf gat.jar | grep VERSION` it's there. Any ideas?

10:46 that gat.jar! exclamation point is suspicious.

10:46 clgv: sveri: I dont know luminus, so you need to find someone who does or try to find projects which also need parameterized routes

10:47 sveri: clgv: ok, thank you

10:54 danneu: sveri: have you tried http://ring-clojure.github.io/ring/ring.middleware.reload.html

10:55 donbonifacio: I created a project, deployed it to clojars, referenced it on another project, but I can't load a namespace from the other project. What could I be messing?

10:55 *missing

10:55 inad922: Hello

10:56 jphx: this is dog

10:56 inad922: I'm new to the language. If I defined a PersistentArrayMap via {:a 1 :b 2} does this create some efficient balanced binary tree like and rbt or avl?

10:58 sveri: danneu: yea, but it seems to have problems with route changes

10:58 and maybe some other stuff like protocols

11:02 justin_smith: donbonifacio: is the dependency successfully pulled in?

11:02 donbonifacio: justin_smith: yes, lein deps brings it

11:03 it's a snapshot versions, don't know if that matters

11:04 justin_smith: how are you requiring the namespace?

11:04 AeroNotix_: Caused by: java.lang.IllegalArgumentException: Not a file: jar:file:/home/xeno/dev/gat/target/uberjar/gat.jar!/VERSION I'm having a problem when using lein-ver. It can't find the file inside the jar, but when I `jar -tf gat.jar | grep VERSION` it's there. Any ideas?

11:06 donbonifacio: justin_smith: fuck, typo. thanks for helping me!

11:07 btcNeverSleeps: When I run "lein test" I get lots of "garbage" output from my program which makes the results of "lein tests" harder to read (I need to scroll, it's harder to see which test(s) failed, etc.). Is there some "best practice" as to what to do to not run into this issue? (I'm using "timbre" for logging btw)

11:07 AeroNotix_: woops

11:07 justin_smith: btcNeverSleeps: turn off logging during tests maybe?

11:07 or log to a file

11:07 btcNeverSleeps: justin_smith: sounds great, how do I do that? Is this some lein configuration?

11:08 justin_smith: it's a timbre config

11:08 AeroNotix_: Btw, is the leiningen s3 bucket not working?

11:08 https://leiningen.s3.amazonaws.com/downloads/leiningen-2.5.0-standalone.jar

11:10 justin_smith: btcNeverSleeps: there are various appender examples in the timbre docs https://github.com/ptaoussanis/timbre you would want to create a file appender

11:10 btcNeverSleeps: another option is to set the TIMBRE_LOG_LEVEL env var

11:10 visof: hi

11:10 justin_smith: if you want to just turn the logging off or make it quieter

11:11 btcNeverSleeps: justin_smith: great, thanks... And can I somehow configure "lein test" to set the TIMBRE_LOG_LEVEL to a quieter mode everytime "lein test" is called? (I realize it's a noobish question but both Clojure / lein timbre / etc.) are quite new to me

11:12 visof: is the best way to deal with my local java jars to local mvn repo, or create s3 mvn remote repo and push my jars there and add the url of repo in project.clj?

11:12 what do you think guys about this?

11:14 mdrogalis: visof: Are you working with others on this project?

11:14 visof: mdrogalis: yeah

11:15 justin_smith: btcNeverSleeps: you can use environ for that https://github.com/weavejester/environ

11:15 mdrogalis: visof: Definitely get yourself a Maven repo with S3.

11:15 Very announcing to have to do local installs on a team, IMO

11:15 annoying, rather*

11:15 btcNeverSleeps: justin_smith: thanks, a lot, reading and bookmarked : )

11:16 visof: mdrogalis: and then refer to this repo in project.clj and this are going to work, right?

11:16 mdrogalis: visof: Correct.

11:16 visof: mdrogalis: thanks

11:17 mdrogalis: visof: Np!

11:17 lambdahands: Hi, all. I was fascinated by the self-documenting code found here: https://github.com/tylerneylon/termtris

11:18 Is it taboo to use an ignore form (#_) on a string of multiple lines to do the same?

11:19 justin_smith: lambdahands: #_ still needs balanced forms

11:19 lambdahands: you can do proper literate programming in clojure https://github.com/gdeer81/marginalia

11:21 the official site is also an output of marginalia http://gdeer81.github.io/marginalia/

11:22 dysfun_: hrm, that's odd. :verbose on (require) seems to only work in the repl if you also use :reload

11:22 lambdahands: justin_smith: This is awesome! Thank you!

11:23 justin_smith: dysfun_: require does nothing if something has already been loaded and you don't specify :reload

11:23 lambdahands: np, this reminds me I meant to use marginalia myself :)

11:23 dysfun_: it's a fresh repl in a presumed nonexistent namespace 'bar'

11:23 or at least presumed not loaded

11:24 justin_smith: require doesn't load anything if the ns is already loaded somewhere else though - did maybe lein or nrepl load the ns?

11:24 dysfun_: oh, no, i know where that's coming from :/

11:34 clgv: so you can use :rename without :refer, it's just that it defaults to importing everything then

11:34 clgv: so your change would be breaking

11:43 clgv: dysfun_: no you cant. (require '[clojure.string :rename {join magic}]) does not refer anything to the current namespace

11:43 dysfun_: start a fresh repl and see yourself (Clojure 1.6.0 here)

11:45 ,join

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

11:45 clgv: ,(require '[clojure.string :rename {join magic}])

11:45 clojurebot: nil

11:45 clgv: ,magic

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

11:45 clgv: ,join

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

11:45 clgv: q.e.d. ;)

12:24 upwardindex: I updated cider and cannot connect anymore, it hangs at “Establishing SSH tunnel connection…” Is that a new feature?

12:27 technomancy: cider's #1 feature is to be full of surprises, always

12:29 nullptr: there are "good cider days" and "bad cider days" in approximately equal measure

12:30 technomancy: upwardindex: using an unstable version of cider is a really bad idea unless you're actively developing it

12:30 mgaare: like an aging relative with dementia

12:30 upwardindex: technomancy: is melpa cider unstable?

12:30 technomancy: verma: is this your comment? https://github.com/technomancy/leiningen/issues/1721

12:31 upwardindex: everything in melpa is unstable

12:31 avoid

12:31 it really boggles me as to why people use it =\

12:31 I guess it's because they are not clear about the fact that it contains a lot of broken crap

12:31 upwardindex: fml, I just pressed U x in list-packages, all my packages are unstable now

12:31 technomancy: ._.

12:32 first thing to do is take melpa off your package list

12:32 back up your elpa/ directory, then delete all your packages and reinstall the ones you care about from a stable source

12:33 ~melpa

12:33 clojurebot: melpa is not what you want.

12:33 nullptr: technomancy: and install nyan-mode manually? bah.

12:34 justin_smith: technomancy: someone should do a sketch comedy where someone goes to a restaurant, and the waiter tells them they should take random items off the stove in the kitchen. Person then complains about the various ways they are not edible (this is still cold / this is raw / how am I supposed to eat this without a sauce ...).

12:34 * technomancy flips the "It has been [ ] days since some poor soul's Emacs got messed up by melpa" counter back to 0

12:34 technomancy: justin_smith: haha; nice

12:35 justin_smith: it's the waiter's fault for telling them to just grab things from the kitchen, and the diner's fault for thinking that is reasonable

12:36 technomancy: except maybe the kitchen is disguised as a vending machine

12:36 justin_smith: hmm...

12:36 yeah, kind of falls apart there

12:37 technomancy: hangs a sign reading "restaurant" on a grocery store, fast forward to people eating uncooked noodles out of the box

12:37 technomancy: hehe

12:46 mdeboard: melpa-stable is... serviceable

12:46 I have avoided most of the headaches since switching

12:47 Of course, some of the same people who don't see the point of having melpa-stable are also maintaining critical emacs libraries for me

12:47 So they don't do granular release management which means e.g. CIDER goes a really long time between updates

12:47 (which is good given some of its recent turbulence)

12:48 melpa does a good job

12:48 errrr magit*

12:55 TimMc: upwardindex: Once you have everything back in working order, put your .emacs.d under source control.

12:56 upwardindex: TimMc: that is a very wise suggestion, I have gotten lazy in my emacs administration since I discovered prelude

12:57 technomancy: that should be qualified though. you want all the .el files checked in, but not the .elcs

12:57 upwardindex: Just for the record, latest cider managed to connect when given the ip (I usually just use the hostname)

12:59 justin_smith: technomancy: will package generate new elc files if you have cleaned them out?

13:00 technomancy: justin_smith: only on fresh installs, I think

13:00 I mean, don't delete them, just don't check them in

13:00 you can regenerate them if you move your dotfiles to a fresh machine

13:00 or something

13:02 justin_smith: technomancy: I was just thinking it would be good to know about package clean / package compile if such commands existed

13:16 TimMc: technomancy: Why not the elcs?

13:16 technomancy: TimMc: they're not portable across emacs versions

13:17 justin_smith: also, they are compiled artifacts, and shouldn't be in version control

13:17 TimMc: justin_smith: This is a different kind of version control. It's more like... dependency management, where you want to lock in versions of things.

13:17 nullptr: mv **/*.elc ~/.m2

13:18 TimMc: If I'm worried that I might not be able to generate binaries in the future, I'll include them.

13:19 (I don't think that applies here, though.)

13:20 justin_smith: TimMc: which is why I asked about clean / compile tasks

13:21 technomancy: M-x byte-compile-directory is a thing

13:21 not sure if it's recursive

13:23 clgv: nullptr: mv **/*.elc /dev/null would fit your name better ;)

13:24 nullptr: clgv: true indeed! not sure i'd really notice if my elcs were got, fwiw -- computers are pretty fast these days.

13:24 justin_smith: is there a version of apropos that returns the var of the result? or at least a namespaced symbol?

13:24 ,(apropos "base64")

13:24 clojurebot: ()

13:25 justin_smith: ,(apropos "str")

13:25 clojurebot: (clojure.core/char-escape-string clojure.core/char-name-string clojure.core/construct-proxy clojure.core/create-struct clojure.core/defstruct ...)

13:25 justin_smith: woah - that's the version I want...

13:25 ,*clojure-version*

13:25 clojurebot: {:interim true, :major 1, :minor 7, :incremental 0, :qualifier "master"}

13:25 justin_smith: ,#'apropos

13:25 clojurebot: #'clojure.repl/apropos

13:26 mikerod: I asked in the #leiningen channel, but no luck: I have a macro used in some of my namespaces that def's a var, but prevents redefs - e.g. someone tries to re-compile the file or redefs a var with the same name later in the same ns.

13:26 The macro throws an exception in this case. Leiningen apparently is redef'ing some vars in my test namespaces, so the tests fail with compile errors.

13:27 Anyone familiar with this and have any advice on how you'd address it?

13:28 hiredman: mikerod: leinigen doesn't do that

13:28 technomancy: actually lein test requires your tests with :reload

13:28 otherwise it wouldn't work in persistent settings; you'd just run your old tests over and over

13:28 justin_smith: yeah, require reload would do that

13:28 hiredman: ugh

13:29 anyway, that'll do it

13:30 mikerod: technomancy: that's the problem I think. It goes like: (a) I have a "test resource namespace" in my test resources that a test uses - this gets compiled on its own at some point

13:30 technomancy: mikerod: so you never run your tests in the repl?

13:30 mikerod: (b) my actual test namespace comes along and it compiles the dependency again? wait no, that doesn't make sense if it is just a :reload on each namespace

13:31 technomancy: repl is fine, it is a dependency namespace of a test that is getting loaded 2 times. I get it now

13:31 The test compiles first

13:31 technomancy: hm; yeah it's not :reload-all

13:31 mikerod: a) the test compiles first, compiling its dependency (b) the dependency namespace is picked up as its a test of its own and is :reload required

13:31 stuartsierra: More to the point, why do you have such a macro?

13:32 mikerod: stuartsierra: We have a DSL. Some of what the DSL defines are stored in vars. It was a common mistake for users of the DSL to accidentally name 2 vars the same.

13:32 stuartsierra: mikerod: okay, fair enough. Might be easier to do that with a pre-processing pass instead.

13:33 mikerod: stuartsierra: within the same file. Clojure doesn't complain about this. I think it is a similar issue with like `clojure.test/deftest`. People often name 2 tests the same name on mistake and then that means only one really runs

13:33 technomancy: yeah, you could work around this in your tests, but it would be better to make your code reload-safe

13:33 mikerod: shouldn't you be blocking redefs that have a different file/line rather than redefs in general?

13:34 mikerod: technomancy: yeah, it'd be nice if we just silently didn't redef. except from the DSL perspective that would just confuse people since they wouldn't know their 2nd definition did not do anything. It is really a user-error that we found nice to throw at compile-time

13:34 technomancy: I guess that is a good point

13:34 I mean that would work

13:35 It'd make development nicer, that's for sure

13:35 One hook we had in at one point was just a *debug* sort of dynamic var. I wasn't sure if I could scope a dynamic var for the `lein test` time though. I also wasn't sure I liked that approach anyways. :P

13:36 We actually have these files logically separated though as, "test resources" and "test namespaces". The issue is leiningen treats both paths as "test namespaces", so they all get their require :reload done. If the order goes the real "test namespace" first, then later its "test resource" dep, the error shows up.

13:37 technomancy: are they all under test/ ?

13:37 mikerod: I agree that maybe I should just change the macro. But does Leiningen not have the concept of a "test resource" dir? - Maybe I just make it :resource-paths in a test profile.

13:37 technomancy: stuff under dev-resources won't get reloaded

13:38 the test profile won't work in the repl, but dev-resources will

13:38 mikerod: ok, I may just try that to understand what lein does better. Although I'm now a fan of your line # filename approach, so I'll probably change to that.

13:38 (inc technomancy)

13:38 lazybot: ⇒ 148

13:38 mikerod: (inc stuartsierra)

13:38 lazybot: ⇒ 11

13:39 mikerod: and nope, we have the classic maven style directory layout here - src/test/resources src/test/clojure src/test/java

13:39 technomancy: k, just use :dev instead of :test

13:40 mikerod: ok, thanks for the advice

13:53 mskoud: normaly a ring handler is created with a (def app ...) but what if i needed to define it as a function (defn make-app [system] ...) , how should serve be called?

13:53 weavejester: mskoud: How should serve be called?

13:54 mskoud: Could you explain that sentence a little more?

13:55 mskoud: I'm using [ring.server.standalone :as server] , and calling (server/serve (make-app system)) seems to fail when the url is requested.

13:55 Bronsa: uhm. I can generate at runtime (fn [] (b (c))) as (comp b c), is there a way to express (fn a [] (b (c a)))?

13:56 weavejester: Bronsa: Is that (fn a [] …) or (fn [a] …) ?

13:56 justin_smith: Bronsa: (fn [a] (b (c a))) is (comp b c)

13:57 Bronsa: weavejester: justin_smith (fn a [] ..)

13:57 weavejester: mskoud: Hm, that should work. Is make-app returning a function?

13:58 mskoud: it returns a nesting of middleware: (wrap-edn-params (wrap ... (routes cms-routes)))

13:58 justin_smith: ,((comp inc (constantly 1))) ; or did you mean this case Bronsa?

13:58 clojurebot: 2

13:59 Bronsa: justin_smith: no, I definitely mean it as I said :) I need to pass the "this" local to one of the function I compose

13:59 justin_smith: Bronsa: just saying (fn [] (b (c))) is not (comp b c) unless you are calling with no args

13:59 but that's beside your point, clearly

14:00 weavejester: Bronsa: Sounds like you might want the y-combinator

14:00 Bronsa: justin_smith: suyre it is. (fn [] (seq (conj)) == (comp seq conj)

14:01 weavejester: mskoud: That looks like it returns a handler function… What error are you getting?

14:01 gfredericks: Bronsa: ##((fn [] (seq (conj))) [] 1 2)

14:01 lazybot: clojure.lang.ArityException: Wrong number of args (3) passed to: sandbox5671$eval11395$fn

14:01 gfredericks: &((comp seq conj) [] 1 2)

14:01 lazybot: ⇒ (1 2)

14:01 mskoud: java.lang.IllegalArgumentException

14:01 contains? not supported on type: compojure.core$routes$fn__512

14:01 RT.java:724 clojure.lang.RT.contains

14:01 core.clj:1415 clojure.core/contains?

14:01 flash.clj:19 ring.middleware.flash/flash-response

14:01 flash.clj:36 ring.middleware.flash/wrap-flash[fn]

14:01 Bronsa: gfredericks: I never said I have to pass args to that

14:02 ,(seq (conj))

14:02 clojurebot: nil

14:02 gfredericks: Bronsa: yeah but justin_smith said "unless you are calling with no args"

14:02 daniel___: i want to write a library with some configurable vars that can be configured from the project importing the library

14:02 Bronsa: ah, missed that

14:02 daniel___: can anyone share some techniques

14:02 gfredericks: Bronsa: I think we all know how clojure works though so I'm not sure why I'm going this far out of my way to emphasize that

14:03 weavejester: mskoud: I think I’d need to see the app in more detail. Is it online?

14:06 mskoud: Yes, http://pastebin.com/AjtgAcVD lin 235 , 254.

14:18 justin_smith: Bronsa: would something in a letfn context count? that's all I can think of without maybe some ugly tricks

14:22 Bronsa: justin_smith: I don't think letfn would work, I might just end up using a dynamic var and be done with it. ugly solution but it's better than what I'm doing now (composing the functions every time the fn is invoked)

14:23 justin_smith: or a promise.

14:25 bbloom: Bronsa: what do you need it for?

14:27 Bronsa: bbloom: https://github.com/clojure/tools.analyzer/blob/master/src/main/clojure/clojure/tools/analyzer/passes.clj#L198-L199

14:27 bbloom: I'd like to compose the passes just once rather than each time they are invoked

14:28 there might be some stupid easy way to do this that I'm missing

14:28 bbloom: Bronsa: there's lots of crap going on in there, i gotta study it a sec

14:29 Bronsa: bbloom: yeah, I'm in the process of refactoring & commenting the weird bits :P

14:30 bbloom: Bronsa: why do you need to actually compose the passes? why not just have a vector of them?

14:30 Bronsa: presumably they are actually all tail calls to the next pass, right?

14:32 Bronsa: bbloom: actually, no. (schedule #{#'pass-a, #'bass-b ..}) generates something like (fn [ast] (-> ast (prewalk (comp pass-a pass-c)) (postwalk pass-b ..) ..))

14:33 bbloom: it composes together all the passes it can to reduce the number of complete tree traversals

14:34 bbloom: doing a full tree traversal for each logical pass would be way too expensive

14:34 bbloom: ok i think i understand now

14:35 Bronsa: when do you dynamically need to generate a fix-point like that? you're doing it statically here

14:37 Bronsa: bbloom: maybe I explained myself badly, but you can see that I'm doing the reduce comp in line 199 -- that is inside the pass. this means it will be invoked every time that function is invoked and it will generate a bunch of functions again

14:37 bbloom: it's the difference between (let [a (comp x y)] (fn [] (a))) and (fn [] (comp x y))

14:38 I'm doing the latter, I'd like to do the former. the issue is that in my case, y might need to take `this` as a parameter

14:38 bbloom: Bronsa: oh ok, ... well what if you define your fn as curried? so instead of (fn a [] (b (c a))) you have (fn a [] ((b (c)) a))

14:39 my parens may be off there

14:39 but anyway, you basically omit the recursive argument and return a function of that pending recursive argument

14:39 then you just call that and give it itself

14:40 Bronsa: I see, that might work

14:40 bbloom: Bronsa: also a fun read: http://okmij.org/ftp/Computation/fixed-point-combinators.html

14:41 Bronsa: see the section on the U combinator

14:41 Bronsa: bbloom: thanks!

14:42 justin_smith: lein marg (the margenalia plugin) is hanging every time I use it - is that normal? do I need to make a pr that calls (shutdown agents) if it is called on its own?

14:44 dysfun_: do all bindings in a let show as being on the line the let starts on?

14:44 justin_smith: dysfun_: yes, it is sequential

14:45 ,(let [a 0 b (inc a) c (inc b) d (inc c)] d)

14:45 dysfun_: okay, cool

14:45 clojurebot: 3

14:45 SagiCZ1: i need a function that returns true if a string contains given substring, how would i do that?

14:46 (foo "hello" "ell") => true

14:47 (re-find #"ell" "hello")

14:47 ,(re-find #"ell" "hello")

14:47 clojurebot: "ell"

14:48 noonian: ,(.contains "hello" "ell")

14:48 clojurebot: true

14:48 SagiCZ1: noonian: thats javas method right?

14:48 noonian: ,(map #(.contains #"ell" %) ["foobar" "hello"]))

14:48 clojurebot: #<IllegalArgumentException java.lang.IllegalArgumentException: No matching method found: contains for class java.util.regex.Pattern>

14:48 noonian: ,(map #(.contains % "ell") ["foobar" "hello"]))

14:48 clojurebot: (false true)

14:49 noonian: SagiCZ1: yes

14:49 SagiCZ1: noonian: thank you

14:49 noonian: np

15:15 SagiCZ1: does anyone have any experience with incanter? or where would i find people who do?

15:18 Raynes: Nobody knows anythin about incanter. Nobody on the planet.

15:18 (It's best to just ask your question and see if anyone bites.)

15:18 (Your question may not require an incanter expert, and if it does require one they're unlikely to volunteer to assist with an issue they know nothing about, due to time constraints and such)

15:19 SagiCZ1: i have a bunch of points plotted by scatter-plot and displayed by (view) .. i want to redefine the data and see the change interactively in the jframe.. as is possible when interactively working with swing

15:22 xemdetia: SagiCZ1, I would look for some sort of way to trigger a repaint of the widget

15:22 sqd: would core.async channels be suitable for reconfiguring in a max/msp like interface? or is something about them fundamentally different

15:23 (max/msp as in visual dataflow programming, connecting nodes etc)

15:23 SagiCZ1: xemdetia: yeah.. some things trigger the repaint.. like adding more data

15:24 xemdetia: SagiCZ1, this is normal behaviour of any widget. If something triggers a redraw it redraws. You just need to find out a way to force a redraw whenever you change your data.

15:27 justin_smith: sqd: they should work very nicely for that - though you would have to implement splits (where to outputs come from the same place) explicitly

15:27 sqd: one adaptation would be to have a dedicated "splitter" that is used explicitly

15:29 sqd: one thing that comes to mind is using a data graph representation to track units as edges, and connections between them as vertices, and then constructors that make each unit and return the input and output channels for that unit

15:29 sqd: justin_smith: cool, then i've got myself a little hobby project :-) currently programming with arduino and channels, could use something like this

15:29 justin_smith: cool

15:31 I forget the name for it, but there is that flattened representation of graphs, where you have a map from id to edge, and then a map from id to collection ids (the set of vertexes from that edge)

15:32 the sparse representation that is

15:33 but I guess in this case it would be a mapping from the id of some processing unit to its input channels

15:34 how complex this ends up being depends on whether you would compile and run, or leave things running and modify the graph while it runs

15:34 TimMc: justin_smith: adjacency list

15:34 https://en.wikipedia.org/wiki/Graph_%28abstract_data_type%29#Representations

15:34 sqd: the live modification would be coolest, a use case now is to experiment with different parameters for feedback loops etc

15:34 sudodoki: So, beginner clojure question: I have canvas context, and I have dot as a (list x y)

15:34 justin_smith: TimMc: ahh, that's the one, thanks

15:35 sqd: oh, so you want to actually route audio too?

15:36 * sudodoki :facepalm: at the shift+enter posting things. Sorry.

15:36 justin_smith: sqd: in that case, check out pink, it's a modular dsp engine written in clojure, by one of the authors of csound

15:36 sqd: justin_smith: i'm currently just using two motors as feedback to input from the hand

15:36 justin_smith: ahh, that kind of feedback :)

15:41 upwardindex: Is it possible to do something tlike this: (. (symbol "System") (getProperties))

15:41 TimMc: Nope.

15:42 upwardindex: TimMc: not even in cljs? (crosses fingers)

15:42 justin_smith: upwardindex: you could find the class / method from a string using reflection, but not like that

15:42 oh, cljs, never mind, I have no idea

15:42 Bronsa: upwardindex: in clj you can use reflection, in cljs you can use js*

15:43 but I wouldn't reccomend to do either

15:43 upwardindex: Bronsa: I was hoping not having to use js* but I guess thats where I have come

15:43 TimMc: What's the use-case?

15:43 upwardindex: I need to implement some kind of “call this method on the object” for interaction with awesomium

15:44 Bronsa: upwardindex: why doesn't normal interop work for you?

15:47 upwardindex: Bronsa: I need to provide an abstraction for async calls to awesomium, so I need to call methods of the awesomium object that is bound on the c++ side. When I simply call the function cljs does a “.call(null, …)” which is not appropriate and it seems I can’t resolve the symbol inside the abstration

16:04 bbloom: hey jvm perf wizards... how much impact does the dynamic-ness of vars have on escape analysis?

16:05 er not really :dynamic *earmuffed* vars, just normal getRawRoot or whatever it is

16:10 stuartsierra: bbloom: I've heard that Escape Analysis hardly does anything anyway.

16:10 hiredman: bbloom: I think the issue is vars is the volatile read

16:11 bbloom: stuartsierra: is that b/c it's too hard to do well, or b/c bump pointer allocation w/ a GC nursery is "fast enough"

16:11 hiredman: with vars

16:11 stuartsierra: bbloom: It's hard, and I recall someone like Goetz saying it doesn't work in as many cases as was originally hoped.

16:12 bbloom: hiredman: hm, i understand the meaning of volatile, but i'm not sure i really understand what the jvm physically *does* or *does not do* differently in response to it

16:12 hiredman: bbloom: same boat pretty much

16:12 stuartsierra: Volatile read isn't particularly special. Volatile *write* is a memory barrier that busts caches.

16:13 bbloom: stuartsierra: is it doing some voodoo w/ the kernel's memory manager or some cpu instructions i don't know much about? ie, man $WHAT_DO_I_TYPE_HERE

16:13 :-)

16:13 hiredman: stuartsierra: well, the reads have to be ordered

16:13 bbloom: i need apropos-by-smart-people

16:14 stuartsierra: bbloom: You have IRC don't you? ;)

16:14 bbloom: apropos volatile

16:14 go.

16:15 stuartsierra: The JVM says a write to a `volatile` variable must be visible on all threads by the time it completes.

16:15 bbloom: how does that happen without a read barrier? and what is the write barrier implemented in terms of?

16:16 stuartsierra: bbloom: OutOfKnowledgeException :)

16:16 hiredman: huh, according to the internet the i386 memory model is strong enough to not need a fence on read

16:16 http://www.infoq.com/articles/memory_barriers_jvm_concurrency is what I landed on googling

16:16 stuartsierra: I think a volatile write has the effect of forcing the CPU to synchronize any cached copies of that variable.

16:17 bbloom: stuartsierra: if you had restartable exceptions, i could pass you back more knowledge or something

16:18 soooo you're saying that the write barrier just triggers some secret internal private ubiquitous read barrier? heh

16:18 stuartsierra: bbloom: Sadly I am not implemented in Common Lisp.

16:19 hiredman: http://brooker.co.za/blog/2012/09/10/volatile.html actually as some experiments run timing volatile operations

16:22 bbloom: hmm interesting

16:31 hiredman: I wonder if the root field for vars could just be made non-volatile, I mean, no one is mutating vars and using that to coordinate multiple threads, right?

16:31 technomancy: that's not something you can change with a system property, is it?

16:32 hiredman: not really

16:32 technomancy: maybe you could have two paths, and have a system property to select for newly-compiled code, but not retroactively

16:32 but it's probably not worth it

16:32 hiredman: and you'd end up with the overhead of checking the system property

16:33 technomancy: eh; I think that could be done at compile time?

16:33 hiredman: I suppose that is true

16:33 (defn ^:non-volatile foo [...] ...)

16:33 technomancy: similar to definline, I guess

16:34 hiredman: well, no, you could still redefine stuff without having to recompile callers

16:34 just not a strong guarantee of when those changes become visible to other threads

16:35 technomancy: you'd pick up the changes in content but not the changes in volatility

16:35 hiredman: well, no

16:36 changes in volatility would be inadvisable and require recompiling callers

16:36 changes of content would be at the whim of the processor caches I believe

16:36 stuartsierra: There's been some work to make non-mutable Vars, like `^:static`

16:37 hiredman: sure, but those suck :)

16:38 technomancy: was that when every var in a namespace starting with "clojure" got opted into staticness?

16:38 stuartsierra: I don't think it ever did that, but lots of defs in clojure.core were annotated ^:static.

16:38 hiredman: technomancy: I vaguely recall that

16:39 technomancy: it never made it into a release, but we had master giving static behaviour to clojure-http-client at one point

16:39 that was fun

16:39 hiredman: yeah

16:39 stuartsierra: Someone (Rich, Stu, Alex M?) was working on bringing it back as a compile-time flag.

16:39 technomancy: yeah, this one wasn't applied by metadata iirc

16:42 but the result was similar

16:42 Bronsa: should be the direct branch

16:43 hiredman: the fastload branch is also messing with this stuff, but changin vars directlly it looks like, instead the compiler puts a stub in the var that loads the fns class on first use

16:46 (no idea how that is going to work with invokePrim)

16:46 I guess it just doesn't

16:46 https://github.com/clojure/clojure/commit/32760085c1d72ee676927109e9ba804ee4983247#diff-f17f860d14163523f1e1308ece478ddbR3941

16:48 Bronsa: hiredman: do you have any idea what the !hasEnclosingMethod is there for btw? I could never figure it out

16:49 hiredman: Bronsa: maybe for :static?

16:50 or maybe for defuns inside fns or something crazy like that

16:50 (who does that?)

16:50 Bronsa: hiredman: as I read it, it's there to ensure that only defns get through the static invoke, but I don't understand why a local fn couldn't

16:52 hiredman: oh, sure, right

16:52 Bronsa: well a local fn doesn't have a nice mutable binding(var) to swap in to

16:53 Bronsa: no wait, that's inside emitForDefn, I didn't notice that

16:53 so yeah, looks like it's preventing forms like (fn [] (defn x []))

16:53 bah, whatever. I'll look into it when/if it gets into master

17:36 literary: johnwalker

17:54 wei: how do i clear the cache of a memoized function?

17:55 sritchie: wei: you can’t with the usual memoize -

17:55 wei: core.memoize gives you a bunch of options

17:56 wei: oh, didn’t realize they were different

17:56 sritchie: yeah, core.memoize is a library that gives you a bunch of different strategies for memoization

17:56 wei: can i use memo-clear! on a normal memoized function?

17:56 Bronsa: no

17:56 wei: kk

18:31 * technomancy tried to submit a patch to allow that but got WONTFIX'd =\

18:33 mdeboard: roasted

18:33 They must not know about you

18:34 They don't know who they're messing with.

18:35 nullptr: lein'd

19:09 hiredman: technomancy: your patch was silly, if I recall

19:10 memoizing a function is generally supposed to speed it up, function metadata wraps the function in an AFunction metadata holder deal, which slows down invocation

19:14 tieTYT: hi i'm maintaining some old clojure code. I'm not very good at the language anymore. I have some java code calling the clojure code and if it's called in a certain way it gives an error the first time but never again. The error is an IllegalAccessException

19:14 Bronsa: I never realized the AFunction withMeta reify is a RestFn w/o direct invoke instances

19:14 irctc: hi, wondering why does ((symbol ".toString") "hello") returns nil , while (.toString "hello") returns "hello"?

19:14 tieTYT: it's re: the interval method I've required here: (:require [clj-time.core :refer [interval overlaps?]])

19:15 i can paste the stack trace

19:15 http://pastebin.com/2RrcSqsN

19:17 turbofail: irctc: ((symbol ".toString") "hello") is calling a symbol object as a function

19:18 ,((symbol ".toString") {".toString" :foo})

19:18 clojurebot: nil

19:18 turbofail: ,((symbol ".toString") {'.toString :foo})

19:18 clojurebot: :foo

19:19 Bronsa: tieTYT: the error is pretty clear, there is no "interval" Var in the clj-time.core namespace

19:19 justin_smith: tieTYT: are you sure there is a public interval function in the version of clj-time you have required?

19:19 turbofail: irctc: that does an entirely different thing than the method call syntax. if you want to call a method that you're selecting at run-time, you'll have to use reflection yourself

19:21 irctc: turbofail: ok, thanks

19:24 tieTYT: it must be there because the code works fine every time after the first time, right?

19:25 i mean it only fails the first time, so it must be there, right?

19:26 justin_smith: tieTYT: that's weird - have you looked at the namespace in the jar being used?

19:26 tieTYT: looked at it in what way?

20:07 TimMc: technomancy: Feels bad, man.

20:11 technomancy: hmm?

20:13 oh, yeah not having a reasonable way to put metadata on functions is a drag

20:24 TimMc: I meant the WONTFIX, actually.

20:24 It's not so bad if there's a reason given, of course.

20:24 technomancy: I don't recall anything about performance mentioned

20:41 bacon1989: Damn, I wish chestnut was a thing before I started my clojurescript project

20:41 I still don't have a proper cljs repl

21:52 ToxicFrog: Not again

21:52 It would be really nice if, when I screw up somewhere, I didn't get something completely useless like this: https://gist.github.com/ToxicFrog/fdff8babd1b0062d4c60

21:53 danneu: bacon1989: yeah, i have yet to evolve from my primitive cljs workflow

22:00 amalloy: well uh...you have a null pointer exception at line 13 of ifirc/core.clj, inside the main function. does that not help narrow it down?

22:00 looking at https://github.com/ToxicFrog/ifirc/blob/master/src/ifirc/core.clj, i conclude you forgot to pass the three arguments your -main requires

22:01 supposition substantiated by https://gist.github.com/ToxicFrog/fdff8babd1b0062d4c60#file-gistfile1-txt-L1

22:01 so i'd say that stacktrace contains all the information you needed to debug the problem, ToxicFrog

22:19 ToxicFrog: amalloy: oh wow, I'm so used to the information being in the first stack trace or nowhere that I didn't actually read the second one.

22:19 Sorry about that.

22:19 amalloy: it's usually in the last one

22:19 ToxicFrog: (the root cause was actually completely different, as it happens; this is the commit that completely rewrites command line handling)

22:19 amalloy: if you don't know where to look, look at the topmost lines of the last trace

22:20 seangrove: amalloy: Absolute last, or just the last you look at?

22:21 amalloy: furthest down on the page

22:22 ToxicFrog: That has not, historically, been my experience.

22:23 Syntax errors in particular always seem to have the file:line in the first line of the first stack trace or not at all anywhere, but this is true of runtime errors as well.

22:25 verma: sup dnolen_

22:27 amalloy: oh, that's true, ToxicFrog. compiler errors are different

22:27 runtime errors in your own code behave the way i was saying; compiler errors because your code isn't runnable at all are a little different

22:28 i always forget about that, and look at the lowest one first. i guess i get more runtime errors than compiler errors. three cheers for paredit

23:24 mdeboard: Is there an idiom when destructuring hashmaps like `[{:keys [foo :as bar, baz :as qux]} some-map]'

23:28 scottj: mdeboard: give an example some-map and what bar and qux would be?

23:28 mdeboard: In this case I'm drawing events from a channel in clojurescript

23:28 and want to have descriptive variable names

23:29 in a particular function, but the data is best described in one way in the map, and another way in the function.

23:31 scottj: mdeboard: why does (let [{bar :foo qux :baz} some-map}] ...) not work?

23:32 mdeboard: Is that a thing?

23:32 If so, it would

23:32 Thanks :P

23:32 scottj: mdeboard: :keys is the more advanced version

23:32 mdeboard: there's such a wide variety of syntax for destructuring binds

23:32 hard to keep them all straight

23:49 ddellacosta: anyone know of any decent metrics libraries for Clojure?

23:49 amalloy: mdeboard: {:keys [...]} is shorthand for the more general map destructuring form, which is {x :x, y :y}

23:49 there are also :strs and :syms, which see much less frequent use

23:51 ddellacosta: this looks promising: https://github.com/sjl/metrics-clojure

23:52 egghead: ddellacosta: i have used that lib, works as advertised

23:53 ddellacosta: cool, thanks egghead

23:58 rntz^2: hey, can anyone explain to me why this doesn't work: (eval `('~list 1 2 3))

23:58 I'd expect it to do the same as (eval `(list 1 2 3))

23:58 but it raises an error instead

Logging service provided by n01se.net