2014-05-08
| 00:51 | PigDude | is #inst reader macro documented somewhere? |
| 00:52 | PigDude | *data reader |
| 02:53 | dhruvasagar | Hey guys, I am learning clojure and having fun, I am a little confused with the syntax of this function (.toUpperCase), it looks like most string functions are like this, I am unable to get (doc .toUpperCase) and (macroexpand) also doesn't do anything for this so I am not sure what to make of this '.' methods |
| 02:53 | beamso | ,(.toUpperCase "foo") |
| 02:53 | clojurebot | "FOO" |
| 02:53 | beamso | if it starts with a ., it's most likely java interop |
| 02:53 | dhruvasagar | beamso: I know how to use it, I just don't understand the significance of the '.' |
| 02:54 | dbasch | it’s java interop, .toUpperCase is a method of java String |
| 02:54 | dhruvasagar | dbasch: why the '.' ? |
| 02:54 | beamso | then it looks like a method call? |
| 02:54 | dbasch | dhruvasagar: see http://clojure.org/java_interop |
| 02:54 | dhruvasagar | dbasch: thanks, reading |
| 02:54 | dhruvasagar | beamso: (toUppercase "asd") also looks like a method call |
| 02:54 | dhruvasagar | babilen: reading the interop docs |
| 02:55 | dhruvasagar | beamso: * |
| 02:55 | servo | isn't like everything in clojure java interop? |
| 02:55 | dhruvasagar | servo: I don't think so, libraries written in clojure are different from the ones borrowed / imported from java |
| 02:56 | dhruvasagar | servo: I suppose this is the way to differentiate |
| 02:56 | servo | i guess im conflating java/jvm |
| 02:56 | dbasch | servo: there’s clojure for other platforms, most notably clojurescript on javascript |
| 02:57 | servo | (not= clojure clojurescipt) (== clojure clojurescript) |
| 03:01 | dhruvasagar | I am considering building a small webapp this weekend using clojure, I am considering using something like Noir / Luminus, however I've been recommended to use compojure / rain directly, what are your thoughts ? |
| 03:01 | servo | noir is deprecated |
| 03:01 | dhruvasagar | s/rain/ring |
| 03:02 | dhruvasagar | servo: why so > |
| 03:02 | servo | use httpkit + compojure |
| 03:02 | beamso | i thought noir was deprecated but lib-noir wasn't |
| 03:02 | servo | i never said lib-noir was deprecated ;) |
| 03:02 | beamso | ah |
| 03:03 | dhruvasagar | servo: checking out httpkit |
| 03:03 | servo | httpkit is the shiz |
| 03:03 | dhruvasagar | servo: interesting, my familiarity to nodejs might come in handy |
| 03:04 | clgv | dhruvasagar: ring+compojure is pretty standard |
| 03:04 | dhruvasagar | clgv: hey :) |
| 03:04 | dbasch | dhruvasagar: start with compojure and see if that’s enough for what you want to build |
| 03:05 | dhruvasagar | dbasch: what about templating? |
| 03:06 | servo | i use hiccup |
| 03:06 | servo | but i hear good things about enlive |
| 03:06 | dbasch | dhruvasagar: whatever you like, really |
| 03:06 | dbasch | hiccup is ok |
| 03:06 | clgv | servo: yeah well, hiccup is not really templating, you'll force you designers to learn the EDN part of Clojure ;) |
| 03:07 | servo | i consider that a win |
| 03:07 | dbasch | or you could go the api / client-side app route |
| 03:09 | servo | im kinda of the opinion that only static data should be spit out as html |
| 03:09 | servo | and data should be used to update dom using reactjs et al |
| 03:09 | dhruvasagar | servo: I agree |
| 03:09 | dhruvasagar | servo: reactjs / angular / knockout ? |
| 03:09 | beamso | sometimes my html output isn't for browsers :/ |
| 03:09 | servo | what reads html besides browsers? |
| 03:10 | beamso | wkhtmltopdf |
| 03:10 | dhruvasagar | servo: he didn't mention html |
| 03:10 | dhruvasagar | servo: oops my bad |
| 03:10 | servo | ok |
| 03:11 | servo | so for the other 99% of use cases id say my opinion still stands |
| 03:12 | dhruvasagar | servo: whatever you said is pretty much http standard... |
| 03:12 | dhruvasagar | servo: I can't output dynamic data as html...unless I am thinking wrong |
| 03:13 | servo | dynamic on the server side |
| 03:13 | servo | before render |
| 03:14 | dhruvasagar | is :use deprecated ? |
| 03:14 | beamso | i take it that it's easy to use reactjs with REST resources? |
| 03:14 | dhruvasagar | beamso: I think so |
| 03:14 | clgv | yes you shoud only use "use" on the repl |
| 03:14 | dhruvasagar | beamso: but I think either angular or knockout or even backbone would do good too |
| 03:15 | dhruvasagar | clgv: thanks |
| 03:15 | servo | im a big fan of react |
| 03:15 | beamso | i didn't like what i saw of angular |
| 03:15 | dhruvasagar | servo: tbh I haven't used it much |
| 03:15 | servo | learning curve with angular is too steep |
| 03:15 | clgv | (:require [my.awesome.namespace :as an]) with (an/my-fn ...) makes it clear where the function is defined |
| 03:15 | dhruvasagar | so far the most that i've liked is knockout |
| 03:16 | dhruvasagar | knockoutjs is pretty good, have started disliking backbonejs since I used knockoutjs |
| 03:16 | servo | theres a cool clojurescript lib for react called om |
| 03:16 | servo | although personally i like to write native javascript |
| 03:16 | dhruvasagar | servo: me too |
| 03:17 | dhruvasagar | servo: I did like Coffeescript for a bit, but then I guess I just didn't groke js well enough then |
| 03:18 | servo | coffee script is ok. one good thing is that it's guaranteed to pass lint in script mode everytime |
| 03:18 | servo | strict mode* |
| 03:18 | sjy | i still like coffeescript. are you saying there comes a level of js zen where you actually want to mess around with prototypes? |
| 03:18 | dhruvasagar | sjy: well sort of, I think it's more to do with the ease of debugging |
| 03:20 | servo | not everyone likes coffeescript and when you're on a team you force people to maintain code. vanilla javascript is standard. its mostly a political thing |
| 03:20 | sjy | fair point, i don't use coffeescript at work. tbh 90% of the benefit for me is not having to write out "function" |
| 03:21 | servo | function is only one more character than (defn ) |
| 03:23 | servo | although most editors will autocomplete the trailing ) |
| 03:24 | dhruvasagar | sjy: you can always use snippets |
| 03:24 | servo | snippets? |
| 03:25 | dhruvasagar | servo: what editor do you use ? |
| 03:25 | dhruvasagar | servo: I guess you could call them templates too ? |
| 03:25 | servo | sublime |
| 03:25 | dhruvasagar | servo: or bundles / |
| 03:25 | servo | ah |
| 03:25 | servo | i know what you're talkign about now |
| 03:27 | servo | bengillies: you have the same last name as me |
| 03:28 | dhruvasagar | servo: and that would be ? |
| 03:29 | servo | gillies |
| 03:29 | servo | obviously |
| 03:30 | servo | :) |
| 03:30 | dhruvasagar | servo: k :) |
| 03:31 | servo | almost have 1000 messages logged from #ubuntu into datomic woo |
| 03:32 | dhruvasagar | servo: interesting datomic |
| 03:33 | dhruvasagar | servo: wonder how they manage the queries since they maintain all versions / changes of a record (document?) |
| 03:33 | servo | datomic is to databases as jesus is to sinners |
| 03:34 | servo | dhruvasagar: queries happen in the application |
| 03:34 | dhruvasagar | servo: I meant resolving queries |
| 03:34 | servo | the data store is just a binary blob key value covering index |
| 03:34 | dhruvasagar | servo: I suppose they just get the latest version |
| 03:35 | servo | its the datom with newest transaction id |
| 03:36 | servo | theres an index that groups transaction ids |
| 03:39 | dhruvasagar | servo: cool |
| 03:39 | dhruvasagar | servo: sounds interesting although might force a lot of horizontal scaling and backups etc will be slower etc |
| 03:39 | dhruvasagar | servo: write performance would also be compromised a little |
| 03:40 | dhruvasagar | servo: still an interesting idea especially considering read is the most frequent operation |
| 03:45 | servo | writes are slower only in theory |
| 03:46 | servo | with dynamodb cranked up you will have to try really hard for transactor to get away from you |
| 03:49 | dhruvasagar | servo: k |
| 05:40 | jcidaho | Anyone tried https://github.com/sunng87/hbs? |
| 05:40 | jcidaho | handlebars for Clojure? |
| 06:13 | clgv | jcidaho: sparse docs. syntax for variables looks similar to selmer but no idea what the collection syntax looks like |
| 06:24 | jcidaho | clgv: Have you used Selmer? We are analyzing templating options |
| 06:25 | jcidaho | we have a mixed team of Clojurians and front end ppl who want to hack on the HTML templates |
| 06:25 | jcidaho | Something mustache related is the current favourite option, but the logic-less side isn't so appealing |
| 06:26 | clgv | jcidaho: one of our students is using it for his project. so we'll see how it performs... |
| 06:26 | Glenjamin | i'm not clear why you'd use mustache if you don't go logic-less? |
| 06:26 | Glenjamin | the main selling point was portability, i thought |
| 06:27 | jcidaho | Glenjamin - it's an easy templating language for UX devs + Clojure server-side devs to converge, plus the template can be used client-side, the door is open to that possibility |
| 06:28 | Glenjamin | jcidaho: as soon as you add logic, the server-client stuff gets much harder. unless you're using a language that runs both sides i guess |
| 06:28 | Glenjamin | raw mustache gets is client/server portability by having very few features |
| 06:29 | jcidaho | Glenjamin - Yeah. Handlebars is an option, so long as both server-side and client-side use the same extensions |
| 06:29 | jcidaho | I'm tempted by Antlers too |
| 06:29 | Glenjamin | mm, whenever i've used mustache i've done an explicit "presenter" layer |
| 06:30 | jcidaho | Glenjamin - makes sense - I've seen a large project where we didn't do that, and wish we had |
| 06:32 | Glenjamin | yeah, mustache trades off power for portability - so you have to put the power somewhere else or its just a mess |
| 06:33 | Glenjamin | but if you want UX people to be able to make significant changes to rendering logic it probably isn't a good fit |
| 06:34 | jcidaho | I wonder what are the other options? Hiccup would be too hard core for them, as would Enlive.. |
| 06:34 | Glenjamin | something derived from the django/jinga/twig family i guess |
| 06:36 | jcidaho | Selma |
| 06:36 | martintrojer | can you render selmer templates in the client? |
| 06:38 | jcidaho | I guess if you need to, you can just use pure mustache, which is a subset of Selma.. (haven't used Selma, so making an educated guess) |
| 06:41 | locks | selma? |
| 06:41 | ssideris | jcidaho: with this scenario there is the added complexity of staying within mustache syntax in some cases and not staying within it in some others |
| 06:42 | jcidaho | yup - templates living in a special directory that swing both ways, and are restricted to normal mustache |
| 06:42 | jcidaho | a price must be paid somewhere.. |
| 06:42 | jcidaho | https://github.com/yogthos/Selmer |
| 06:44 | locks | thanks jcidaho, that was proving tricky to search for |
| 06:47 | jcidaho | Sorry, I typoed |
| 07:37 | CookedGr1phon | Rather than the error message "nth not supported on this type", for the sake of clojure beginners, would it not make more sense to say something like "Was expecting a value which supports nth, e.g. a vector" |
| 07:38 | CookedGr1phon | and while we're at it, what about printing the value that's at fault, rather than just its type |
| 07:39 | CookedGr1phon | it really bugs me that error messages almost never show you what you passed in to make it complain, just make cryptic comments about how it was wrong |
| 07:57 | clgv | CookedGr1phon: yeah would be awesome if the clojure compiler would throw ExceptionInfo instances with additional context data |
| 07:58 | CookedGr1phon | well ideally we could browse all the values at every stage in the stack frame, but I'd settle for up to 30 characters of the pr-str'd value that's caused the issue in the message |
| 07:59 | CookedGr1phon | (any more than that you might make the error message stupidly large |
| 07:59 | CookedGr1phon | but a snippet is usually enough to give you an idea where to look for your error |
| 07:59 | clgv | well if it used ExceptionInfo the REPL frontends could implement functions to investigate that |
| 08:01 | CookedGr1phon | guess so |
| 08:02 | CookedGr1phon | getting more information (specifically locals from stack frames) into exceptions would make working with clojure 100x smoother |
| 08:03 | Glenjamin | there's a suggestion in the clojure wiki about being able to run in different modes |
| 08:03 | Glenjamin | you generally don't want locals-capture if you're in production or benchmarking, for example |
| 08:03 | Glenjamin | but you would want that in dev |
| 08:03 | CookedGr1phon | sounds promising |
| 08:25 | borkdude | I got this in my profiles.clj: https://www.refheap.com/85253 - and this in my project.clj: :profiles {:ring-server {:dependencies [[org.immutant/immutant-jobs "1.1.1"]]}} |
| 08:26 | borkdude | yet when I start my project like this: lein with-profile ring-server ring server |
| 08:26 | borkdude | I get this: Exception in thread "main" java.lang.RuntimeException: No reader function for tag spy/p, compiling:(fuod/report.clj:206:72) |
| 08:26 | borkdude | help. |
| 08:27 | clgv | borkdude: you specify dependencies in your profile.clj? that's very likely a really bad idea |
| 08:27 | clgv | borkdude: oh wait. missread "lein-ring" as "ring" sorry |
| 08:28 | agarman | clgv it's not a bad idea, just one that you need to be careful with as you can accidentally use something in a project and forget to add it to the project |
| 08:29 | borkdude | it is an idea I got from http://dev.solita.fi/2014/03/18/pimp-my-repl.html |
| 08:29 | Glenjamin | that sounds like it makes it a bad idea to me :) |
| 08:29 | borkdude | only deps for debugging purposes |
| 08:29 | Glenjamin | oh right, debugging / tooling dependencies |
| 08:29 | agarman | I use it for alembic, fresh, criterium, sigmund, better stack trace etc. |
| 08:29 | Glenjamin | i see now |
| 08:29 | agarman | lots of stuff that just doesn't belong in a project.clj |
| 08:30 | Glenjamin | borkdude: try lein with-profile ring-server classpath |
| 08:31 | clgv | agarman: yeah tools are fine, but not something like "ring" ;) |
| 08:32 | agarman | I do keep separate profiles for when I want to launch and incanter, datomic or postgresql repl |
| 08:32 | AWizzArd | Does Jetty, Ring or Compojure have an intelligent way on how to treat gzipped files? I could easily add a with-gzip middleware, but this would cost cpu on each request. Instead I want to pre-gzip my static files and have them delivered. |
| 08:32 | clgv | borkdude: but it is possible that the :user profile is not used for ring-server you should check that |
| 08:33 | borkdude | ah, the problem might be that I first have to load the program, then add the #spy/p thing, because of some dynamism |
| 08:35 | justin_smith | /join #caribou |
| 08:35 | justin_smith | err |
| 08:39 | borkdude | and that it fails when I load it at firstah wait. if I start with lein with-profile ring-server,user ring server |
| 08:40 | borkdude | sorry. if I start with lein with-profile ring-server,user ring server I get this error msg: Exception in thread "main" java.lang.IllegalStateException: Attempting to call unbound fn: #'spyscope.core/print-log, compiling:(fuod/report.clj:206:72) |
| 08:42 | justin_smith | AWizzArd: I think hlship is working on a ring content middleware that would cover issues like that - he is also the guy behind the tapestry java lib |
| 08:44 | justin_smith | https://github.com/hlship/dieter |
| 08:44 | justin_smith | oh, never mind, that doesn't do gzip (yet?) |
| 08:47 | clgv | borkdude: huh. how about adding spyscope to the dev dependencies or dependencies of the project and see whether that works first? then you can move it farther away incrementally and see when it fails |
| 08:47 | borkdude | clgv good idea |
| 08:49 | AWizzArd | justin_smith: yeah, a middleware that checks when "game.html" is requested if there is also a "game.html.gzip" and deliver that, along with the right response headers. |
| 08:49 | justin_smith | AWizzArd: and also maybe generate game.html.gzip if that does not exist yet - for static files at least |
| 08:49 | justin_smith | this would be tricky with templates |
| 08:50 | AWizzArd | I would be happy enough if it didn’t try to gzip explicitly, just serving the corresponding files if they should exist, or just serve what was requested in the first place. |
| 08:52 | justin_smith | now that I think about it - why not a wrapper for wrap-resource, where it first looks for foo.bar.gzip (returning if found) and otherwise for foo.bar |
| 08:52 | justin_smith | that should be like a 5 line middleware |
| 08:52 | clgv | AWizzArd: with-gzip middleware using core.cache? |
| 08:53 | AWizzArd | clgv: intriguing |
| 08:54 | Glenjamin | is there a load balancer / reverse proxy between your app and the internet? |
| 08:54 | Glenjamin | i'd normally just have my app return proper mime types and put this sort of thing there |
| 08:54 | AWizzArd | Glenjamin: not yet, but I guess nginx is just a question of time. |
| 08:55 | justin_smith | (inc Glenjamin) |
| 08:55 | lazybot | ⇒ 3 |
| 08:55 | justin_smith | yeah, let nginx or varnish handle that actually |
| 08:55 | Glenjamin | in that case with-gzip + proper cache headers will probably be fine |
| 08:56 | AWizzArd | Glenjamin: so nginx would not forward requests of "game.js" to my Jetty anymore, but instead cache&deliver game.js.gzip itself? |
| 08:56 | Glenjamin | yeah, i'd maybe have a deploy step that created assets and gzipped versions |
| 08:56 | justin_smith | AWizzArd: yeah, you can configure nginx to do that |
| 08:56 | Glenjamin | although ideally you want to put a hash in the URL, the cache forever |
| 08:56 | borkdude | argh, context switch from another project to this clojure project. why is this false? (== 0M 0.000M) |
| 08:56 | justin_smith | and that is better than serving static resources from ring |
| 08:57 | AWizzArd | Okay, sounds fine then, thx guys. |
| 08:57 | justin_smith | borkdude: == respects float vs. integral distinction iirc |
| 08:57 | justin_smith | borkdude: what is your version? this stuff has been in flux a little lately |
| 08:58 | justin_smith | ,(== 0M 0.000M) |
| 08:58 | clojurebot | true |
| 08:58 | justin_smith | maybe update your version |
| 08:58 | borkdude | 1.5.1 still |
| 08:58 | justin_smith | ,*clojure-version* |
| 08:58 | clojurebot | {:major 1, :minor 6, :incremental 0, :qualifier nil} |
| 08:58 | borkdude | ok I'll upgrade |
| 08:59 | borkdude | ah this could also explain why I'm seeing different results locally compared to on the server. if I use immutant, does it respect the clojure version of the project? |
| 08:59 | justin_smith | I don't know immutant |
| 08:59 | tcrawley | borkdude: yes, Immutant will use the clojure dep in your project.clj |
| 08:59 | borkdude | ok, then it doesn't explain it :) |
| 09:00 | borkdude | what is the latest clojure, 1.6.0? or 1.6.1? ? |
| 09:00 | tcrawley | 1.6.0 |
| 09:00 | borkdude | k |
| 09:00 | martinklepsch | I'm processing lots of data and my JVM just crashed because there was no more memory available (on a 512mb machine ;D) — is there anything that I can do to make that work or should I just go for more ram? |
| 09:01 | borkdude | martinklepsch you can increase the default heap space |
| 09:01 | justin_smith | borkdude: when the machine has 512 max that won't go too far |
| 09:01 | borkdude | justin_smith true, but mayb it's not even using all of that |
| 09:03 | hyPiRion | martinklepsch: would you expect it to crash? If possible, stream the data instead of reading it all in at once |
| 09:03 | hyPiRion | I have no idea if that's your issue, of course |
| 09:04 | martinklepsch | hyPiRion, it doesn't surprise me to much. I want to bulk insert stuff into elasticsearch so not sure if streaming would work in that context |
| 09:04 | hyPiRion | ah |
| 09:05 | martinklepsch | borkdude, just reading up on heap space a bit. can I do that with leiningen? I'm just running stuff from the repl on that server |
| 09:05 | borkdude | martinklepsch yeah, you can define jvm-opts |
| 09:05 | Glenjamin | if the machine only has 512, you'll just have to rely on lazy sequences |
| 09:06 | borkdude | martinklepsch but I'd have to look it up also |
| 09:06 | Glenjamin | steer clear of big vectors or maps |
| 09:06 | martinklepsch | borkdude |
| 09:06 | martinklepsch | http://stackoverflow.com/questions/3757223/jvm-options-using-leiningen |
| 09:06 | borkdude | martinklepsch the answer from 2010, I would also check in the leiningen docs |
| 09:07 | martinklepsch | borkdude, that still seems valid: https://github.com/technomancy/leiningen/blob/master/sample.project.clj |
| 09:07 | hyPiRion | martinklepsch: `:jvm-opts [your-jvm-opts]`. Eventually try to uberjar and run |
| 09:07 | justin_smith | you need ^:replace for some jvm-opts to really apply |
| 09:07 | justin_smith | otherwise they get overridden by some defaults |
| 09:07 | justin_smith | -server is one of those |
| 09:08 | martinklepsch | justin_smith, what does server do? |
| 09:08 | Glenjamin | -server is default, or -server doesn't get added? |
| 09:08 | hyPiRion | justin_smith: That was changed, I think it only applies to lein pre 2.0.x |
| 09:08 | Glenjamin | ah, right |
| 09:08 | justin_smith | hyPiRion: definitely applies to some 2.x |
| 09:08 | Glenjamin | i added -server recently and it seemed to work |
| 09:08 | Glenjamin | on latest |
| 09:08 | justin_smith | martinklepsch: changes the hotspot optimization strategy, and affects startup time |
| 09:09 | justin_smith | Glenjamin: good to know, thanks |
| 09:09 | hyPiRion | justin_smith: technomancy/leiningen#1230 |
| 09:09 | lazybot | Set default :jvm-opts in :base profile to :displace -- https://github.com/technomancy/leiningen/pull/1230 is closed |
| 09:10 | hyPiRion | So uh, pre 2.3 |
| 09:10 | justin_smith | cool, good to know that changed |
| 09:11 | hyPiRion | still an iffy problem though. Wish we could please everyone with some good defaults |
| 09:11 | rolfb | any mnemonics for remember which book is which of "Programming Clojure" and "Clojure Programming" ? |
| 09:12 | martinklepsch | so with 512mb ram I would go for something like :jvm-opts ["-Xmx265m"] or is it safe to use 512m as well? |
| 09:13 | justin_smith | depends, does your OS use memory? |
| 09:14 | martinklepsch | justin_smith, uh, yeah? |
| 09:15 | martinklepsch | I guess 512 mb is just not enough to run riemann, elasticsearch + my data intensive program. :D |
| 09:15 | martinklepsch | (which is fine :)) |
| 10:04 | martinklepsch | is there something about running lein as root that will absolutely ruin my life? |
| 10:06 | justin_smith | well, lein is a dev and build tool... |
| 10:06 | justin_smith | why do you want to run lein as root? |
| 10:08 | clgv | martinklepsch: except from the usual reasons not to run any application programs as root if not necessary? |
| 10:08 | martinklepsch | justin_smith, clgv, I'm just toying around and am to lazy to setup non-root for that :P |
| 10:09 | martinklepsch | switching to a 2GB machine seemed to fix the problem btw |
| 10:09 | justin_smith | you are on a system that has no non-root user? |
| 10:09 | clgv | martinklepsch: too lazy for a "useradd ..." ? |
| 10:09 | justin_smith | making a user account takes about 1 minute tops |
| 10:10 | martinklepsch | yeah, but than I need to switch to do certain like running docker and stuff |
| 10:10 | martinklepsch | but yeah, maybe I should just do it |
| 10:11 | justin_smith | martinklepsch: consider making an uberjar on the dev machine, and just running java -jar on prod also |
| 10:11 | martinklepsch | justin_smith, would that allow me to jump into a repl? |
| 10:11 | martinklepsch | I just wondered — when I do a lot of data processing and print all that data to the repl because the function I'm calling just returns that data, could that be the reason for memory issues? |
| 10:12 | martinklepsch | probably yes right? |
| 10:12 | martinklepsch | because that 2gig machine just crashed too haha |
| 10:12 | justin_smith | martinklepsch: if you use tools.nrepl.server you can connect to the app with a repl |
| 10:12 | martinklepsch | REMOTELY AS WELL?!! |
| 10:12 | martinklepsch | that would be crazy cool |
| 10:13 | justin_smith | make an ssh tunnel |
| 10:13 | martinklepsch | yeah |
| 10:13 | justin_smith | don't open nrepl to the whole world :) |
| 10:13 | justin_smith | yes, works remotely |
| 10:13 | justin_smith | also, use an ssh tunnel to connect a local visualvm (or other profiler) process to the server |
| 10:13 | justin_smith | to see what is really happening, where resources are actually going, etc |
| 10:13 | martinklepsch | haha, I mean, I run my stuff as root so I can open the nrepl to the world as well right ;) |
| 10:13 | justin_smith | visualvm comes with the jdk |
| 10:16 | borkdude | can I ask a question about cursive clojure here? |
| 10:17 | justin_smith | martinklepsch: http://java.dzone.com/articles/how-debug-remote-java-applicat this shows how to start the java process with a debug port open |
| 10:18 | justin_smith | you can add the args to the lein :jvm-opts if you still don't want to uberjar (though I still recommend making uberjars and not running lein on prod) |
| 10:18 | borkdude | my question is: how can I debug while starting lein ring server in cursive clojure |
| 10:18 | martinklepsch | justin_smith, eclipse?! ;P |
| 10:18 | justin_smith | hah, stop at the jvm setup step |
| 10:18 | justin_smith | and connect a real profiler |
| 10:19 | martinklepsch | justin_smith, yeah will probably do that in the future. seems saner and I wanted to understand that whole uberjar stuff better anyway |
| 10:19 | justin_smith | it's not super hard, just means you need a compiled -main for the app |
| 10:20 | justin_smith | there is a way to specify the jar, then the class, then the args so you don't need a compiled main as well |
| 10:20 | martinklepsch | justin_smith, yeah got so far the last time but ran into other issues and then stopped |
| 10:20 | Glenjamin | if you uberjar, presumably there's no way for it to pick up the :jvm_opts from your project.clj anymore? |
| 10:20 | borkdude | or lein immutant run for that matter |
| 10:21 | justin_smith | Glenjamin: right, I typically make a short startup scripts with my prod jvm opts |
| 10:21 | Glenjamin | makes sense |
| 10:22 | justin_smith | it just eliminates a few moving parts |
| 10:22 | justin_smith | and makes restarts on the server much faster |
| 10:22 | martinklepsch | justin_smith, just for the interim — could it be that printing all that stuff to the repl actually causes the memory to get full because it's stored until the fn returns? |
| 10:23 | justin_smith | martinklepsch: depends on whether you are holding on to the head of lazy sequences |
| 10:23 | martinklepsch | holding on to the head? |
| 10:23 | justin_smith | lazy sequences reduce memory usage if you iterate over them but don't have abinding to the head (the first element) |
| 10:23 | justin_smith | if the head is bound, then all of the lazy sequence must be stored |
| 10:24 | justin_smith | because it is accessible via the head |
| 10:24 | justin_smith | if you print the lazy sequence in its entirety, then the whole thing will be realized |
| 10:25 | justin_smith | if you instead print as you process, and don't hold onto the head, then lazy sequences can actually help you reduce memory usage |
| 10:25 | justin_smith | this means not binding the entire sequence, instead using it as it is generated |
| 10:25 | martinklepsch | justin_smith, the printing just happens as a consequence of the called function returning all the data |
| 10:26 | justin_smith | (let [r (range)] (map f r)) <- this eats up heap |
| 10:26 | justin_smith | (map f (range)) <- this doesn't neccessarily eat up heap |
| 10:26 | justin_smith | in the second case, clojure knows that nobody can actually access the previous elements of (range) so it can let them be collected |
| 10:27 | martinklepsch | and the repl does what you just described I think, i.e. it waits until the function is done and then attempts to print it all |
| 10:27 | justin_smith | it does the first thing, holding onto the entire lazy-seq |
| 10:27 | justin_smith | you should print element by element |
| 10:28 | martinklepsch | yeah |
| 10:28 | justin_smith | (if you want to conserve mem) |
| 10:28 | martinklepsch | think I understood how to fix it, thank you! |
| 10:28 | martinklepsch | (inc justin_smith) |
| 10:28 | lazybot | ⇒ 42 |
| 10:28 | martinklepsch | hah! |
| 10:29 | justin_smith | np |
| 10:29 | martinklepsch | I always saw people doing that, hope it's fine that I just did it :) |
| 10:29 | justin_smith | yeah, it's a meaningless number, but it's all good |
| 10:32 | mikerod | Non-dynamic vars still are deref'ed every time they are accessed (as long as their value is not inlined) correct? |
| 10:32 | mikerod | So I write: (defn my-test [x] (some-other-fn x)) |
| 10:33 | mikerod | And call: (my-test 5) ;= `some-other-fn` is deref'ed during evaluation right? This is true for the AOT-compiled version of this `my-test` fn as well right? |
| 10:33 | mikerod | I have done some digging and I believe this is accurate. |
| 10:34 | mikerod | And it also is the only way I could see something like `alter-var-root` or `with-redefs` to work to change the behavior of vars referenced in the BodyExpr of other fn's |
| 10:34 | Glenjamin | you are correct |
| 10:36 | agarman | it's a bit more subtle though |
| 10:37 | clgv | mikerod: correct but there is a slight problem if the first function was a primitive one (i.e. primitive long or double in its signature) |
| 10:37 | agarman | ,(def *name* "world") |
| 10:37 | clojurebot | #<CompilerException java.lang.SecurityException: denied, compiling:(NO_SOURCE_PATH:0:0)> |
| 10:37 | clgv | ,(def a 1) |
| 10:37 | clojurebot | #'sandbox/a |
| 10:37 | clgv | interesting |
| 10:38 | agarman | if you are in a repl and redefine a var as dynamic |
| 10:38 | Glenjamin | ,(do (def a) (identical? a (deref (var a))) |
| 10:38 | clojurebot | #<RuntimeException java.lang.RuntimeException: EOF while reading> |
| 10:38 | agarman | any existing references to the var will continue to lookup the original var |
| 10:39 | agarman | that is, non-dynamic vars get cached |
| 10:39 | agarman | static vars get cached |
| 10:39 | agarman | dynamic vars do not |
| 10:39 | mikerod | Hmm, interesting. |
| 10:40 | mikerod | So a static var really shouldn't be attempted to be redefined in "production" code it would seem. |
| 10:40 | mikerod | Since it seems a bit risky on the scenarios where it may not be re-looked-up |
| 10:41 | mikerod | I have heard it is "bad practice", but I'm just trying to think if this relates to some reasons why. |
| 10:41 | agarman | you can re-point an existing var |
| 10:42 | agarman | you just can't put a new var the the same symbol in the namespace and expect to have occurring usages of that symbol to point to your new var...unless you're var started out as ^:dynamic |
| 10:43 | agarman | there is a nice clojure/west video that describes how all this works much better than I could in IRC :-) |
| 10:44 | mikerod | agarman: Yeah, that makes sense. I can dig for the video and see if I've watched it before. If it is pretty new, chances are I haven't. |
| 10:45 | agarman | I'll pass the link, just looking for it right now |
| 10:45 | agarman | https://www.youtube.com/watch?v=8NUI07y1SlQ |
| 10:46 | agarman | https://www.youtube.com/watch?feature=player_detailpage&v=8NUI07y1SlQ#t=443 |
| 10:46 | agarman | that's roughly where he starts talking about static vs dynamic |
| 10:46 | agarman | if you're impatient :-) |
| 10:46 | mikerod | hah, thanks for the insight. |
| 10:47 | agarman | yw |
| 10:47 | mikerod | This looks good and I haven't seen it before. I'll check it out. |
| 10:52 | martinklepsch | justin_smith, this nrepl server stuff gets me really excited |
| 10:52 | martinklepsch | makes me understand this whole "modify running programs" thing |
| 10:53 | justin_smith | martinklepsch: yeah, it is handy - I typically have a conditional block that starts up an nrepl server based on an env var in pretty much every top level project |
| 10:54 | martinklepsch | justin_smith, yeah, makes perfect sense |
| 10:56 | martinklepsch | that would pretty much be my main function I guess ;D |
| 10:57 | justin_smith | next step after that: once a function misbehaves in a way you don't understand, go into its namespace at runtime and (def debug (atom {})) and then add apropriate calls to (swap! debug assoc (java.util.Date.) ["description of place" some values at this place]) |
| 10:57 | justin_smith | and then use your repl foo to investigate the values going on :) |
| 11:05 | AWizzArd | core.async: put! / take! vs. >! / <! — what are the differences? |
| 11:06 | AWizzArd | Is (put! my-chan 15) the same as (go (>! my-chan 15))? |
| 11:06 | teslanick | put! and take! can be used outside goblocks |
| 11:06 | teslanick | And don't park |
| 11:07 | teslanick | note that take! takes a callback function to avoid parking for information. |
| 11:08 | AWizzArd | How can put! *not* park if there is nobody reading from the chan? |
| 11:08 | teslanick | It also takes a callback if you care about when something is removed from the channel |
| 11:09 | teslanick | put! and take! are (at least from the examples I've seen) used on the edges of your core.async machine in parts of your system that need to operate asynchronously |
| 11:10 | teslanick | Note that if you want to park, you can use >!! and <!! outside a goblock. Probably not a good idea, but... |
| 11:10 | AWizzArd | I’m not sure if it is otherwise equivalent to (go (>! my-chan 15)). |
| 11:11 | teslanick | put! and (go (>! ...)) aren't equivalent. They do different things, which is why they have different names/idioms. ;) |
| 11:12 | ttallman | quit |
| 11:38 | technomancy | I ... uh http://i.imgur.com/zfqbtYL.png |
| 11:38 | agarman | lmao |
| 11:42 | clgv | awesome :P |
| 11:42 | bbloom | heh |
| 11:50 | tbaldridge | I actually heard someone use an argument once that "OOP may be more verbose than FP, but if all programmers moved to FP, then we'd have an overpopulation software engineers, and I'd have to fight harder for a job". |
| 11:52 | teslanick | Because less code would need to be written to solve the same problems? |
| 11:53 | Glenjamin | i'm not sure that's possible |
| 11:54 | Glenjamin | the overpopulation bit |
| 11:54 | Glenjamin | we'd just make more things |
| 11:54 | tbaldridge | agreed. but I pretty much gave up at that part of the argument. |
| 12:01 | technomancy | there's actually a really interesting paradox around that |
| 12:01 | technomancy | https://en.wikipedia.org/wiki/Jevons_paradox |
| 12:01 | technomancy | tbaldridge: next time you see him, you can point him to wikipedia and 19th-century coal consumption |
| 12:02 | Glenjamin | seems to apply to computer gui apps too |
| 12:03 | joegallo | ugh, it's the old "if everyone has fast-pass/ez-pass, then the traffic will be on the streets rather than at the toll lanes" argument |
| 12:03 | joegallo | barf |
| 12:05 | bbloom | technomancy: that's an interesting article. thanks |
| 12:06 | joegallo | now if you'll excuse me, i'm going to go stimulate the economy by burning down a bunch of buildings |
| 12:07 | hiredman | maybe start a few wars |
| 12:07 | mikerod | I launch the REPL with some AOT-compiled clj record types on the classpath. When attempt to reload this record, I am able to create new instances of the same class that are loaded with a DynamicClassLoader. However, when I do (.getClassLoader some.class.Name) in the REPL, it is still resolving to the original class loaded on the AppClassLoader. |
| 12:08 | mikerod | *by "same class" I meant the redefinition of the same class name. |
| 12:09 | bbloom | tis same sort of stupid broken thinking is what causes massively successful companies to fail to innovate |
| 12:09 | mikerod | The consequence of this is that in my REPL, I construct (new some.class.Name) and (some.class/->Name) and get instances of 2 different classes. |
| 12:10 | bbloom | they hold on to their initial successes and think the world won't change around them, assuming that b/c their inventions produced wealth in the past, that they will always be their primary sources of wealth... which becomes a self-fulfilling prophecy by being their ONLY source of wealth |
| 12:11 | technomancy | bbloom: yeah, I figure Jevon's paradox is also relevant to code.org naysayers |
| 12:11 | bbloom | technomancy: very. |
| 12:11 | cbp | java.lang.ThreadDeath |
| 12:12 | bbloom | cbp: argh. i hate that ThreadDeath exception |
| 12:12 | cbp | such description, very understandable |
| 12:12 | bbloom | if you catch Throwable, you actually need to remember to RETHROW ThreadDeath, otherwise you may never get out of an infinite loop |
| 12:13 | cbp | =/ |
| 12:13 | mikerod | tbaldridge: that argument made me laugh; but in a bad way |
| 12:15 | tbaldridge | I think the world would be a better place if everyone knew at least some coding. And no, we wouldn't have a problem with demand, because just like some people who write hate writing (me), we'd have people who knew how to code, but don't understand enough theory to do it as a profession. |
| 12:15 | tbaldridge | That is to say, anyone can code, but learning how to apply it properly takes time, like any profession. |
| 12:17 | mikerod | tbaldridge: agreed |
| 12:18 | angusiguess | @tbaldridge I guess one part of it is people's expectation that it be professional. Something not shared with, say, musical or artistic aptitude. |
| 12:22 | mikerod | So, does anyone know why the REPL doesn't eval Class literals as the newest definition of dynamically loaded types when the class was loaded initially by the AppClassLoader? |
| 12:22 | mikerod | To re-phrase my questions/observation on this. |
| 12:22 | borkdude | is it possible to find usages of a function in cider? |
| 12:25 | Bronsa | mikerod: http://dev.clojure.org/jira/browse/CLJ-979 probably related |
| 12:27 | mikerod | Bronsa: nice, this does seem to be on-topic |
| 12:27 | mikerod | thanks! |
| 12:27 | mikerod | It's a bit annoying. I just noticed it because I get test failures from reloading the defrecord |
| 12:28 | mikerod | because of an instance? check failing after that, but it is in the same ns as the defrecord, so I was expecting them to stay in sync. |
| 12:28 | mikerod | Fun |
| 12:29 | seangrove | I wonder how much bootstrapped cljs would help people get on the cljs wagon |
| 12:30 | Bronsa | mikerod: me & ambrosebs looked into this a bit a while ago while he was porting core.typed to tools.analyzer |
| 12:30 | bbloom | seangrove: probably not at all... why do you think it would? |
| 12:30 | bhauman | seangrove: do you have something particular in mind? |
| 12:30 | Bronsa | mikerod: another relevant ticket is probably http://dev.clojure.org/jira/browse/CLJ-371 which unfortunately got declined |
| 12:31 | mikerod | Bronsa: cool, it is all making sense now |
| 12:32 | Glenjamin | so the general theme seems to be you can AOT, or repl - but not really both |
| 12:32 | Bronsa | Glenjamin: yeah |
| 12:32 | mikerod | AOT is full of surprises |
| 12:32 | Glenjamin | which means you can't patch a protocol definition in a live app |
| 12:32 | seangrove | bbloom: A node.js developer is going to be pretty unnerved by the amount of jvm tooling to get start with cljs |
| 12:33 | seangrove | bbloom: Just removing that initial barrier, making it easier to get up and running |
| 12:33 | cbp | Is it possible to have a cljs repl when opening a file:// from a browser? |
| 12:33 | Glenjamin | jvm peeps probably underestimate how foreign all the jvm stuff is if you don't have a java background |
| 12:33 | nullptr | seangrove: as is a jquery developer |
| 12:33 | cbp | I mean I guess I know it's possible since Lighttable does it but is it possible with austin? |
| 12:34 | bbloom | seangrove: meanwhile, node.js requires a lot of C++ tooling to get started.... this is a presentation/readme problem and maybe automation problem, not a justification for self-hosting |
| 12:34 | nullptr | i'm very savvy with jvm stuff, have a reasonable amount of clojure experience, and am an expert in g closure, and i still found getting started with cljs maddening |
| 12:34 | Glenjamin | bbloom: not to run the JS |
| 12:34 | bbloom | ... and this is coming from a guy wants that :-P |
| 12:34 | Glenjamin | it's a single binary |
| 12:35 | bbloom | Glenjamin: not if you actually want to do anything useful it isn't... you also need the package manager: npm |
| 12:35 | seangrove | bbloom: Not a justification, of course not. Just a nice side-effect that it becomes far more portable for other envs |
| 12:35 | Glenjamin | ok, 2 binaries |
| 12:35 | bbloom | Glenjamin: bottom line: you need an installer |
| 12:35 | Glenjamin | there's not that many libs that need to c++ build |
| 12:35 | bbloom | what it installs is moot |
| 12:35 | seangrove | I know almost nothing about node.js personally, and I'm frustrated that I have to use npm sometimes |
| 12:35 | bbloom | npm is atrocious |
| 12:35 | expez | seangrove: any plans on adding a bit more documentation to your om-draggable component, it wasn't as easy as I'd hoped to put it to use. |
| 12:35 | Glenjamin | npm is the best :( |
| 12:35 | bbloom | Glenjamin: no, it really isn't |
| 12:35 | cbp | but npm solved dependency management |
| 12:36 | bbloom | lol |
| 12:36 | Glenjamin | no dependncy conflicts is great |
| 12:36 | seangrove | But it's the same frustration that node devs would experience on the cljs side. If you gave them the foundation, they'd hack cljs up in their own npm way and run with it |
| 12:36 | seangrove | expez: No, I'll probably just remove it. Been working on a much more all-encompassing approach to this stuff |
| 12:36 | expez | seangrove: aight, good to know! |
| 12:36 | seangrove | expez: I could probably change it a bit though so normal Om apps could use it, on reflection |
| 12:36 | Glenjamin | bbloom: what problems do you have with npm? i've generally found using it to be great |
| 12:37 | cbp | Is there a tool thingy that takes an html file as input and serves it through whatever web server? |
| 12:37 | stompyj | Glenjamin: it’s *always*[0] down and/slow [0] always meaning at least 2x a month |
| 12:38 | stompyj | and when you’re pushing to production 10x a day |
| 12:38 | stompyj | and deploys hang and/or outright fail |
| 12:38 | Glenjamin | then you use a caching proxy :s |
| 12:38 | Glenjamin | don't rely on a free external service for production deploys :) |
| 12:38 | Glenjamin | i got the impression bbloom had issues with the tool itself |
| 12:38 | stompyj | the fact it could have learned from rubygems.org and bundler |
| 12:38 | bbloom | even ignoring the downtime, i've had massive problems actually *using* it |
| 12:38 | Glenjamin | i assume people deploying clojure a lot use nexus instead of maven central |
| 12:39 | stompyj | and seemingly didn’t, isn’t encouraging |
| 12:39 | stompyj | oh, i’ve had tons of issues with it as well |
| 12:39 | bbloom | the node_modules thing is attrocious. there is nothing like bundler's lock files, which is also a complaint i have about lein |
| 12:39 | stompyj | one of my devs couldn’t create an account for weeks |
| 12:39 | stompyj | with no error returned |
| 12:39 | Glenjamin | bbloom: `npm shrinkwrap` does exactly what lock files do |
| 12:40 | Glenjamin | the local node_modules thing is my favourite bit :s |
| 12:40 | bbloom | Glenjamin: never head of shrinkwrap, looks like it isn't standard |
| 12:40 | Glenjamin | it's in the core package, but doesn't run unless you ask it to |
| 12:41 | bbloom | the package.json format, being json, can't have comments in it... which is insane |
| 12:41 | technomancy | bbloom: aren't lockfiles just there to work around the fact that everyone uses version ranges in bundler? |
| 12:41 | bbloom | technomancy: i dunno. i don't like version numbers, i like sha1s |
| 12:41 | bbloom | i like refspecs |
| 12:41 | technomancy | what's a refspec? |
| 12:41 | bbloom | https://www.kernel.org/pub/software/scm/git/docs/gitrevisions.html |
| 12:41 | technomancy | oh, sure |
| 12:41 | bbloom | see my rant on semver: http://www.brandonbloom.name/blog/2013/06/19/semver/ |
| 12:41 | Glenjamin | not having comments i can see, but it's more of a manifest rather than a config file - there shouldn't really be anything complex in there |
| 12:42 | bbloom | Glenjamin: it doesn't need to be complex to say "TODO: remove this dep" |
| 12:42 | technomancy | bbloom: are you ranting about publishers who use semver or people/tools who assume others use semver? |
| 12:42 | Glenjamin | i can see that |
| 12:42 | bbloom | technomancy: tools that assume semver |
| 12:43 | technomancy | right |
| 12:43 | Glenjamin | although echo "TODO: remove dep x" >> README.md is roughly as useful |
| 12:43 | bbloom | the node_modules directory is terrible b/c it confuses every damn tool i have... i have to add ignore rules to so many configs |
| 12:43 | technomancy | bbloom: version numbers are like ^:private imo; they contribute intent, but relying on their mechanism is madness. |
| 12:43 | bbloom | technomancy: indeed |
| 12:43 | technomancy | s/contribute/communicate/ |
| 12:44 | Glenjamin | my personal approach is ranges for libs that trust/assume semver - but lock down numbers in applications and check it works |
| 12:44 | technomancy | seems silly to be "against semver" for that reason though |
| 12:44 | martinklepsch | just trying to setup that repl server I found the following to launch it in main: https://groups.google.com/forum/#!topic/clojure/wWunRvmX5Co — but I wonder why that let binding & Thread/sleep is used? |
| 12:46 | bbloom | technomancy: you'll see my rant is balanced :-P |
| 12:46 | stompyj | Glenjamin: although, in all seriousness, “don’t like the package manager endorsed by the language? then don’t use it!” is a very dangerous stance for a community to take |
| 12:46 | technomancy | bbloom: I can see it there because I know what I'm looking for, but I think it would be easy to miss |
| 12:46 | stompyj | especially when go exists |
| 12:47 | Glenjamin | stompyj: i don't follow? if you don't like rubygems, you probably should use ruby |
| 12:47 | Glenjamin | etc |
| 12:49 | stompyj | In general, the JS/node community has had flippant responses to real concerns by people trying to use the technology stack |
| 12:49 | stompyj | the net result of that is going to be an exodus to Go, or a similar language |
| 12:49 | bbloom | i also generally hate tools that have interactive defaults & no obvious master flag for "I AM SCRIPTING THIS THING" |
| 12:50 | Glenjamin | go's dependency management story appears to be "you always get master, better hope no-one breaks you" |
| 12:50 | justin_smith | martinklepsch: I think the sleep is just for keeping the process going |
| 12:50 | technomancy | Glenjamin: no one would ever do such a horrible thing as break backwards-compatibility |
| 12:50 | Glenjamin | "If a library creator doesn't have the discipline to follow proper release practices and the idioms in the Go community, I think it can be argued that you probably don't want to be using their code in production either." |
| 12:50 | bbloom | yeah, which is why go-get is terrible, by why go is awesome for big company wide code bases (which i'm not a believer in, but understand it) |
| 12:50 | Glenjamin | thats a quote from the go community |
| 12:50 | justin_smith | martinklepsch: the let block is likely the trace of an incomplete refactoring |
| 12:51 | technomancy | Glenjamin: http://p.hagelb.org/oh-yeah.gif |
| 12:51 | technomancy | high-larious |
| 12:51 | Glenjamin | anyway, dependency management is hard |
| 12:51 | martinklepsch | justin_smith, would you mind pasting me some code how you did that? |
| 12:51 | justin_smith | martinklepsch: I think both can be eliminated, since the l in repl is for loop |
| 12:51 | technomancy | Glenjamin: "Life is hard. But it's a lot harder if you're stupid." |
| 12:51 | Glenjamin | heh |
| 12:51 | technomancy | I forget who said that. |
| 12:51 | martinklepsch | justin_smith, I tried it earlier without the sleep and I think it didn't work |
| 12:52 | justin_smith | (start-server :port 42042) should suffice - though you can add the sleep if it is exiting too soon on you |
| 12:52 | justin_smith | or a while loop that sleeps etc. |
| 12:52 | martinklepsch | deploying an uberjar is very cool btw :) |
| 12:52 | justin_smith | martinklepsch: yeah, definitely the RIGHT WAY™ |
| 12:53 | technomancy | bbloom: because at a company you can literally beat a path down to the offender's cubicle with pitchforks and torches? |
| 12:53 | martinklepsch | justin_smith, it's so crazy simple... I'm coming from ruby/rails and that's quite different :D |
| 12:53 | Glenjamin | are uberjars always AOTed, will you run into the dynamic reload of Record issue described above? |
| 12:54 | technomancy | Glenjamin: you can use uberjars without AOT |
| 12:54 | Glenjamin | ah neat |
| 12:54 | technomancy | you just have to use clojure.main as your entry point |
| 12:54 | justin_smith | martinklepsch: yeah... their deployment story is crazy - but look how many startups it created :P |
| 12:54 | technomancy | I don't know that I'd recommend it though; afaik the pitfalls of AOT don't apply in production |
| 12:55 | Glenjamin | unless you want to mess around in a repl on production i guess |
| 12:55 | technomancy | justin_smith: /me whistles innocently |
| 12:55 | Glenjamin | unsure if i do yet :) |
| 12:55 | justin_smith | martinklepsch: it is harder to make a business model out of "send us a jar and we will execute it" |
| 12:55 | technomancy | Glenjamin: true, you do have to be more careful with a repl |
| 12:55 | martinklepsch | justin_smith, looks like my previous try was just fine :) |
| 12:57 | rasmusto | just made this typo: lein eastwoord |
| 12:57 | justin_smith | haha, sounds dutch |
| 12:58 | rasmusto | was thinking of http://en.wikipedia.org/wiki/Die_antwoord maybe |
| 12:58 | rasmusto | dunno why I'd have muscle memory for that |
| 12:58 | justin_smith | or like an insane white south african hiphop performance art project |
| 12:58 | justin_smith | jynx |
| 12:58 | rasmusto | ,(range 10) |
| 12:58 | clojurebot | (0 1 2 3 4 ...) |
| 12:58 | bbloom | technomancy: if you "always ship master" and have a giant perforce tree, then everything is effectively defacto vendored anyway |
| 12:59 | bbloom | technomancy: and also pitchforks + cubicles |
| 13:00 | technomancy | bbloom: pretty soon the pitchfork thing will be possible in the OSS world with drone attacks though |
| 13:00 | seangrove | Necks to throttle. |
| 13:01 | TimMc | to whom? |
| 13:01 | rasmusto | seangrove: look in the mirror |
| 13:01 | seangrove | Wonderful mixing of third and first person there... |
| 13:02 | rasmusto | seangrove: jokes :) |
| 13:02 | seangrove | rasmusto: I need to delegate! |
| 13:02 | seangrove | Ordering food is easy, it's the last mile problem that hasn't been solved: take out box to mouth. |
| 13:02 | seangrove | But now we have... DroneForks! |
| 13:02 | rasmusto | I always picture that wallace and grommit morning routine |
| 13:03 | rasmusto | machine thing |
| 13:07 | martinklepsch | justin_smith, how do you access this nrepl in your prod env then? do you use ssh tunneling? |
| 13:07 | martinklepsch | (sorry if you mentioned that earlier) |
| 13:08 | justin_smith | martinklepsch: yeah, but usually I don't end up needing a repl in prod |
| 13:09 | martinklepsch | justin_smith, currently my whole programm does nothing on it's own (which is intended) so having a repl seems like the best way to control that remotely |
| 13:10 | technomancy | martinklepsch: you could use something like xmpp too if you want easier control from a mobile |
| 13:10 | technomancy | that's what I do with the bot in my lab |
| 13:10 | martinklepsch | technomancy, that sounds pretty cool but also a lot more complex |
| 13:11 | martinklepsch | technomancy, what do you send via xmpp then actually? |
| 13:11 | technomancy | martinklepsch: yeah, it means you have to decide up front which commands you want to expose over chat |
| 13:11 | technomancy | in my case it's just temperature querying and setting |
| 13:12 | technomancy | (also this is erlang rather than clojure, but whatever) |
| 13:12 | martinklepsch | technomancy yeah ok, thought so |
| 13:12 | technomancy | martinklepsch: actually... you could easily do a full repl over xmpp |
| 13:12 | technomancy | or you could do a repl that's restricted to only call functions in a given namespace |
| 13:13 | justin_smith | oh yeah, xmpp has the security layer taken care of |
| 13:13 | technomancy | https://github.com/technomancy/mire/blob/master/src/mire/commands.clj <- this does something like that |
| 13:13 | justin_smith | is there an easy xmpp lib for clojure? |
| 13:14 | martinklepsch | I'm fine with the repl and tunneling |
| 13:15 | martinklepsch | although I'm having trouble fguring out how to map a port on a remote machine that only listens on localhost to a local port on my machine :/ |
| 13:15 | justin_smith | ssh -L handles that pretty easily |
| 13:18 | justin_smith | ssh -L local-port:127.0.0.1:remote-port <host> |
| 13:18 | martinklepsch | justin_smith, yeah I have something like this but doesn't seem to access the port through localhost on the remote machine: ssh -L root@host -L 4242:host:42042 -N |
| 13:18 | justin_smith | no, 127.0.0.1 |
| 13:18 | justin_smith | is manditory - means local |
| 13:19 | justin_smith | host means treat it as a remote access, which is denied which is the reason for the tunnel |
| 13:19 | martinklepsch | ah ! |
| 13:19 | martinklepsch | thank you! |
| 13:19 | martinklepsch | works now |
| 13:19 | justin_smith | I guess you can also specify localhost instead of 127.0.0.1 but 127.0.0.1 may work in some circumstances where the host is misconfigured |
| 13:20 | martinklepsch | justin_smith, yeah was thinking in that direction just wasn't aware that I can put in 127.0.0.1 in that place |
| 13:21 | martinklepsch | justin_smith, you've helped me tons today! thanks so much! |
| 13:22 | justin_smith | np |
| 13:25 | martinklepsch | sometimes when I run java -jar my-thing.jar I can't cancel it with ctrl-c anymore, anyone an idea why that is? |
| 13:26 | justin_smith | martinklepsch: are you running agents? are you catching Throwable? |
| 13:26 | justin_smith | anyway, kill -9 is the brutal way, which almost always works |
| 13:27 | martinklepsch | yeah, having some (catch) statements in there |
| 13:27 | martinklepsch | justin_smith, yeah that was what I did the first time. just wondered why that sometimes happens and sometimes not |
| 13:27 | justin_smith | if your catch is Throwable, you should rethrow if you get the interrupt signal |
| 13:32 | martinklepsch | cheers everyone for being so incredibly helpful today! you made my day (really!) have a good day/evening! |
| 13:45 | guns | ambrosebs: I was able to build that Closeable linter with tools.analyzer; it was just as easy as you said. thanks again for the tip |
| 13:45 | ambrosebs | guns: very nice |
| 13:56 | nillkill | hmm is there an easy way to load a var from a .clj file and get the name of the var? So something like (load-file https://github.com/Parsely/streamparse/blob/master/streamparse/bootstrap/project/topologies/wordcount.clj) then pull the name of the var (“wordcount” in this case) as well as the evaluated form? |
| 13:57 | nillkill | or a better question perhaps, should we be doing this w/ something other than (var-get (load-file …)) |
| 14:00 | nillkill | i was hoping I could get (:name (meta (var-get (load-file …)))) but that doesn’t seem to work |
| 14:04 | Glenjamin | nillkill: are you expecting the var to be the last form in the loaded file? |
| 14:05 | nillkill | yeah, should only ever be one var in the file. looks like (meta (load-file “file..clj”)) will work |
| 14:05 | Glenjamin | i feel like that should work if you leave out the var-get |
| 14:05 | Glenjamin | yeah |
| 14:07 | technomancy | http://www.clojure.tn/images/stk-trc.png <- whoa, is this what you get with cider out of the box now? |
| 14:07 | ucb | technomancy: yes |
| 14:07 | hiredman | :( |
| 14:07 | ucb | technomancy: latest which is 0.7.0-alpha I believe |
| 14:07 | hiredman | hiding frames |
| 14:07 | technomancy | fancy ultra fresh |
| 14:07 | mstang | Best Java decompiler? |
| 14:08 | technomancy | I assume those are hyperlinks? |
| 14:08 | nillkill | Glenjamin: how would I still evaluate that var after the load-file? |
| 14:08 | nillkill | i guess do a get-var later on |
| 14:08 | Glenjamin | if you have name and ns, you should be able to fish it back out |
| 14:09 | Glenjamin | or (let [var (load-file)] { :name (:name (meta var)) :var var }) |
| 14:09 | Glenjamin | something like that |
| 14:09 | ucb | technomancy: which ones? the headings? Yes, they hide/show different sections of the stacktrace |
| 14:11 | technomancy | ucb: yay, interactivity. |
| 14:11 | stompyj | checking out that new podcast that dnolen_ did, dude is a beast |
| 14:11 | ucb | technomancy: yayayayayaya indeed |
| 14:11 | technomancy | ucb: do you know if that's happening server-side or client-side? |
| 14:12 | ucb | technomancy: I haven't a clue. I'm just a user :) |
| 14:12 | mstang | stompyj: was that the interview or does he have something new? |
| 14:13 | stompyj | mstang: the interview at javascript jabber |
| 14:13 | mstang | stompyj: I am about 1/3 of the way through, he is a beast! |
| 14:15 | stompyj | the best part about the clojure community is the ability with which the stewards of different parts of the ecosystem can articulate why X thing is important |
| 14:15 | stompyj | feels like the early rails days |
| 14:18 | SegFaultAX | What would you call group-by where the keying function returns multiple groups for a given element? |
| 14:18 | SegFaultAX | group-many is the best I can do. |
| 14:19 | teslanick | 'categorize' ? |
| 14:21 | SegFaultAX | teslanick: I like it! Thanks. |
| 14:26 | amalloy | SegFaultAX: i'm curious what your implementation of that looks like. seems like there are a number of plausible approaches |
| 14:28 | SegFaultAX | amalloy: I can show you the sauce if you want. |
| 14:28 | SegFaultAX | amalloy: https://gist.github.com/SegFaultAX/3f2657c6c338691d812c (Python) |
| 14:29 | amalloy | ah. i just sketched it out in clojure, SegFaultAX: https://www.refheap.com/649f9d50c4f7df0bd835dd7ca |
| 14:33 | teslanick | til about fnil |
| 14:33 | nullptr | ,(doc fnil) |
| 14:33 | clojurebot | "([f x] [f x y] [f x y z]); Takes a function f, and returns a function that calls f, replacing a nil first argument to f with the supplied value x. Higher arity versions can replace arguments in the second and third positions (y, z). Note that the function f can take any number of arguments, not just the one(s) being nil-patched." |
| 14:34 | teslanick | So (fnil conj []) returns a version of conj that will use an empty vector if the first argument to it is nil. |
| 14:35 | Frozenlock | In compojure, do I need to specify a 'not-found' route everytime I use `context'? |
| 14:36 | amalloy | Frozenlock: i can't think why you would do so |
| 14:37 | Frozenlock | I ask because when I use (context "/some-url" ....), if a page doesn't exists under "/some-url/..." I just get a blank page. :-/ |
| 14:37 | amalloy | Frozenlock: you want a single not-found route after all of your routes, probably |
| 14:38 | Frozenlock | amalloy: Yes, that's how things are for now. A single not-found route at the end of my app-routes |
| 14:38 | amalloy | (routes (context "/foo" ...) (context "/bar" ...) not-found) |
| 14:38 | amalloy | i don't think context surreptitiously inserts a blank page. if you're getting one, you put it there |
| 14:39 | Frozenlock | hmm... |
| 14:40 | dbasch | Frozenlock: what does the response look like? A blank page could mean many things |
| 14:44 | Frozenlock | dbasch: http 200 |
| 14:44 | Glenjamin | anyone familiar with test.check who knows how i can run a (defspec) in isolation at the repl? |
| 14:45 | reiddraper | Glenjamin: run the test as a function: (test-ns/my-test) |
| 14:45 | Glenjamin | hah, d'oh |
| 14:45 | Glenjamin | thanks |
| 14:45 | reiddraper | np |
| 14:46 | Glenjamin | is there a neat way to feed a failure case back in to the body, without extracting to a function? |
| 14:46 | Glenjamin | my sequence is something like: check => fail, add-watch, run-once |
| 14:47 | reiddraper | Glenjamin: no way that i'm aware of, without extracting to a function |
| 14:48 | Glenjamin | ok, thanks |
| 14:50 | reiddraper | Glenjamin: i think you'll find that extracting it into a function is a good idea anyway |
| 14:51 | Glenjamin | mm, i started like that, but then folded them into the defspec as it was only 3 lines |
| 14:52 | Glenjamin | being able to do something like (check-case (:smallest result)) might be quite nice |
| 14:57 | Frozenlock | amalloy: You were right, I added a allow-cross-origin middleware and it was messing with the headers |
| 15:00 | roppongininja | Guys I'm really commited to JVM and I want to learn my first functional language - should I start with clojure or scala? |
| 15:02 | ystael | roppongininja: Learn enough of each to make an educated choice! |
| 15:02 | bbloom | roppongininja: yes. |
| 15:02 | bbloom | but you're in #clojure, so the answer should be clear |
| 15:02 | amalloy | roppongininja: you're asking here instead of in #scala. you know what you want in your heart of hearts |
| 15:03 | llasram | It might have been a loyalty test |
| 15:03 | bbloom | llasram: here we are only loyal to shit that works |
| 15:03 | technomancy | amalloy: he could be asking in both |
| 15:03 | dbasch | I agree that you should try both and decide for yourself |
| 15:03 | amalloy | technomancy: yeah, but i'm not in #scala so i think it probably doesn't exist |
| 15:05 | dbasch | having a mixed Scala / Java codebase is not fun, for example |
| 15:05 | technomancy | that said, the jvm seems like a weird thing to be committed to |
| 15:05 | technomancy | just kind of going forward assuming you'll never have requirements for low-memory or tight C integration |
| 15:06 | mstang | Scala seems a bit on the complicated side of things |
| 15:06 | mstang | I took a two day class ;-) |
| 15:06 | dbasch | technomancy: it depends on where you work. Some companies require that you give their devops a jar / war that they can toss into production, and they don’t care how it was created |
| 15:07 | technomancy | dbasch: sure, if you've decided to specialize solely in long-running server software |
| 15:07 | roppongininja | dbasch: I don't need to learn this for work (maybe for a future one) I just want to try functional programming by writing a simple bitcoin trading bot :) |
| 15:07 | roppongininja | dbasch: I dont care how long it takes its just for fun |
| 15:08 | technomancy | dbasch: it makes more sense for a company to be committed to a platform than for an individual, anyway |
| 15:08 | bbloom | roppongininja: if you just want to learn, and you've never done a lisp before, clojure will be a bigger and more rewarding learning experience |
| 15:08 | roppongininja | technomancy: I've never done any other programming than Java/c/python/js |
| 15:08 | roppongininja | and c# |
| 15:08 | technomancy | and loyalty to a company is pretty old-fashioned these days |
| 15:09 | roppongininja | so I've never done any functional programming |
| 15:09 | dbasch | roppongininja: in Scala you always have the temptation to code as if it were Java, you have to be more disciplined to stay functional |
| 15:09 | dbasch | Scala is an easier sell to organizations where most developers have a Java background for that reason |
| 15:10 | roppongininja | dbasch: I know that scala is better when looking for a job but I'm not looking for a new one |
| 15:10 | bbloom | dbasch: s/Scala // |
| 15:12 | dbasch | bbloom: ok, atrocious in a very specific way :P |
| 15:12 | bbloom | dbasch: that's for sure |
| 15:12 | dbasch | e.g. people transforming a collection by iterating over every item and copying the result of a function into a new collection |
| 15:13 | fowlslegs | What is the correct syntax for recur when I want to assign the value of one var to another. Say I have (loop [x 1 y 2] (if (= x 2) [x y] (let [u 4] (recur (inc x) (y u))))) |
| 15:13 | cbp` | why can't cljs get a repl to a browser-opened html file? |
| 15:13 | fowlslegs | Except the (y u) is incorrect syntax. What if I want 4 bound to y for the next loop? |
| 15:14 | amalloy | just...(recur (inc x) 4) |
| 15:14 | amalloy | you just put values there. no names |
| 15:14 | fowlslegs | purrrfect |
| 15:14 | bbloom | cbp: has to do with same domain policy |
| 15:14 | dbasch | roppongininja: a bitcoin trading bot in clojure would be a fun project |
| 15:14 | roppongininja | are there any beginners here? |
| 15:14 | amalloy | yes |
| 15:15 | roppongininja | I don't know anything about clojure but if someone's a total no-life like me we could team up and write a free open source btc trading bot:) |
| 15:16 | roppongininja | I guess that if you want to learn that's the fastest way - learning by doing :) |
| 15:16 | dbasch | roppongininja: I don’t know about #scala, but if you start something and share your code here you’ll get tons of good feedback |
| 15:19 | nullptr | roppongininja: you can get from a->b down either path, but i do think you'll have more fun with clojure |
| 15:21 | roppongininja | Should I use emacs for clojure? I've been a intellij idea user so far |
| 15:21 | nullptr | have you used emacs before? |
| 15:22 | nullptr | it's a nice clojure environment, but the learning curve is, well ... http://ergoemacs.org/emacs/i/emacs_learning_curves.png |
| 15:22 | roppongininja | nullptr: yes for a max of 24h total, so I know close to nothing about it, I've been using vim for a long time though |
| 15:22 | roppongininja | nullptr: I know that picture |
| 15:22 | bbloom | ~fireplace |
| 15:22 | clojurebot | Huh? |
| 15:23 | nullptr | https://github.com/tpope/vim-fireplace |
| 15:23 | bbloom | clojurebot: fireplace is github.com/tpope/vim-fireplace |
| 15:23 | clojurebot | 'Sea, mhuise. |
| 15:24 | dbasch | roppongininja: by now there are some decent choices besides emacs, including LightTable and Cursive (IntelliJ) |
| 15:24 | roppongininja | dbasch: and which one are you using |
| 15:24 | dbasch | roppongininja: I use Emacs personally |
| 15:25 | technomancy | roppongininja: don't learn emacs and clojure at the same time |
| 15:25 | zerokarmaleft | roppongininja: Cursive is quite capable |
| 15:25 | cbp | Once you go into the emacs rabbit hole you never come back |
| 15:25 | roppongininja | there's this thing called evil-mode |
| 15:25 | technomancy | emacs will be there waiting for you once you get decent at clojure |
| 15:25 | zerokarmaleft | evil-mode is terrible |
| 15:25 | bbloom | roppongininja: just use what you know |
| 15:26 | bbloom | and if you don't know anything else, just use light table, since it's so easy to get started |
| 15:26 | nullptr | i agree with bbloom, LT is a great low hassle startup env |
| 15:27 | nullptr | and as technomancy says, emacs will be there waiting for you ... probably even if you wait a couple of decades |
| 15:27 | cbp | you probably will only need lein repl for a good while anyway |
| 15:27 | roppongininja | Ok I will give LT a try then! |
| 15:28 | dbasch | roppongininja: btw, I’ve written some bits of bitcoin-related code in clojure, let me know when you have specific questions |
| 15:28 | kenrestivo | Raynes: would it be an abuse of irclj to use it as a gateway from irc to another chat system, which i think would require multiple connections from ircj (one for each user on the other system)? |
| 15:29 | Glenjamin | i've been fairly happy with the latest LT - it now seems to have most of the "proper editor" bits |
| 15:30 | roppongininja | dbasch: do you mind adding me on skype? |
| 15:30 | dbasch | roppongininja: I don’t use skype much, but you can mention me here or on Twitter (same handle) |
| 15:31 | mstang_ | LT isn't a great editor, but I like it's interactivity better than Emacs or Vim |
| 15:31 | roppongininja | mstang_: I've got sublime text 2 by the way is that any good |
| 15:32 | roppongininja | or shall I ask is it better than LT |
| 15:32 | mstang_ | roppongininja:I have heard that people like it, the nice thing about LT is that you can edit, CTRL-ENTER and see the result inline |
| 15:33 | mstang_ | Cursive is looking interesting, haven't tried it yet |
| 15:35 | mstang_ | roppongininja: I don't think sublime is as interactive from what I have heard, never used it |
| 15:35 | {blake} | LT's not bad. The inline has some use but limited (to me so far). |
| 15:35 | mstang_ | roppongininja: If I have some fancy editing, I open Vim or gedit depending on what kind of editing... |
| 15:36 | mstang_ | roppongininja: but then I go back to LT |
| 15:36 | SegFaultAX | amalloy: Reasonable implementation? |
| 15:36 | SegFaultAX | amalloy: I don't really know how much python you do. :D |
| 15:36 | SegFaultAX | But you get the idea, right? |
| 15:36 | mstang_ | roppongininja: btw, I keep the Emacs cheat sheet open on my desk ;-) |
| 15:38 | Glenjamin | the watch feature in LT is quite neat |
| 15:39 | nullptr | Glenjamin: is that like cider-tracing? |
| 15:39 | Glenjamin | highlight form, add watch, see values passing through on eval? |
| 15:44 | amalloy | SegFaultAX: i don't do any python. implementation seems fine, although the problem is pretty bland if you can just mutate things |
| 15:45 | amalloy | i wouldn't have created the variable `keys` at all: just write `for key in fn(e): ...` |
| 15:48 | amalloy | you can also use setdefault instead of get, to simulate fnil and remove some more nonsense |
| 15:48 | amalloy | ie, replace lines 8-10 with acc.setdefault(key, []).append(e) |
| 15:49 | Glenjamin | setdefault is a weird function |
| 15:51 | amalloy | what. is gist broken? when i click the Fork button on SegFaultAX's gist, i get a 422 Unprocessable Entity |
| 15:51 | dinduks | Hi folks. Can some please share some piece of code that shows how are operations on collections usually nested in Clojure? It's hard to find this with a search engine. |
| 15:52 | amalloy | "The change you wanted was rejected. Maybe you tried to change something you didn't have access to." |
| 15:52 | Glenjamin | amalloy: works for me :s |
| 15:52 | Glenjamin | dinduks: what do you mean by nested? |
| 15:52 | tbaldridge | dinduks: operations are nested? |
| 15:53 | dinduks | Glenjamin: like a map on a filter on another map, etc. |
| 15:53 | tbaldridge | (->> [1 2 3] (map inc) (filter pos?) (filter even?) (map dec)) |
| 15:53 | Bronsa | gist |
| 15:53 | Glenjamin | generally you just nest them, you can improve readability with intermediary variables using let, or via ->> |
| 15:53 | tbaldridge | , (->> [1 2 3] (map inc) (filter pos?) (filter even?) (map dec)) |
| 15:53 | clojurebot | (1 3) |
| 15:54 | dinduks | How is "->>" called, so I can search it? :) |
| 15:54 | Glenjamin | threading macro |
| 15:54 | dinduks | Cool thanks. |
| 15:55 | dinduks | I thought about using many `let` but then I wondered if it was a good idea to have 10 let that are simple temp variables |
| 15:55 | amalloy | i always call it the Arrow of Awesome |
| 15:55 | dbasch | dinduks: technically it’s thread-last, there’s also -> or thread-first http://clojuredocs.org/clojure_core/clojure.core/-%3E%3E |
| 15:56 | amalloy | dbasch: "technically" it's ->>. thread-last and thread-first are two colloquial names that some people use |
| 15:56 | dbasch | amalloy: I mean as opposed to threading macro |
| 15:57 | dbasch | no nitpicking, just trying to clear the confusion because dinduks would encounter -> when searching for threading macro |
| 15:57 | Glenjamin | some subjective combination of nesting, threading and let usually produces something readable |
| 15:57 | amalloy | but how sad would he be to find information on ->? not sad at all |
| 15:59 | dinduks | :) |
| 15:59 | dinduks | Thanks everyone. I think ->> with some line breaks if my (fn …) are long will do the trick. |
| 15:59 | amalloy | sounds about right, Glenjamin |
| 16:00 | llasram | + splitting into multiple functions |
| 16:00 | llasram | + our fanatical devotion to the Pope |
| 16:00 | ystael | llasram: but everyone expects the threading macro |
| 16:00 | amalloy | llasram: nobody must know our secret nickname for rich hickey |
| 16:01 | llasram | heh |
| 16:03 | stompyj | If theres any “The State” fans here: HEEYYYYY, ITS A DA POPAAAA |
| 16:25 | Glenjamin | i seem to have a complete mental block here, i'm wanting to return a reverse lazy sequence from a java.util.ArrayList - but i can't seem to think what to use |
| 16:25 | Glenjamin | i assumed that lazy-seq was the right thing, but that doesn't fit at all |
| 16:26 | Glenjamin | oh wait, i think i got it |
| 16:35 | haywood | Om question. I have a nested component structure, think table -> row -> cell. The cell needs a bit of 'global state but it feels wrong to pass that down in a cursor when the components above don't need it at all |
| 16:38 | seancorfield | haywood: perhaps a better Q for the #clojurescript channel? |
| 16:39 | haywood | seancorfield: will do! thanks |
| 16:40 | microamp | curious, how often do you guys use loop/recur? |
| 16:41 | Glenjamin | probably too often |
| 16:41 | technomancy | microamp: very rarely |
| 16:41 | AimHere | When I can't think of a way of using 'reduce' |
| 16:42 | Glenjamin | i think the only one i didn't factor away was reducing a huge collection into two big collections |
| 16:42 | microamp | thanks, just got back to learning clojure again, tempted to use loop/recur probably more often than i should've |
| 16:43 | technomancy | microamp: it's usually a sign either 0) you're a schemer or 1) you haven't fully internalized the seq API |
| 16:43 | technomancy | or both! |
| 16:43 | amalloy | Glenjamin: that sounds like a group-by,not a loop/recur |
| 16:44 | amalloy | or a reduce in the worst case |
| 16:44 | microamp | technomancy: hah, coming from python background, i guess it's more like 1 :) |
| 16:44 | Glenjamin | ~7 million records into two maps, one with ~1 mil the other with ~6 mil |
| 16:44 | clojurebot | excusez-moi |
| 16:44 | seancorfield | microamp: I have a handle of loop/recurs in tight code that manipulates text (it's horribly non-functional in style but it's fast!) but otherwise I hardly have any in about 20kloc |
| 16:44 | AimHere | I'm just wondering if a third option would be 2) or 10) |
| 16:44 | Glenjamin | even with reduce, i'd have to create something to hold the two intermediaries at each step |
| 16:45 | seancorfield | 15 of them total in just over 20kloc... see, you made me go count them! |
| 16:46 | Glenjamin | two in this file :s |
| 16:46 | seancorfield | a few of those are in go loops |
| 16:47 | amalloy | Glenjamin: huh? the two intermediaries are held in the map you're reducing over |
| 16:47 | amalloy | i'm curious to see this process of splitting up a collection into two that you think requires loop/recur |
| 16:47 | Glenjamin | i end up with two distinct maps |
| 16:48 | Glenjamin | although i do ultimately return a map |
| 16:48 | Glenjamin | hrm, let me time it |
| 16:48 | Glenjamin | https://www.refheap.com/85264 is my other example |
| 16:49 | Glenjamin | amalloy: this is the splitting one - https://www.refheap.com/85265 |
| 16:51 | amalloy | what is with all these transients? |
| 16:51 | Glenjamin | well a) it's a large collection and b) i'd just read up on transients when i started |
| 16:52 | amalloy | anyway, this is just a reduce over (result-set-seq rs) |
| 16:52 | Glenjamin | yes, but it's faster |
| 16:52 | Glenjamin | i did start with that |
| 16:53 | Glenjamin | i've changed a lot of other stuff since the last slow version, i should try the seq again though |
| 16:54 | amalloy | but, really, this isn't a terrible candidate for loop/recur. squeezing it into a reduce over a pair doesn't increase readability by much, and what you have isn't already a seq |
| 16:58 | dans | evening all - so i was thinking is there a name for a composition pattern as so: (defn comp-i-dont-know? [g h] (fn [inst val] (g inst (h val)))) I'm thinking of this as composing transformations over a value before it is passed for example to a java setter. |
| 17:01 | amalloy | doesn't ring any bells for me, dans |
| 17:05 | dans | hmm, thats cool was wondering whether I was just being thick amalloy - its pretty specific, I can't think of any general use cases for such a function - useful for setters as I said, as I tend to create lots of setters via composition etc when building up java interop layers. |
| 17:05 | amalloy | i don't really understand the comparison to setters |
| 17:06 | amalloy | is doto not suitable for this? doto and -> are often useful for interop |
| 17:06 | mercwithamouth | newb dev question. so i created a post route to collect data to be used in a function. i can see the post data in firebug...what would be a good way to see if it's actually touching my server code? I start the server from the repl... |
| 17:06 | dans | yes - but I like to have the power of the various map/data transformation options that are available if I generalise setters as functions |
| 17:08 | noonian | mercwithamouth: i usually write a simple ring middleware function that just prints the request and response to stdout |
| 17:08 | dans | so I use something like https://github.com/danstone/getteretta to create maps of getters setters I can then do some interesting things in my interop layers. |
| 17:10 | noonian | mercwithamouth: https://www.refheap.com/85266, then wrap your handler with that before passing it you run-jetty or w/e |
| 17:10 | mercwithamouth | noonian: hrmm... ehh hmm how can i about doing that when right now my posts are coming from client side only. i could see how that would be possible...i guess i should just add some persistence now |
| 17:10 | mercwithamouth | noonian: ok, taking a look |
| 17:11 | noonian | that will print out the data that the server receives in the request, and also what it will return to the client with the response |
| 17:11 | mercwithamouth | hmm even using the repl in light table? |
| 17:12 | noonian | yes, if you are running your server from within light table, it will print to the console so you may have to open light tables console in a tab (ctrl+space type console and the fuzzy search should find it) |
| 17:12 | mercwithamouth | ahh! gotcha! |
| 17:12 | mercwithamouth | ty! |
| 17:13 | noonian | np |
| 17:13 | Glenjamin | you can also do it with the "watch" feature |
| 17:14 | mercwithamouth | Glenjamin: watch? do tell... |
| 17:14 | Glenjamin | instead of the print statements, select the form and "add watch" - it's alt+w on my LT |
| 17:15 | Glenjamin | then the value will be displayed inline when you make a request |
| 17:16 | mercwithamouth | nice! ok i'll try that out...be back in a few |
| 17:16 | whodidthis | whoa, i also had no idea |
| 17:38 | mercwithamouth | hmm one issue... after (start-server) in a repl...when I try to call anything on the next line it just starts opening up new tabs like crazy going to my server |
| 17:38 | mercwithamouth | is this avoidable? |
| 17:42 | mercwithamouth | ahh oops...dur |
| 17:43 | mercwithamouth | *cuts live off* -_- |
| 17:44 | PigDude | if you ever wanted to know how clojure prints dates, you didn't :P |
| 17:45 | PigDude | but long story short it's simpler to parse the string out of `pr-str' than to try to do this any other way, as far as i can tell |
| 17:46 | amalloy | PigDude: simpledateformat in java is a hassle to deal with, but flexible enough to do whatever you need |
| 17:47 | amalloy | &(.format (java.text.SimpleDateFormat. "kk:mm:ss") (java.util.Date.)) |
| 17:47 | lazybot | ⇒ "14:44:40" |
| 17:49 | mordocai | amalloy: If there isn't a wrapper/native way to do that, there should be... |
| 17:49 | justin_smith | PigDude: clj-time helps a lot |
| 17:50 | amalloy | mordocai: that's silly. if things in java work, there's no need for a wrapper in them in clojure.core |
| 17:50 | justin_smith | the native java time code has issues, joda-time (which clj-time wraps) improves |
| 17:50 | nullptr | (inc clj-time) |
| 17:50 | lazybot | ⇒ 1 |
| 17:50 | amalloy | as justin_smith says, the native java time stuff *is* pretty garbage, but wrapping garbage just gets you wrapped garbage |
| 17:51 | mordocai | amalloy: I don't know, right now I'm very new to clojure (about 1/7th through "The Joy of Clojure" as my intro) but I am all for abstracting away java as much as possible. My attitude may change. |
| 17:52 | noonian | wrapped gargabe doesn't stink as much :P having said that, clj-time is the way to go |
| 17:53 | justin_smith | mordocai: given that by using interop you can already be more concise than native java would be, and lose very little functionality, you'll be happier just learning how to do interop and being comfortable with it. It's good to fight library bloat where you can anyway. |
| 17:57 | PigDude | justin_smith: yea, but this is for the glue between clj-time :_) |
| 18:00 | justin_smith | PigDude: ahh, I had remembered clj-time having its own formatters |
| 18:02 | noonian | it does iirc |
| 18:22 | martinklepsch | with an ns statement like this I'm getting "No value supplied for key: true": https://www.refheap.com/85271 |
| 18:22 | martinklepsch | if I remove the lighttable.nrepl part it just works fine |
| 18:22 | amalloy | martinklepsch: (:gen-class :main true) doesn't make any sense to me. don't you just want (:gen-class)? |
| 18:23 | martinklepsch | amalloy, hm good question. I probably just copied that from somewhere else ô.O |
| 18:24 | martinklepsch | funnily that doesn't change anything |
| 18:25 | martinklepsch | ah, wait a sec |
| 18:26 | amalloy | oh, your require is wrong |
| 18:26 | martinklepsch | omg, that was stupid |
| 18:26 | martinklepsch | :D |
| 18:26 | martinklepsch | should probably go to bed |
| 18:29 | Glenjamin | this may be a dumb question - but would RandomAccess & List be considered sufficient to implement clojure.lang.Reversible? |
| 18:30 | Glenjamin | i noticed that seq works on ArrayList, but rseq does not |
| 18:32 | amalloy | Glenjamin: yes, but that's an uncommon enough use case that it's not really exciting to put into core |
| 18:33 | Glenjamin | would it be considered better practice for me to extend the protocol in my application, or just implement arraylist-rseq? |
| 18:33 | amalloy | and like, you can write it yourself: (defn list-rseq [xs] (let [n (count xs)] (for [i (range n)] (nth xs (- n i 1))))) |
| 18:33 | Glenjamin | in fact, this is a library, so it would have to be the latter |
| 18:33 | amalloy | it's not a protocol, so you can't do that; but if you could you shouldn't anyway |
| 18:34 | Glenjamin | i've done a lazy version with recursive and lazy-seq, but basically the same thing |
| 18:35 | Glenjamin | unless for is lazy? that'd be far neater |
| 18:35 | amalloy | of course for is lazy |
| 18:35 | Glenjamin | whoops |
| 18:35 | Glenjamin | thats so much neater than what i had |
| 18:36 | Glenjamin | doall is the non-lazy for, so ofc for is lazy |
| 18:36 | amalloy | s/doall/doseq |
| 18:36 | Glenjamin | erm |
| 18:36 | Glenjamin | yes |
| 18:36 | Glenjamin | so obvious now |
| 18:36 | amalloy | you could also use List/listIterator, and ListIterator/prev to walk backwards over the list |
| 18:36 | amalloy | insetad of using nth |
| 18:37 | Glenjamin | i had .get, no idea what the differences are really :) |
| 18:37 | amalloy | eh, nth goes through some dispatching logic in c.l.RT and then calls .get |
| 18:38 | Glenjamin | i suppose the iterator enforces the blow-up-if-mutated constraint |
| 18:39 | amalloy | &(let [a (java.util.ArrayList. '(a b c d e)), iter (.listIterator a (count a))] ((fn step [] (lazy-seq (when (.hasPrevious iter) (cons (.previous iter) (step))))))) |
| 18:39 | lazybot | ⇒ (e d c b a) |
| 18:40 | kil3n | hey |
| 18:41 | kil3n | anyone using emacs-live vanilla setup? |
| 18:41 | Glenjamin | oh, now we've swapped |
| 18:42 | justin_smith | kil3n: there are many emacs users here, we may be able to answer a question even if we aren't using the emacs-live setup |
| 18:42 | Glenjamin | (defn arraylist-rseq [al] (let [n (count al) it (.listIterator al n)] (for [i (range n)] (.previous it)))) |
| 18:42 | Glenjamin | &((fn [al] (let [n (count al) it (.listIterator al n)] (for [i (range n)] (.previous it)))) java.util.ArrayList. '(a b c d e)) |
| 18:42 | lazybot | java.lang.ClassNotFoundException: java.util.ArrayList. |
| 18:43 | kil3n | justin_smith: thanks, it’s just that I can’t seem to make changing the font size stick, it auto-resets after a second on startup (when “zoning…” is done or something) |
| 18:43 | kil3n | setting the new font size in live-packs |
| 18:43 | Glenjamin | &((fn [al] (let [n (count al) it (.listIterator al n)] (for [i (range n)] (.previous it)))) (java.util.ArrayList. '(a b c d e))) |
| 18:43 | lazybot | ⇒ (e d c b a) |
| 18:44 | justin_smith | kil3n: what method are you using to set the font? is it actually saving it for future sessions via customize? |
| 18:44 | amalloy | urgh. you shouldn't really use the side-effecting .previous inside a for-loop |
| 18:44 | amalloy | i can't think of any way it could go wrong here, but it makes me queasy |
| 18:45 | kil3n | justin_smith: in `init.el` in my live-packs folder |
| 18:45 | kil3n | `(set-face-attribute 'default nil :font "Menlo 15")` |
| 18:45 | justin_smith | kil3n: try m-x customize-group basic-faces and check out what is under the Default face: entry |
| 18:45 | Glenjamin | is it particularly different from a side-effecting lazy-seq? |
| 18:45 | kil3n | justin_smith: checking… |
| 18:46 | kil3n | justin_smith: |
| 18:46 | amalloy | well, Glenjamin, chunked sequences make it a bit different |
| 18:46 | kil3n | justin_smith: state: STANDARD, “inherit”: INS DEL Face: (sample) |
| 18:47 | amalloy | eg, you could imagine writing (take n (for [i (range)] (.previous iter))) instead |
| 18:47 | Glenjamin | ah, i see - lazy-seq is unchunked? |
| 18:47 | kil3n | justin_smith: sorry that was button face |
| 18:47 | kil3n | justin_smith: Height is 120 |
| 18:47 | amalloy | which looks okay, but will probably call .previous too many times because you're not explicitly guarding it with .hasPrevious |
| 18:47 | kil3n | justin_smith: font is menlo, correct |
| 18:48 | kil3n | justin_smith: I’ve tried changing the :height before in the init.el file as well, like this “(set-face-attribute 'default nil :height 180)” |
| 18:48 | PigDude | OK! How do I compare sets? |
| 18:48 | kil3n | justin_smith: but still resets after a sec |
| 18:48 | amalloy | Glenjamin: there are only a couple things in clojure.core that produce chunked sequences. range, seq on a vector, seq on a map...maybe something else i can't think of at the moment |
| 18:48 | justin_smith | kil3n: odd - maybe try opening ielm and checking the current face attributes? |
| 18:48 | PigDude | justin_smith: yea, this is for part of the program before i can guarantee clj-time (a cljs part) |
| 18:48 | Glenjamin | interesting, i wouldn't have expected range to be chunked |
| 18:48 | justin_smith | ahh |
| 18:48 | amalloy | some things *preserve* chunked sequences, like: for, map, filter, remove |
| 18:48 | technomancy | kil3n: starter kits like emacs live often do weird things that make them really difficult to debug |
| 18:48 | PigDude | justin_smith: for pulling (pr-str) formatted date when reading json, as value-fn |
| 18:48 | kil3n | justin_smith: tried changing the height directly, but how do I actually save this? |
| 18:49 | technomancy | it's difficult to recommend their use for new users |
| 18:49 | kil3n | technomancy: yeah :) |
| 18:49 | PigDude | ,(compare #{1} #{1 2}) |
| 18:49 | clojurebot | #<ClassCastException java.lang.ClassCastException: clojure.lang.PersistentHashSet cannot be cast to java.lang.Comparable> |
| 18:49 | kil3n | technomancy: honored to speak to you btw, love leiningen |
| 18:49 | PigDude | ,(compare #{} #{}) |
| 18:49 | clojurebot | 0 |
| 18:49 | technomancy | kil3n: glad you like it =) |
| 18:50 | kil3n | please recommend another start if you have one, semi-n00b in emacs, used to be die-hard vim user before discovering the epicness of emacs when starting doing lots of clojure |
| 18:50 | PigDude | ,(superset? #{1 2} #{1}) |
| 18:50 | clojurebot | #<CompilerException java.lang.RuntimeException: Unable to resolve symbol: superset? in this context, compiling:(NO_SOURCE_PATH:0:0)> |
| 18:50 | PigDude | ah it's not in core |
| 18:50 | justin_smith | kil3n: not only is emacs epic, it has lots of great fan fiction available too (melpa...) |
| 18:51 | amalloy | that's pretty weird, PigDude. why does it work for two empty collections? |
| 18:51 | justin_smith | ,(do (require 'clojure.set) (clojure.set/superset? #{1 2} #{1})) |
| 18:51 | clojurebot | true |
| 18:51 | kil3n | justin_smith: fan fiction..? metaphor? |
| 18:51 | amalloy | &(identical? #{} #{}) |
| 18:51 | lazybot | ⇒ true |
| 18:52 | amalloy | i guess that's why. i didn't realize those read to indentical objects |
| 18:52 | justin_smith | kil3n: expanding on the "epic" metaphor |
| 18:52 | technomancy | kil3n: it's best to just pick individual packages that do things you like instead of finding one huge package that does everything |
| 18:52 | amalloy | &(identical? [] []) |
| 18:52 | lazybot | ⇒ true |
| 18:52 | amalloy | &(identical? {} {}) |
| 18:52 | lazybot | ⇒ true |
| 18:52 | amalloy | well, today i learned something |
| 18:52 | kil3n | technomancy: yeah but that seems like something to do when you actually know what you need, after you’ve used the stuff productively for a while… ;) |
| 18:52 | Bronsa | amalloy: they get compiled to PHS/EMPTY PHM/EMPTY PV/EMPTY |
| 18:53 | technomancy | kil3n: but if you feel the need to start somewhere, I can at least promise that https://github.com/technomancy/better-defaults won't mislead you in weird/confusing ways |
| 18:53 | kil3n | hehe thx |
| 18:53 | amalloy | Bronsa: yeah, i gathered as much: there's not really any other explanation |
| 18:53 | Glenjamin | PigDude: i dunno about how well it works with cljs, but http://momentjs.com is my go-to for JS date/time handling |
| 18:53 | Bronsa | amalloy: yeah, that should also be true for (). see Compiler$EmptyExpr or however it's called |
| 18:53 | amalloy | technomancy: isn't that the same thing people with starter kits say? |
| 18:54 | coventry | ,(identical? (pop [1]) []) |
| 18:54 | clojurebot | false |
| 18:54 | technomancy | amalloy: the difference is I'm not (anymore) filled with lies |
| 18:54 | PigDude | amalloy: interesting |
| 18:55 | justin_smith | ,(identical? (empty #{}) (empty #{})) |
| 18:55 | clojurebot | false |
| 18:55 | PigDude | Glenjamin: in this case i have some common code handling dates in cljs and clj |
| 18:55 | PigDude | Glenjamin: so am going to use common JS/Java Date API as much as possible but probably end up shipping the object to clj-time immediately in clj and to date.js (or your moment.js) in cljs |
| 18:56 | Glenjamin | ah, that's likely to be tricky - i think java.util.Date and js Date are pretty similar - the latter being modelled on the former |
| 18:56 | Bronsa | justin_smith: looks like empty preserves meta |
| 18:56 | PigDude | Glenjamin: yea, in the end i just need to get consistent dates that can be compared in the host environment |
| 18:56 | PigDude | Glenjamin: which isn't so bad. the fanciest arithmetic is adding a minute to a date |
| 18:56 | justin_smith | PigDude: what about just using .getTime? |
| 18:57 | justin_smith | ,(.getTime (java.util.Date.)) |
| 18:57 | clojurebot | 1399589548663 |
| 18:57 | justin_smith | it's trivial to parse at least |
| 18:57 | PigDude | justin_smith: my designs originally all used unix timestamps, yes |
| 18:57 | PigDude | justin_smith: however that's a last resort :) |
| 18:57 | justin_smith | why last resort? do you need to carry something like tz info too? |
| 18:58 | PigDude | nope, and w/ timestamps comparison and basic arithmetic are pretty simple ... now i'm thinking if i should go back to that design. i wrote a lot of code for it .. |
| 18:59 | dbasch | ,(System/currentTimeMillis) |
| 18:59 | clojurebot | 1399589681249 |
| 18:59 | justin_smith | it just seems that serialization / parsing is simpler with a timestamp number, and there are fewer weird things to go wrong (not to say there are none...) |
| 18:59 | PigDude | justin_smith: either way i want library users to be able to provide date objects, so i can't justuse timestamps. originally the library required calling w/ timestamps but i think this is unfriendly |
| 19:00 | justin_smith | then your wrapper layer is the getTime method of the Date object :) |
| 19:00 | PigDude | yea .. ok, thanks for talking w/ me about this, it's easy to doubt myself :P |
| 19:01 | PigDude | maybe better to go w/ timestamp |
| 19:01 | justin_smith | this is not flawless - sometimes a time has to be specific to a timezone, so then you need that metadata |
| 19:01 | justin_smith | but mostly it is the path of least complexity I think |
| 19:02 | Glenjamin | amalloy: cheers for the tips - am I ok to use your last sample pretty-much verbatim? |
| 19:02 | justin_smith | dbasch: nice, for some reason I missed that one :) |
| 19:03 | amalloy | it should work, yeah. although i'd really just use the version with for/range/nth |
| 19:03 | PigDude | justin_smith: yea, and lets me filter w/ (partial > t) rather than #((complement neg?) (compare t %)) |
| 19:03 | PigDude | justin_smith: so i'll tak that :) |
| 19:03 | PigDude | (don't expect those to be identical coimparisons, point being comparing Dates is harder) |
| 19:03 | Glenjamin | oh right, i forgot to try that one |
| 19:03 | amalloy | well, i guess the version with a ListIterator works even for non-RandomAccess lists like a LinkedList |
| 19:04 | Glenjamin | in this case its a concrete ArrayList, but that version is much neater anyway |
| 19:08 | martinklepsch | if my uberjar saves files to certain directories (like resources/ in dev) etc, how would I intergrate that into the deployment? |
| 19:08 | martinklepsch | (I guess resources wasn't really the right place for this in the first place) |
| 19:09 | justin_smith | martinklepsch: io/resource finds resources in the classpath |
| 19:09 | justin_smith | martinklepsch: or are you concerned about data stored to the fs at runtime? |
| 19:09 | martinklepsch | the latter |
| 19:10 | justin_smith | you could modify your code to take a path as an env var or config |
| 19:10 | justin_smith | or use a CDN |
| 19:18 | swarthy | anyone every experience clojure.java.shell/sh causing segfault when trying to run a ruby script? |
| 19:18 | swarthy | ever* |
| 19:19 | justin_smith | causing the jvm to segfault? or just the shell? |
| 19:19 | noonian | i've experienced segfaults when trying to run ruby scripts myself :P |
| 19:21 | noonian | if you have ruby configured using rvm or rbenv it might not behave the same way from clojure.java.shell because afaik those tools monkey with your bash environment and it may be different from the jvm |
| 19:25 | swarthy | noonian: that is likely what is happening then |
| 19:25 | swarthy | justin_smith: causing ruby to segfault |
| 19:25 | swarthy | noonian: is there anything I might try to force an env/user? anything that worked for you? |
| 19:25 | justin_smith | with ProcessBuilder you can construct the specific env you want to pass to the child process |
| 19:26 | noonian | i haven't tried this with clojure.java.shell, but i had a similar problem in the past calling ruby from a pallet script and i had to first source a script for rvm that setup some variables for the correct version |
| 19:27 | noonian | i'm not sure where those scripts lived though |
| 19:28 | noonian | https://rvm.io/integration/cron#environment |
| 19:29 | noonian | so in bash before running the ruby script you do something like: source /usr/local/rvm/environments/ruby-1.9.2-p290 |
| 19:29 | swarthy | so would it be possible to use (sh <source env> <call script>) ? |
| 19:29 | swarthy | i suppose I can try |
| 19:30 | justin_smith | with a ; in between, should work |
| 19:30 | swarthy | justin_smith: will do |
| 19:30 | swarthy | I smell a blog post. |
| 19:31 | amalloy | justin_smith: i don't think you can just put a ; in there, can you? sh doesn't actually call your shell, it invokes a process. you'll need (sh "bash" "-c" "source env; call script") or something |
| 19:32 | justin_smith | oh, ok - I thought by the name sh that it would be invoking a shell - in that case you wouldn't be able to use source either |
| 19:33 | justin_smith | yeah, clojure.java.shell/sh just spawns the program, so you would need to call /bin/sh explicitly (or bash if you really feel the need) |
| 19:34 | noonian | my bash-fu isn't where it should be without even calling out from java |
| 19:34 | justin_smith | (verified via (clojure.java.shell/sh "pstree")) |
| 19:35 | justin_smith | noonian: (clojure.java.shell/sh "sh" "-c" "source <file>; script") |
| 19:35 | noonian | justin_smith: nice |
| 19:36 | justin_smith | the whole command can be in one string arg to sh, after the "-c" |
| 19:37 | justin_smith | https://www.refheap.com/85278 <- example |
| 19:38 | noonian | later folks |
| 19:40 | swarthy | justin_smith: thanks for this, I'm working on it now |
| 19:40 | swarthy | so far no luck |
| 19:45 | justin_smith | how is the ruby in question installed? |
| 19:45 | justin_smith | perhaps it needs libs that are in /usr/local/lib/ instead of /usr/lib/ for example |
| 20:05 | TimMc | Given a var, is there an *easy* way to tell whether it could accept a given arglist? |
| 20:05 | TimMc | I'd rather not parse the arglists myself... |
| 20:06 | technomancy | TimMc: (some #{'&} (apply concat (:arglists (meta #'myvar)))) is a thing |
| 20:06 | technomancy | oh, a given arglist |
| 20:06 | technomancy | that's harder |
| 20:06 | technomancy | we do basically that in leiningen though |
| 20:07 | TimMc | For detecting bad CLI args? |
| 20:07 | technomancy | it ain't purty |
| 20:07 | TimMc | because that's exactly what I'm up to right now. |
| 20:07 | technomancy | https://github.com/technomancy/leiningen/blob/master/leiningen-core/src/leiningen/core/main.clj#L226 |
| 20:08 | TimMc | ,((fn [& &] &) 1 2 3) |
| 20:08 | clojurebot | #<CompilerException java.lang.RuntimeException: Invalid parameter list, compiling:(NO_SOURCE_PATH:0:0)> |
| 20:08 | TimMc | Just checking. :-P |
| 20:09 | technomancy | http://p.hagelb.org/smart.gif |
| 20:11 | amalloy | is & the only symbol that backquote treats specially that isn't a special form? |
| 20:12 | amalloy | that is, look at ##`(foo, def, &, let*, bar) |
| 20:12 | lazybot | java.lang.SecurityException: You tripped the alarm! def is bad! |
| 20:12 | amalloy | die in a fire, bro |
| 20:12 | amalloy | ,`(foo, def, &, let*, bar) |
| 20:12 | clojurebot | (sandbox/foo def & let* sandbox/bar) |
| 20:13 | TimMc | hah |
| 20:13 | TimMc | technomancy: imma steal that, k? |
| 20:13 | TimMc | and relicense it under the WTFPL |
| 20:13 | technomancy | ~guards |
| 20:13 | clojurebot | SEIZE HIM! |
| 20:15 | TimMc | Seriously though, I might copy that into org.timmc/handy. |
| 20:16 | TimMc | I just realized I don't actually know how to do attribution in such a case other than adding a comment about the source... |
| 20:16 | technomancy | as long as it's EPL you're fine |
| 20:59 | zeroem | ,(get-in {} []) |
| 20:59 | clojurebot | {} |
| 20:59 | zeroem | ,(update-in {} [] identity) |
| 20:59 | clojurebot | {nil nil} |
| 21:00 | zeroem | is that inconsistency expected? |
| 21:06 | amalloy | zeroem: it's not totally clear what it would mean to update-in with an empty keyseq. {nil nil} is a stupid result, but nothing else is super-appealing |
| 21:07 | amalloy | do you want (update-in {} [] (constantly 5)) to return 5? then update-in doesn't even always return a map! |
| 21:07 | zeroem | amalloy: well, get-in with an empty keyseq returns the map itself, it would make sense if update-in provided the map itself to the fn |
| 21:08 | zeroem | if you println instead of identity, it's just given nil |
| 21:08 | amalloy | that's "reasonable", but as i said it leads to some unpleasant consequences |
| 21:09 | hyPiRion | I think it would be more sane to just throw if it's an empty keyseq, but perhaps that's just me. |
| 21:10 | coventry | ,`~'` ; <- Is there any way to get a backtick inside a backtick? |
| 21:10 | clojurebot | #<RuntimeException java.lang.RuntimeException: EOF while reading> |
| 21:11 | amalloy | hyPiRion: that'd be my preference too |
| 21:11 | amalloy | coventry: no, it doesn't really make sense to do so given that backquote is read-time |
| 21:11 | coventry | Right. |
| 21:15 | lemonodor | is there a mocking library that I can use with clojure.test? |
| 21:15 | danlamanna | any immediate thoughts on mist/peer/freepastry? |
| 21:36 | justin_smith | newb jvm question: is onEnable a standard java method, or a convention of some plugin system? |
| 21:36 | jeremyheiler | in what context? |
| 21:37 | justin_smith | as a method on a class, in examples I see it contains initialization code |
| 21:37 | justin_smith | which I would usually assume goes in the constructor |
| 21:37 | justin_smith | googling is not giving me much |
| 21:38 | jeremyheiler | onEnable is surely a valid java method name. otherwise i don't understand your question. |
| 21:39 | justin_smith | I just wondered if it was a convention of some plugin system or framework, or something that the jvm would call |
| 21:39 | jeremyheiler | i mean, wht class are you talking about? |
| 21:39 | justin_smith | like I said, a newb question |
| 21:39 | jeremyheiler | where do you see it? |
| 21:40 | justin_smith | it's something I saw in a random paste of java code, and I got curious |
| 21:40 | justin_smith | sorry, I guess it's a stupid question |
| 21:40 | jeremyheiler | oh, ok. it doesn't ring a bel for me. |
| 21:41 | jeremyheiler | not a stupid question. i get it. seeing code out of context in an unfamiliar language begs lots of questions. |
| 21:42 | cbp | standard java method as in a method of Object? |
| 21:42 | cbp | then nope |
| 21:58 | justin_smith | PigDude: btw, it looks like there is a "Calendar" class for doing math on date / time. No idea if it is worth using though |
| 22:00 | justin_smith | ,(doto (java.util.Calendar/getInstance) (.add java.util.Calendar/HOUR_OF_DAY 10)) |
| 22:00 | clojurebot | #inst "2014-05-09T11:56:01.005+00:00" |
| 22:00 | zeroem | amalloy_: yeah I definitely would have preferred an exception rather than blowing hours on assumed functionality :F |
| 22:11 | justin_smith | amalloy_: I remember a little while back we were talking about setting up default java versions on debian. I just upgraded to jdk 1.8 and instead of messing with update-alternatives it sufficed to rm /etc/alternatives/java and replace it with a symlink to the jdk1.8 bin/java file |
| 22:11 | justin_smith | oh, and this worked |
| 22:17 | AWizzArd | dnolen_: In core.match, can I express: match x if it is (:or 1 2 3) or if it is `:guard even?`? If it is one bind its actual value to `n` so that I can `n` in the result. |
| 22:19 | AWizzArd | (if (or (= x 1) (= x 2) (= x 3) (even? x)) (let [n x] ...then...) else) |
| 22:39 | philc | from a repl, is it possible to run just a single (testing ...) context within a deftest? |
| 22:45 | servo | anyone know if theres a ruby fressian library? |