2013-01-21
| 00:05 | TimMc | Anyone want to help me redesign my high-level circuit simulator? (Sequential circuit, functions as combinatorial logic blocks, registers.) I have a working version, but it's a little limited in design and I think it could be nicer. https://github.com/timmc/feedback |
| 00:06 | tomoj | kind of something like this https://www.refheap.com/paste/9bd8650fb60801977f3eec825 |
| 00:06 | tomoj | needs to support conj though, hmm |
| 00:11 | muhoo | whoahbot: http://refheap.com please |
| 00:11 | muhoo | whoahbot: wait, no i meant WuHoUnited |
| 00:12 | muhoo | TimMc: industrial-sounding at first, then very circuit-bendy |
| 00:14 | TimMc | tomoj: What does it mean for an infinite sequence to be reversible? |
| 00:14 | muhoo | reversible infinity... start at the end and work backwards... um, wait... |
| 00:15 | TimMc | I can't think of a meaningful invariant that is defined on infinite seqs. |
| 00:15 | tomoj | hmm |
| 00:15 | tomoj | (= cycle (rseq (rseq cycle))) obviously |
| 00:16 | tomoj | oh, my impl has (= (first cycle) (first (rseq cycle))) |
| 00:16 | tomoj | which does seem weird |
| 00:18 | TimMc | Even then, I still don't think Reversible is appropriate. |
| 00:21 | TimMc | tomoj: Anyway, what's the use-case? |
| 00:22 | tomoj | ring buffer |
| 00:24 | tomoj | real use case is reusing dom nodes for a list |
| 00:33 | tomoj | I guess it's like a deque |
| 00:34 | tomoj | to move right, you pop-left and conj-right, to move left, you pop-right and conj-left |
| 00:36 | TimMc | tomoj: So you really want a completely filled, fixed-size ring that you can navigate left and right in? |
| 00:37 | TimMc | (first (left 3 ring)) |
| 00:39 | tomoj | I dunno, that's what I thought I wanted |
| 00:39 | TimMc | (->> ring (left 3) (set "hi!")) |
| 00:40 | TimMc | Reversible would make sense if you made the seq finite. |
| 00:40 | tomoj | now that I think about it more the real use case seems more complicated, so maybe it's moot |
| 00:42 | tomoj | how about: (= (reverse (drop-last coll)) (rest (reverse coll))) |
| 00:42 | warz | went ahead and reformatted to ubuntu, heh. |
| 00:45 | tomoj | .. uh, where drop-last is the identity on cycles |
| 00:46 | tomoj | well that's a semantic equality anyway, obviously not going to call reverse on a cycle |
| 00:46 | TimMc | (defn reversible? [coll] (if (empty? coll) (empty? (rseq coll)) (and (= (first coll) (last (rseq coll))) (reversible (rest coll))))) |
| 00:47 | TimMc | *reversible? |
| 00:47 | clerksy | So, If I am attempting to use the case macro, but the test constants are static fields from a java class, what would be the best way to handle that? |
| 00:47 | TimMc | or (= (nth coll x) (nth (rseq coll) (- (count coll) x 1))) |
| 00:48 | tomoj | are there things which fail those that pass my test? |
| 00:48 | clerksy | Ohh, I should be using (cond), huh? |
| 00:48 | TimMc | clerksy: Yeah, I don't know if case can handle Java static fields as compile-time literals. |
| 00:49 | TimMc | &(let [x Long/MAX_VALUE] (case x Long/MAX_VALUE :can :can't)) |
| 00:50 | lazybot | ⇒ :can't |
| 00:50 | TimMc | tomoj: reverse will fail on a cycle |
| 00:51 | tomoj | well, yeah |
| 00:51 | tomoj | I mean the semantics of reverse |
| 00:51 | TimMc | (oh, you said that) |
| 00:51 | tomoj | semantic `(reverse (drop-last cycle))` would be implemented by (rseq cycle) |
| 00:52 | tomoj | but anyway your functions assume finitude |
| 00:52 | TimMc | It's true. |
| 00:52 | tomoj | uh, finiteness |
| 00:53 | TimMc | finity? |
| 00:53 | clojurebot | is too infinity +1! |
| 00:53 | TimMc | ... |
| 00:54 | muhoo | so says.... godel? or was it cantor? |
| 00:54 | TimMc | tomoj: You can't ask for last on an infinite sequence, so you can't ask for first on the reverse of one. |
| 00:55 | muhoo | cantor http://en.wikipedia.org/wiki/Transfinite_number |
| 00:55 | tomoj | hmm, yes, these aren't sequences |
| 00:55 | TimMc | Given a general rseq, (defn last [x] (first (rseq x))) |
| 00:56 | tomoj | they have a rest and an unrest |
| 00:56 | TimMc | unrest :-P |
| 00:57 | TimMc | Is Cycle going to implement Counted? |
| 00:57 | tomoj | heh |
| 00:58 | TimMc | (counted? cyc) ;;= true / (count (seq cyc)) ;; infinite... |
| 00:58 | tomoj | well it has to be an int |
| 00:59 | tomoj | so no |
| 01:01 | tomoj | if they have a first, rest, and unrest, then they have a first and rest, so the can be ISeq. Reversible does seem possibly strange |
| 01:05 | n_b | How do you seq a BufferedReader by char rather than line? |
| 01:05 | n_b | Do I have to go down to using the java.io stuff? |
| 01:08 | TimMc | n_b: How are you currently getting a seq from a BufferedReader? |
| 01:08 | n_b | line-seq, but given my input it's not very convenient |
| 01:10 | TimMc | (defn char-seq [br] (let [c (read br)] (when-not (= c -1) (cons c (lazy-seq (char-seq br)))))) |
| 01:10 | TimMc | Should work? |
| 01:11 | TimMc | Oh, change that to (cons (char c) ...) |
| 01:11 | TimMc | Cribbed from the line-seq implementation. |
| 01:12 | tomoj | (take-while pos? (repeatedly #(.read br))) ? |
| 01:12 | TimMc | ooh |
| 01:12 | n_b | ooh |
| 01:13 | TimMc | Replace pos? with (complement neg?), though. |
| 01:13 | TimMc | Otherwise you'll start dropping NULs. |
| 01:13 | tomoj | oh yeah |
| 01:13 | tomoj | #(not= % -1) is probably good |
| 01:14 | yunfan | hi, can lein repl hook those use fail error, and install that library ? |
| 01:16 | TimMc | &(let [br (java.io.StringReader. "foo")] (->> (repeatedly #(.read br)) (take-while #(not= % -1)) (map char))) |
| 01:16 | lazybot | ⇒ (\f \o \o) |
| 01:17 | TimMc | yunfan: That would be an interesting modification. You'd need pomegranate (or similar) to add stuff to the classpath, and some other hook with a database of namespaces -> Maven coordinates... |
| 01:19 | TimMc | I'm not sure how you'd go about detecting #'use failures, though. |
| 01:19 | yunfan | TimMc: because i am reading someone's handbook on clojure, which the code sample use many library that i dont have |
| 01:21 | TimMc | (Heading to bed.) |
| 01:22 | n_b | TimMc: Thanks for the hel |
| 01:22 | n_b | (conj p *1) |
| 01:23 | n_b | same to you tomoj |
| 01:37 | johnmn3_ | trying to convert a piece of java here: while(true){if((line=br.readLine())==null)continue; post(line);} |
| 01:37 | johnmn3_ | I don't think I can do it with a clojure while |
| 01:37 | tagrudev | morning |
| 01:37 | johnmn3_ | can I just take-while on a br? |
| 01:38 | johnmn3_ | morning tagrudev |
| 01:38 | johnmn3_ | or is there a best highlevel function to consume the buffered reader? |
| 01:40 | tomoj | should `continue` be `break`? |
| 01:41 | johnmn3_ | tomoj... that's what I'm seeing... continue.. this while happens to be within an inner class which is also running a while(while) true... not sure if that's why a continue is used |
| 01:41 | johnmn3_ | I'm not familiar with it. |
| 01:42 | johnmn3_ | sorry, it is an inner class which calls another inner class, both of which have while(true) |
| 01:42 | johnmn3_ | and this second, sub while(true) has the continue |
| 01:42 | johnmn3_ | nakkaya mentions using a line-seq on a buffered reader |
| 02:03 | TheBusby | johnmn3_: isn't that filter? |
| 02:05 | johnmn3_ | I suppose filtering on nil would consume the sequence for me. |
| 02:09 | TheBusby | (->> br line-seq (filter identity)) |
| 02:14 | johnmn3_ | well, because I had to call post, I went with (->> br line-seq (map #(post %) )) |
| 02:19 | xumingmingv | I want to add a hook for `lein repl` |
| 02:19 | TheBusby | jhowarth__: remember map is lazy |
| 02:19 | TheBusby | whoops, sorry |
| 02:20 | xumingmingv | The doc: https://github.com/technomancy/leiningen/blob/stable/doc/PLUGINS.md says I needs to add a namespace lein-repl/plugin.clj |
| 02:20 | TheBusby | johnmn3_: remember that map is lazy |
| 02:20 | TheBusby | also you removed the filter... |
| 02:21 | johnmn3_ | won't it just stop mapping once it hits nil? |
| 02:21 | TheBusby | ah, I see your point |
| 02:22 | johnmn3_ | I'm hoping the seq will be consumed |
| 02:22 | TheBusby | doall? |
| 02:22 | johnmn3_ | I guess I'll throw a doall in front of it... sometimes I don't need to though |
| 02:23 | TheBusby | I think the chunksize for some sequences is ~32? So if it's less than that likely not, but otherwise... |
| 02:23 | TheBusby | your java was an endless loop, so not sure how to handle that here |
| 02:25 | johnmn3_ | I'm putting it in a function and I'll be calling repeatedly on that function in a thread |
| 02:26 | johnmn3_ | hoping that will work |
| 02:37 | johnmn3_ | if a library I'm using has a (def foo (atom nil)) in it and I require that namespace in two separate namespaces of mine, do each of my namespaces have unique atoms? or do they share the same one? |
| 02:43 | amalloy | the same |
| 02:45 | johnmn3_ | they're "thread local" right? But the loading of my namespaces will all take place in the same thread, so they'll share the same atoms? |
| 02:58 | semisight | hey does anyone here have any experience with clojure and sql? |
| 02:58 | amalloy | there is no thread locality involved |
| 02:59 | semisight | I'm having a really weird problem with it |
| 02:59 | semisight | here's my code: https://gist.github.com/4584333 |
| 02:59 | semisight | I can't insert multiple records using clojure's builtin map? |
| 03:00 | amalloy | ~map |
| 03:00 | clojurebot | map is slightly retarded |
| 03:00 | amalloy | hm |
| 03:00 | amalloy | more importantly it is LAZY |
| 03:01 | semisight | wat |
| 03:01 | semisight | that completely makes sense |
| 03:02 | semisight | thank you so much! |
| 03:03 | semisight | so would the best strategy be to wrap the map in a dorun call? |
| 03:06 | amalloy | meh |
| 03:06 | amalloy | that's fine, though i'd personally use doseq. but it looks like insert-records already does exactly what you want? |
| 03:07 | semisight | the problem with the batch insert is that I really need an upsert |
| 03:08 | semisight | I am guaranteed that there will be multiple rows of data with the same primary key |
| 04:14 | Wraithan | So is there something I could do so my template files are lazy loaded? https://github.com/wraithan/leech-tracker/blob/master/src/leech_tracker/handler.clj |
| 04:16 | Wraithan | So, my problem is I have to bounce my server to see changes to my templates, which makes working on them terribly inconvenient |
| 04:19 | ro_st | you'd have to touch handler.clj as well, and ensure ring reloads files with wrap-reload |
| 04:19 | ro_st | then handler'd reload the html files when it reloads |
| 04:20 | Wraithan | Sure, that is a terrible solution though, I know I could touch a clojure file to make it reload as well |
| 04:20 | ro_st | otherwise handler must load them every time they're used |
| 04:21 | Wraithan | I come from other languages and expect it to load the file from disk each time it executes |
| 04:21 | ro_st | congratulations :-) |
| 04:22 | ro_st | two option's i've presented are the shortest-path solutions on offer to you |
| 04:22 | Wraithan | I don't want to come off as combative, but you didn't. |
| 04:23 | ro_st | apologies. it appears that you want it to do something magical. my point is, there is no magic :-) |
| 04:23 | Wraithan | You offered one solution (touching handler.clj) and then you mentioned exactly what I am looking for without an sort of solution, just a restatement of what I want. |
| 04:23 | ro_st | if you want it to load after initial compilation (as it does now) you need to write code to produce that effect |
| 04:24 | brainproxy | Wraithan: have you looked into the reload middleware for ring? |
| 04:24 | Wraithan | What would code that loads it from the file system each time look like? |
| 04:24 | Wraithan | brainproxy: it already reloads on clj files changing if that is what you mean? |
| 04:24 | brainproxy | w/ the lein-ring plugin you can get the effect pretty easily with an option set in project.clj, but I'm not sure it's exactly what you want |
| 04:25 | ro_st | the issue is that they're html files. if they were clj files, it'd just work |
| 04:25 | brainproxy | Wraithan: ring reload middleware checks whether certain files have changed since the last request came in |
| 04:25 | brainproxy | and if so, the file and dependent namespaces are reloaded |
| 04:26 | brainproxy | lein-ring also exposes an auto-refresh? option, so changes on disk will trigger a browser refresh |
| 04:26 | brainproxy | which then kicks off the namespace reload |
| 04:26 | ro_st | yes. but this mechanic only works for .clj files. you have to touch the relevant .cljs, or, move your loading logic into a function that gets called on each request, rather than once during compilation (as (def) forms) |
| 04:26 | brainproxy | ah I see |
| 04:26 | ro_st | s/cljs/clj |
| 04:27 | Wraithan | I just don't see why it loads at compilation time rather than at execution time |
| 04:27 | brainproxy | well auto-refresh? w/ lein-ring watches other things too |
| 04:27 | ro_st | Wraithan: (def …) is evaluated once |
| 04:27 | brainproxy | e.g. I change a file in resources/public/stylesheets/... |
| 04:27 | brainproxy | a .css file |
| 04:27 | brainproxy | then the browser will refresh |
| 04:27 | Wraithan | ro_st: so it automatically memoizes? |
| 04:27 | ro_st | brainproxy: interesting. i've not experienced this behaviour |
| 04:28 | ro_st | oh, that's the browser. we're talking about updating stuff in memory on the server side |
| 04:29 | ro_st | Wraithan: yes. if you put (render-file "…") into your (GET "/" [] ?) directly, you should see that it updates properly |
| 04:29 | ro_st | or |
| 04:29 | ro_st | (defn get-index [] (render-file …)) and (GET "/" [] (get-index)) |
| 04:29 | Wraithan | I see |
| 04:30 | brainproxy | i see, didn't realize the redner file issue |
| 04:30 | brainproxy | basically, the old stuff is stuck in memory |
| 04:31 | Wraithan | ro_st: thanks, that fixed it |
| 04:32 | ro_st | excellent |
| 04:33 | Wraithan | Also, now I understand the difference |
| 04:33 | ro_st | of course, in production, you'd want some sort of only-load-if-actually-necessary mechanic to prevent excessive disk usage |
| 04:33 | Wraithan | That supposes a high load |
| 04:33 | Wraithan | this should be super low load (10-20 requests a day) |
| 04:33 | ro_st | indeed |
| 04:34 | ro_st | i see you're in portland! are you attending ClojureWest? |
| 04:34 | Wraithan | Unlikely |
| 04:34 | Wraithan | Actually definitely not |
| 04:34 | Wraithan | It is during PyCon |
| 04:34 | ro_st | ah |
| 04:35 | Wraithan | Just playing with clojure in my spare time |
| 04:35 | Wraithan | I am a python hacker for Mozilla |
| 04:35 | ro_st | nice |
| 04:36 | Wraithan | Also hard to justify 350 for a hobby side language |
| 04:39 | ro_st | true :-) |
| 04:46 | muhoo | 350? |
| 04:46 | muhoo | oh right, cljwest fee |
| 05:44 | piranha | I've changed drip wiki a bit: https://github.com/flatland/drip/wiki/Clojure/_compare/8733641e714006f8da8ab1cb081f7a0bf6d6e23d...f953a9221f8b6f3f772b3a05903aa70746a58bad |
| 05:44 | piranha | I hope I actually fixed it and wrote what was intended from the start :) |
| 05:51 | borkdude | is it possible to have a two-line title in org-mode? |
| 05:52 | borkdude | not really important though |
| 06:08 | ucb | borkdude: not afaik; if you find otherwise please let me know though :) |
| 06:11 | borkdude | I'm trying to go from latex to org-mode, so far I like it |
| 06:16 | ucb | borkdude: check out todo items, archiving and calendars (and tables!); your mind will be blown! |
| 06:48 | borkdude | ah, org-mode and jekyll looks like an exciting combination |
| 07:38 | rasputnik | have a simple Ring REST service packaged via uberjar, and need to supply it with some config (DB urls, etc). Is there an idiomatic way to parse config files etc.? |
| 07:39 | rasputnik | e.g want to run it as "java -jar restything.war config.json" or similar |
| 07:41 | borkdude | anyone happen to know this one? http://stackoverflow.com/questions/14438582/org-mode-highlighting-using-minted-for-latex-and-htmlize-for-html |
| 07:57 | augustl | how do I load a schema from a .sql file with clojure.java.jdbc? |
| 08:00 | augustl | it works fine if I just have one CREATE TABLE and pass it to do-commands, but I get syntax error when I have multiple |
| 08:00 | augustl | the file works fine when being executed with "mysql" itself |
| 08:01 | borkdude | is it possible to create a listing with a reference/label in org-mode? |
| 08:01 | augustl | also wondering why 0.2.4 isn't out yet, 0.2.3 seems quite old and there are lots of improvements in 0.2.4 |
| 08:06 | borkdude | ah got it: <<code-reference>> |
| 08:07 | borkdude | I wonder why this has a different notation, but it works |
| 08:12 | augustl | isn't there a way to make the threading macro pass the previous value as a argument I specify, instead of the first argument? |
| 08:12 | augustl | the use case is to end the threading with a (remove predicate insert-prev-value-here) |
| 08:13 | scottj | piranha: were you able to see a speedup in lein? which commands? |
| 08:14 | piranha | scottj: lein cljsbuild once <target> was 18 seconds vs 5 seconds |
| 08:14 | piranha | when I just had -drip it was always 18 seconds |
| 08:15 | ucb | augustl: you also have ->> which places the value as the last arg. |
| 08:15 | ucb | augustl: afaik those are the two only options |
| 08:16 | scottj | piranha: ahh, I was running lein not lein2 :) thanks for the edit! |
| 08:16 | piranha | np :) |
| 08:17 | augustl | ucb: I see |
| 08:22 | augustl | figured out how to load a sql schema - split the sql file on #";" and run them as individual commands ;) |
| 08:46 | dignati | Hey clojurists! Would someone mind to check out this function and tell me if it is idiomatic/good code? I read a lot of CL code recently and think I got confused with functional/non-functional code. https://gist.github.com/4585871 |
| 08:50 | ucb | dignati: why do you define an anonymous fn only to call it immediately? |
| 08:51 | dignati | The function recurs to it. I needed more function params to keep track of my state |
| 08:52 | xeqi | loop |
| 08:52 | ucb | that'd be the one |
| 08:52 | ChongLi | hmm, nested js obj property access is really ugly in cljs |
| 08:52 | ChongLi | is there no macro for this? |
| 08:53 | dignati | xeqi: of course I can loop over it but I looked for a recursive solution |
| 08:54 | ChongLi | dignati: function params to keep track of your state? just use a map |
| 08:56 | ucb | dignati: I think he meant the loop/recur construct; you can have recursion with loop |
| 08:56 | xeqi | dignati: loop just sets bindings and creates a recur point. its the same effect as immediately calling the anon fn |
| 08:56 | dignati | ChongLi: Ah, now I know what "params to keep track of state" reminded me of. I have no idea how to do it in this but might have to take a look |
| 08:57 | ChongLi | dignati: a map is an extremely useful data structure |
| 08:57 | ChongLi | it stores keys and their associated values |
| 08:58 | dignati | ucb: xeqi: Okay I check this out. Thanks! |
| 08:58 | dignati | ChongLi: Oh I thought you meant #'map |
| 08:59 | ChongLi | more like this: {:key value :key2 3} etc. |
| 08:59 | dignati | Okay thanks for your help, I'm going to rewrite it with loop |
| 08:59 | ChongLi | maps in clojure can be nested as well |
| 09:00 | dignati | ChongLi: Got that ;) |
| 09:00 | ChongLi | you can put a very big tree of program state entirely within one map |
| 09:02 | xeqi | $findfn [1 2 3 4 5] [3 4] true |
| 09:02 | lazybot | [clojure.set/superset? clojure.core/not= clojure.core/distinct? clojure.core/every?] |
| 09:02 | xeqi | $findfn [1 2 3 4 5] [3 4] [3 4] |
| 09:02 | lazybot | [clojure.set/select clojure.set/intersection clojure.core/max-key clojure.core/cond clojure.core/dosync clojure.core/sync clojure.core/char-escape-string clojure.core/*data-readers* clojure.core/filterv clojure.core/default-data-readers clojure.core/filter cloju... https://www.refheap.com/paste/8832 |
| 09:02 | aroemers | ChongLi: I am still pondering whether a big state map is a good idea. I think for one it is good for "trampolining" functions, but still.. the entire state passing around.. |
| 09:03 | aroemers | It feels wrong somehow. |
| 09:03 | aroemers | Any opinions on this? |
| 09:06 | ChongLi | aroemers: what do you mean the entire state passing around? |
| 09:06 | ChongLi | all that passes around is a reference |
| 09:07 | ChongLi | you don't pass the entire thing to every function, that would force every function to traverse the state to get what it needs |
| 09:08 | aroemers | Sure, but it may complicate undestanding simple functions that have this reference. It starts with all this state available. Less state in a function is desirable. |
| 09:08 | ChongLi | it's not really state |
| 09:08 | ChongLi | since it's not mutable |
| 09:08 | ChongLi | it's just a value |
| 09:08 | ChongLi | a simple function would operate on a simple value |
| 09:09 | aroemers | Hmm, assuming you know up-front what part of the state the function needs (and what the nested function calls need) |
| 09:11 | aroemers | For instance, in a parses I've written, I have to pass the entire state to a simple function, because that simple may call another function that needs most of the state. Thus, more state is available in the simple function than necessary. |
| 09:11 | aroemers | *parser |
| 09:12 | aroemers | Ah well, still in doubt whether this is a bad thing. |
| 09:12 | ChongLi | well, you can pass the state around, stick it in an atom or go the monad route |
| 09:13 | ChongLi | monads have been used in parsers in the past |
| 09:14 | aroemers | True, if you put it like that, passing the state around is actually a good choice. :) |
| 09:32 | borkdude | hmm, I'm having this in a .org file: src_clojure{[1 2 "a" "b"]} |
| 09:32 | borkdude | but it doesn't translate well to latex |
| 09:37 | aroemers | borkdude: Using the 'listings' package might help you out. |
| 09:37 | borkdude | aroemers I'm using minted |
| 09:37 | aroemers | Ah, don't know that one |
| 09:38 | borkdude | aroemers It has better highlighting for clojure |
| 09:41 | aroemers | Clojure highlighting is listing takes some work indeed, but it is doable. I'll check minted the next time though |
| 09:42 | aroemers | *in |
| 09:47 | borkdude | =[1 2 "a" "b"]= in org-mode becomes [1 2 äb"] in latex… |
| 09:49 | borkdude | maybe it's just better to not inline code |
| 10:14 | xumingmingv | need a little help here |
| 10:14 | xumingmingv | ,(= (quote a) (quote a nil)) |
| 10:14 | xumingmingv | &(= (quote a) (quote a nil)) |
| 10:14 | lazybot | ⇒ true |
| 10:14 | clojurebot | true |
| 10:14 | xumingmingv | why (quote a) == (quote a nil) ? |
| 10:17 | algernon | xumingmingv: because quote quotes a form, "a nil" is two forms, not one |
| 10:17 | xumingmingv | so the `nil` here is just ignored? |
| 10:17 | algernon | yes |
| 10:17 | algernon | &(quote a b) |
| 10:17 | lazybot | ⇒ a |
| 10:17 | xumingmingv | ohh, thanks |
| 10:31 | borkdude | can you have TODO items in org-mode which aren't headings |
| 10:31 | borkdude | headlines |
| 10:32 | borkdude | I just want to add some TODO remarks to my text, without it being a section, and exclude it on export |
| 10:33 | qz | how do i pass java methods as predicate to filter? say i want to call .isFile, wrap it in anonymous function #(.isFile %) ? |
| 10:33 | aroemers | qz: Yes, that's how I do it anyway. |
| 10:34 | qz | aroemers: i see, thanks |
| 10:40 | tmciver | Has anyone else had a problem with nrepl where loading a file (C-c C-l) stops working apparently after a previous attempt at loading a file failed with an exception? |
| 10:41 | tmciver | I'm using 0.1.5. I should probably try out 0.1.6. |
| 10:41 | NeedMoreDesu | How do I add jar to the project? I wish it would be somewhere in project dir. |
| 10:43 | augustl | are there any general tips for calling macros inside macros? Trying to call "binding" within a macro, getting "Can't embed object in code, maybe print-dup not defined:" all of a sudden |
| 10:45 | jweiss | i think i might have asked this before, but is it possible to alias a namespace without requiring it? i don't want to load it, i just want to refer to namespaced keywords |
| 10:45 | jweiss | i mean in the ns form. i am aware of alias fn |
| 10:46 | aroemers | NeedMoreDesu: install the library in your local repository, it's the best option. It is intentional that you cannot add a jar to the project easily. |
| 10:53 | augustl | can preconditions alter the arguments? For example, I want a precondition that validates that something is a date, and to do that I need to create a date object. Would be nice if I could just pass on that date object so I don't have to create a new one |
| 10:55 | nDuff | ...why would you need to create a Date to validate whether something _is_ a date? |
| 10:55 | nDuff | Do you mean validate that something can be used as an argument to one of Date's constructors? |
| 10:56 | NeedMoreDesu | aroemers: thanks. I think I'm getting how does it work now. |
| 10:56 | augustl | nDuff: it was probably not a good example. But in some cases, you want to parse something and check if the parse result was A OK, and use that parsed object. |
| 10:57 | nDuff | Sounds like a precondition just isn't the right construct. |
| 10:58 | nDuff | Move the parsing into your function, and then it's moot. Could make a macro or HOF that automates it for you, of course. |
| 10:59 | augustl | yeah it's in the function now |
| 10:59 | augustl | it's called preconditions, not pre-operations, after all :) |
| 11:37 | gfredericks | is it normal that `lein run` takes a few minutes to return if I use a future? i.e., a few minutes past the last future finishing |
| 11:37 | gfredericks | I assume `shutdown-agents` is related to this... |
| 11:37 | gfredericks | just curious about the long delay |
| 11:40 | nDuff | gfredericks: ...right -- if you shut down the pools yourself, you should be able to avoid that delay. |
| 11:42 | gfredericks | Anybody know why the delay is necessary? |
| 11:42 | craigbro | gfredericks: |
| 11:43 | craigbro | gfredericks: a few minutes islonger than I have experienced, but I have seen such delays. I explicitely System/exit |
| 11:43 | gfredericks | it may be shorter, I'm timing it now |
| 11:43 | craigbro | I had a -main method that called some code that use pcalls and it added tens of seconds or more to calling that module, unless I did System/exit |
| 11:44 | craigbro | gfredericks: I didn't investigate why, I just did that because as a unix dork I was like, "err, waiting on children, exit will round em up." |
| 11:45 | gfredericks | after timing once with and without, it is strikingly close to exactly one minute |
| 11:46 | clgv | gfredericks: do you use shutdown-agents? |
| 11:46 | gfredericks | clgv: it finishes 60 seconds sooner with shutdown-agents |
| 11:46 | gfredericks | this is tricky because I'll need to make sure that I have no more things to run |
| 11:46 | craigbro | http://clojuredocs.org/clojure_core/clojure.core/future |
| 11:46 | craigbro | explains it 8) |
| 11:47 | gfredericks | craigbro: oh nice, thanks |
| 11:48 | craigbro | one would expect dereferencing the future should kill it's thread eh? |
| 11:50 | craigbro | the jira bug is illuminating |
| 11:50 | nDuff | craigbro: I wouldn't tend to expect that. Starting and shutting down threads is expensive. |
| 11:52 | gfredericks | is it odd that there's no mechanism to register a deliverance callback with a promise? |
| 11:52 | nDuff | Hmm. That _could_ be useful. |
| 11:52 | nDuff | Seems like something you could do yourself |
| 11:52 | nDuff | ...not hard to wrap something but still keep it implementing IDeref |
| 11:52 | gfredericks | without holding up a thread on a deref? |
| 11:53 | clgv | gfredericks: put a deref of that promise in a future ;) |
| 11:53 | gfredericks | clgv: I'm naively assuming that's unideal to keep a thread occupied in that |
| 11:53 | clgv | gfredericks: huh? it does not do anything actively |
| 11:54 | gfredericks | clgv: sure. I don't know about the impl details. E.g., is there a fixed-size thread pool that we're hogging a thread from? |
| 11:55 | clgv | gfredericks: futures use an unbounded threadpool |
| 11:55 | gfredericks | then do I have to worry about doing this hundreds of times? |
| 11:58 | craigbro | yah, I didn't realize futures use a pool |
| 11:59 | craigbro | I had a problem with futures accumulating (ring file upload handler) it would blow up under load testing |
| 12:00 | craigbro | so I assumed that each future was it's own thread |
| 12:25 | technomancy | gfredericks: lein used to shut down the thread pool, but it had some weird effects on programs that relied on the fact that the thread pool was keeping the JVM running |
| 12:27 | gfredericks | technomancy: oh that's reasonable; I wouldn't expect lein to monkey with this. Would have broken my code I'm pretty sure. |
| 12:29 | technomancy | it wouldn't be a problem if Clojure actually exposed the thread pool and allowed you to restart it, but it's all hard-coded and yucky |
| 12:31 | Morgawr | hello... I started using clojure a few days ago and I decided to give leinigen a try... I created a new project and I can add functions and stuff to my core.clj file |
| 12:31 | Morgawr | however I want to have multiple files .clj |
| 12:31 | Morgawr | if I give them all the same namespace, I can't still find the functions loaded in the repl |
| 12:31 | Morgawr | how do I make lein recognize multiple different .clj files in my src folder? |
| 12:32 | nDuff | Morgawr: First -- your files should each have their own namespace. |
| 12:32 | nDuff | Morgawr: ...the namespace names need to correlate to the filenames. |
| 12:32 | Schaefer | Morgawr - Each file should be in its own namespace. Also, the file name should match* the namespace. Are you familiar with java packages and class files? |
| 12:32 | nDuff | Morgawr: once that's done, you should be able to require or use them. |
| 12:33 | Schaefer | *match - as you're learning, stay away from special characters in namespaces like the dash "-" |
| 12:33 | Morgawr | Schaefer and nDuff ah okay... I get it, so I have this file called mytest.clj in my src/tests/ directory |
| 12:33 | Morgawr | I do (require 'tests.mytest) (I have the right namespace in the file) |
| 12:33 | Morgawr | and it still can't find the function I declared |
| 12:34 | nDuff | Morgawr: so, require doesn't automatically bring references into the current namespace. |
| 12:34 | nDuff | Morgawr: so, how are you trying to use it? If it's tests.mytest/myfunction, that should work. |
| 12:34 | Morgawr | oh.. okay, using that it worked :) |
| 12:34 | nDuff | Morgawr: ...likewise, if you want a shorter name, you can (require '[tests.mytest :as mytest]), and then it's just mytest/myfunction. |
| 12:34 | Morgawr | thanks, I was getting a bit confused by this :) |
| 12:34 | technomancy | Morgawr: might want to read `lein help tutorial`; it offers some pointers there |
| 12:35 | Schaefer | i'm having trouble with lein's injections and CCW. should i expect ":injections [(prn (into {} (System/getProperties)))" to print out the system properties with i start a CCW repl session? |
| 12:35 | technomancy | Schaefer: it'll put it to stdout; where that goes is CCW's business |
| 12:35 | Morgawr | technomancy: I read the tutorial, I was really confused because I couldn't find any reference to this specific case of having multiple files.. but yeah, might have been me |
| 12:36 | Morgawr | trying to do project euler stuff, having a namespace for each problem :) |
| 12:36 | technomancy | Morgawr: oh, it has a link to the 8th light article instead |
| 12:36 | bozhidar | technomancy: sorry to bother you, but I was wondering if you'll be able to spare some time to review the dozen of PRs for clojure-mode and give it some love :-) |
| 12:37 | muhoo | it's starting to get annoying that nrepl-eval-last-expression keeps trying to eval in the user namespace, not the namespace of the file |
| 12:37 | muhoo | nrepl-set-ns does not fix it |
| 12:38 | muhoo | but evaling the ns declaration in the file does. |
| 12:38 | Schaefer | technomany: i don't think the injections is getting evaluated at all. i have changed my project def to include ":injections [(use 'clojure.pprint)]" but when i try (pprint "test") on the repl, i get an unable to resolve symbol error |
| 12:39 | muhoo | nDuff: i thought it was here, actually. #python has the "NO LOL" rule |
| 12:39 | bozhidar | technomancy: In particular https://github.com/technomancy/clojure-mode/pull/128 fixes a small error I made when I converted clojure-mode to a derived mode and people living on the edge are getting a byte-compilation warning |
| 12:39 | Morgawr | is there a way to force lein to re-load a file? because I am editing a file and I am still in the repl |
| 12:39 | gfredericks | man returning from inside a ruby block has got to be the ultimate example of an impure "function" |
| 12:39 | bozhidar | muhoo: just use `C-c C-k` |
| 12:40 | muhoo | Morgawr: (require 'foo :reload) ? |
| 12:40 | Morgawr | muhoo: thanks! |
| 12:40 | bozhidar | muhoo: we're having some problems deciding on the behaviour of nrepl-eval-last-expression |
| 12:40 | muhoo | bozhidar: great, thanks, that worked |
| 12:40 | tomoj | b |
| 12:47 | muhoo | ok next... is there some way to force stencil to refresh its core.cache? |
| 12:48 | muhoo | ah got it invalidate-cache-entry |
| 12:54 | muhoo | hmm, i could swear i've seen a lein plugin somewhere that watches moustache templates and invalidates the cache entry if they get updated on disk |
| 12:55 | Morgawr | okay.. got another question for lein and repl.. I have a "(def mylist (range 1 20))" (just something, doesn't matter what it is), if I require the correct namespace inside my lein repl, why can't I do (mynamespace/mylist)? it says undefined reference |
| 12:58 | Morgawr | oh nevermind =_= I'm an idiot I was using the wrong namespace name sorry |
| 13:14 | tmciver | technomancy (or anyone else): how do I tell emacs to load the nrepl elisp I cloned from github rather than the version I had installed through package.el? |
| 13:17 | bpr | (load-file "/path/to/nrepl.el") |
| 13:17 | hyPiRion | tmciver: M-x package-list-packages, remove the nrepl you got there first |
| 13:18 | tmciver | bpr: Yeah, I can try that. I was hoping that it would load automatically as the current version of nrepl does. |
| 13:18 | hyPiRion | tmciver: Put it in your emacs.d/init.el file |
| 13:19 | tmciver | hyPiRion: I don't have that file. I wonder how nrepl gets loaded now. |
| 13:23 | bpr | tmciver: you can create it |
| 13:23 | technomancy | tmciver: if you're not planning on updating your git checkout often, M-x package-install-file is an easy way to do it |
| 13:24 | technomancy | muhoo: don't get me started on the namespacing problems of nrepl.el; it's completely bonkers |
| 13:24 | technomancy | muhoo: here's a workaround: (add-hook 'clojure-mode-hook (defun nrepl-fix-buffer-ns () (when (clojure-find-ns) (setq nrepl-buffer-ns (clojure-find-ns))))) |
| 13:24 | jonasen | Do I have to do something special when starting an nREPL server (programmatically) to redirect *out* to the response map? https://www.refheap.com/paste/8838 |
| 13:24 | tmciver | technomancy: ah, that sounds like the solution I was looking for. |
| 13:25 | tmciver | technomancy: do I have to re-run package-install-file each time I update it? |
| 13:26 | technomancy | tmciver: yeah, better to use load if you're updating frequently |
| 13:26 | tmciver | k |
| 13:26 | beffbernard | Is there such a thing as a reusable promise? |
| 13:27 | nDuff | beffbernard: What do you mean by that? You can re-deref them and get the same result more than once after they've done their work. |
| 13:28 | beffbernard | nDuff: I want to be able to set it more than once.. |
| 13:28 | beffbernard | nDuff: my use case to hold a socket in that promise |
| 13:28 | beffbernard | and the socket can and does change |
| 13:29 | nDuff | beffbernard: I'm not sure that promises are the right abstraction for that, then. |
| 13:29 | tomoj | 'set a promise more than once' = 'break a promise' |
| 13:29 | beffbernard | I guess the semantics I want is to block if the resource is nil |
| 13:29 | nDuff | beffbernard: almost sounds more like you want an agent than a promise to me. |
| 13:29 | beffbernard | and have the convenience of deref |
| 13:29 | nDuff | beffbernard: ...if I'm understanding your use case correctly. |
| 13:36 | beffbernard | nDuff: doesn't quite fit my use case I think |
| 13:37 | yedi | how can i find the most recent version numbers for cljs |
| 13:42 | hyPiRion | Oh lord, my hair's on fire. I'm sad I can't use Leiningen for c projects. |
| 13:52 | muhoo | hmm, what's the difference between :injections and :init in lein? |
| 13:52 | technomancy | muhoo: :injections is composable; :init is kind of leftover from 1.x |
| 13:52 | muhoo | cool, thanks |
| 13:54 | gfredericks | is there any straightforward way to check if something is a promise? |
| 13:54 | gfredericks | probably good enough for me to use (instance? clojure.lang.IPending ...), but it's weird there doesn't seem to be anything else |
| 13:56 | muhoo | beffbernard: there was some stuff in lamina that looked like it could be used for that purpose |
| 13:58 | TimMc | gfredericks: When would you want to know that it's one type of IPending versus another? |
| 13:58 | bpr | beffbernard: maybe this is what you want: http://clj-me.cgrand.net/2010/04/02/pipe-dreams-are-not-necessarily-made-of-promises/ |
| 13:58 | TimMc | Oh, do you also want to check for futures as well? |
| 13:58 | gfredericks | TimMc: IPending is fine for me; there might not be an actual use case |
| 13:59 | gfredericks | assuming that IPending is what it sounds like at least |
| 13:59 | gfredericks | unfortunately it has no docstring :) |
| 13:59 | gfredericks | heck, I'm not even sure it's not just an implementation detail |
| 14:00 | technomancy | when in doubt, it's an implementation detail |
| 14:00 | gfredericks | technomancy: okay then. How do I tell if something is a promise? :) |
| 14:01 | gfredericks | ,(instance? (type (promise)) (promise)) |
| 14:01 | clojurebot | true |
| 14:01 | gfredericks | I guess that's bound to work |
| 14:01 | technomancy | I dunno; TBH you'd never really get anywhere in Clojure without relying on implementation details |
| 14:02 | gfredericks | whether or not something is an implementation detail is an implementation detail |
| 14:02 | technomancy | ...! |
| 14:02 | muhoo | meta |
| 14:03 | technomancy | yeah actually even the "keys and vals are guaranteed to use consistent ordering on the same instance" is somewhat apocryphal |
| 14:03 | gfredericks | "Legends of Clojure: implementation details you can count on" |
| 14:04 | technomancy | heh |
| 14:04 | technomancy | I smell a conj talk? |
| 14:04 | gfredericks | haha |
| 14:04 | gfredericks | technomancy: this talk will feature live documentation coding |
| 14:05 | technomancy | gfredericks: for extra living dangerously points: live attempts at using Jira |
| 14:05 | gfredericks | it's not an implementation detail if you can trick stuarthalloway into merging in your docstring patch |
| 14:05 | muhoo | clojure seems not nearly as implentation-detail-heavy as, say, android, which has a huge layer of folklore built on top of its otherwise good documentation |
| 14:06 | hyPiRion | Have anyone here programmed in C++? Then you'll know implementation details. |
| 14:06 | muhoo | good point |
| 14:09 | muhoo | oh gawd, i just realized that after a decade of dealing with autotools. unix itself is pretty much one big implementation detail. |
| 14:09 | muhoo | apt-get hides all that, but it's there. |
| 14:10 | technomancy | I've started to notice these weird parallels between the monthly "everyone hates jira" threads on the clojure mailing list and the monthly "everyone hates bzr" threads on emacs-devel. |
| 14:13 | aaelony | a strange thing just started happening in lein-swank. I compile my ns, which returns nil, but then it is as if it didn't load in any of the require and import statements. For example, I'm importing java.io.BufferedWriter but it reports "Unable to resolve classname: BufferedWriter" If I do a lein repl outside of emacs, and run the same ns statement and run the functions, everything is fine. [lein-swank "1.4.5"] is in my |
| 14:13 | aaelony | ~/.lein/profiles.clj under :user then under :plugins. Any ideas? |
| 14:13 | clojurebot | Gabh mo leithscéal? |
| 14:15 | mmitchell | anyone using nrepl and auto-complete in emacs? I keep getting this error when connecting: clojure.lang.Compiler$CompilerException: java.lang.ClassNotFoundException: complete.core, compiling:(NO_SOURCE_PATH:1) |
| 14:16 | hyPiRion | mmitchell: I do |
| 14:17 | hyPiRion | not sure if this helps, but I have https://github.com/hyPiRion/emacs.d/blob/master/hypirion-clj.el#L21-29 for setting up ac |
| 14:18 | muhoo | can :init-ns be used elsewhere except in :repl-options? |
| 14:19 | amalloy | technomancy: phases of the moon, perhaps? |
| 14:19 | muhoo | i don't want to define :repl-options in the project and have it clobber what's in profiles.clj |
| 14:20 | muhoo | keep getting burned by non-recursive merges in lein |
| 14:22 | mmitchell | hyPiRion: thanks! unfortunately i'm still getting that error hmm |
| 14:23 | mmitchell | i don't even know where to get "complete.core" ? |
| 14:23 | muhoo | oh cool. it merges them. yay lein pprint |
| 14:25 | gfredericks | so future is guaranteed to inherit dynamic var values right? No ambiguity there? |
| 14:25 | muhoo | mmitchell: https://github.com/ninjudd/clojure-complete ? |
| 14:25 | gfredericks | s/ambiguity/edge-cases/ |
| 14:29 | muhoo | hmm, nrepl doesn't seem to honor :init-ns |
| 14:29 | muhoo | always get user |
| 14:30 | muhoo | thrashy thrashy bang bang |
| 14:30 | technomancy | :init-ns might be specific to reply |
| 14:31 | technomancy | cemerick might know if there's a way to set that stuff on the server side |
| 14:32 | muhoo | wait, i'm totally confused now. sample.project.clj says that :injections gets evaled on every form, but then it implies elsewhere it gets evaled on every repl |
| 14:33 | muhoo | "Forms to prepend to every form that is evaluated inside your project." |
| 14:33 | technomancy | oh, that should be "every eval-in-project invocation" instead |
| 14:33 | amalloy | muhoo: from lein's point of view, the repl is one form |
| 14:33 | amalloy | (in-the-project (run-a-repl)) |
| 14:33 | muhoo | ah, cool. confusing way to put it tho |
| 14:33 | technomancy | what amalloy said, but that's an implementation detail that the docs shouldn't assume |
| 14:35 | muhoo | maybe i should take a step back. here's what i'm trying to do: |
| 14:35 | muhoo | 1) set the namespace for every new repl to go into (hmm. maybe :injections might work for that) |
| 14:35 | muhoo | 2) set some code to run on every repl invocation |
| 14:36 | technomancy | 1) would need to be handled by nrepl; I'm not sure how it's done |
| 14:36 | muhoo | 3) have some form to evaluate in-project whenever the project loads, not on every repl, i.e. (myns.server/-main) |
| 14:36 | technomancy | if 2 means on every `lein repl` invocation then :injections inside the :repl profile should do it |
| 14:37 | technomancy | and 3 should work as :injections in the base project map |
| 14:37 | muhoo | ok, so two different injections, get evaled at different times? |
| 14:37 | muhoo | depending on where they are in the map? |
| 14:38 | muhoo | by 2) i mean every time i connect to the repl over :repl-port |
| 14:38 | muhoo | via nrepl |
| 14:38 | gfredericks | so I'm about to write some code that manages running async jobs (via future), particularly giving functionality to wait for all jobs directly or indirectly started from this thread to be done |
| 14:39 | gfredericks | am I reimplementing something that already exists in clojure/jvm? |
| 14:39 | gfredericks | was just going to wrap future with code that registers the job and notes when it's done, and use a dynamic var to track what thread it originated in |
| 14:39 | technomancy | muhoo: oh, ok that's different then for 2 |
| 14:39 | technomancy | that would be an nrepl question rather than leiningen; unfortunately I'm not familiar |
| 14:40 | muhoo | fair enough, thanks |
| 14:40 | jeremyheiler | gfredericks, there is java.util.concurrent.CyclicBarrier |
| 14:41 | technomancy | muhoo: I agree that we should document though |
| 14:41 | technomancy | just haven't figured it out yet |
| 14:41 | muhoo | technomancy: the bummer is though, i thought i was told never to shadow the :repl profile in the project.clj |
| 14:41 | muhoo | because it clobbers it |
| 14:41 | muhoo | but i'll try base project map, that may do it |
| 14:41 | technomancy | muhoo: yeah, I think hyPiRion fixed that |
| 14:42 | muhoo | oh cool |
| 14:42 | technomancy | because you're right that it's confusing |
| 14:43 | amalloy | (doto (f x) (-> (->> (g y)) (h z))) ;; i love arrows and doto, but i really can't bear to put this in my program |
| 14:44 | hyPiRion | muhoo: https://github.com/technomancy/leiningen/issues/520 |
| 14:44 | muhoo | technomancy: sorry, i've got more dumb :injections questions |
| 14:44 | muhoo | why would :injections be exploding with "Unable to resolve symbol: do" ? |
| 14:45 | technomancy | muhoo: that's strange... is it being syntax-quoted? |
| 14:45 | muhoo | i'm trying :injections (do (require 'myns.server) (myns.server/-main)) |
| 14:45 | muhoo | ah i see, it wants a vector |
| 14:46 | technomancy | oh, yeah you need that in order to combine injections from multiple profiles |
| 14:46 | gfredericks | jeremyheiler: that sounds like an interesting google, thanks |
| 14:46 | technomancy | muhoo: we should probably put a warning on non-vectors there; feel free to open an issue |
| 14:47 | Schaefer | hi. i'm having trouble using cemerick's piggieback + clojurescript with CCW. i get "Can't change/establish root binding of: *cljs-repl-options* with set" . |
| 14:48 | amalloy | make sure it's as helpful as the error message for (defn foo (vector bar baz)), technomancy |
| 14:48 | technomancy | amalloy: necessarily |
| 14:48 | amalloy | for the lazy: "Parameter declaration vector should be a vector" |
| 14:49 | muhoo | well in my case, "RTFM" would have been a sufficiently useful error message |
| 14:50 | technomancy | it's not as clear as it should be |
| 14:50 | muhoo | ah, yay, it works. all is bliss. |
| 14:51 | technomancy | just need to stalk cemerick to get those nrepl tips from him |
| 14:52 | Schaefer | thanks. do you happen to know if CCW using lein to start the repl? i can't figure out if it honors :repl-options in the project definition |
| 14:54 | Schaefer | ah... i bet i know the problem: the current release of CCW fails on some dependency. i thought i had a workaround but possibly not |
| 14:57 | gfredericks | that unified update model is quite slick. |
| 15:00 | craigbro | ccw? |
| 15:00 | clojurebot | ccw is http://github.com/laurentpetit/ccw |
| 15:01 | amalloy | (inc clojurebot) |
| 15:01 | lazybot | ⇒ 15 |
| 15:01 | craigbro | ah, eclipse |
| 15:02 | amalloy | gfredericks: yeah, it's great. it's also the only time i can call a single function with seven or eight arguments and not feel filthy |
| 15:02 | mmitchell | muhoo: hey thanks, i'll check that out |
| 15:02 | frozenlock | Any advice on how to handle states in cljs? (Libraries or best practice) I've just begun to deal with them and I'm pretty sure I'm digging myself in a hole :/ |
| 15:03 | mmitchell | muhoo: do you know how i use that? |
| 15:03 | gfredericks | amalloy: yeah that's what sparked the thought :) |
| 15:03 | mmitchell | muhoo: the clojure-complete lib w/emacs and auto-complete? |
| 15:03 | amalloy | gfredericks: the only thing i don't like is that if i write something like (apply swap! x vary-meta update-in :logs concat) i lose track of the fact that i'm applying by the time i get to concat |
| 15:03 | gfredericks | it kind of makes me want a (map coll func & args) |
| 15:04 | muhoo | mmitchell: i thought it was already included from nrepl/reply/etc already |
| 15:04 | therealadam | what is the go-to http client for clojure? |
| 15:04 | gfredericks | clj-http |
| 15:04 | mmitchell | muhoo: oh i see |
| 15:05 | muhoo | mmitchell: last i checked, if you have nrepl and lein installed and working, autocomplete just works |
| 15:05 | therealadam | gfredericks: thanks! |
| 15:05 | muhoo | which isn't to say i have either, so i'm still M-/ 'ing by habit |
| 15:05 | amalloy | states like: california, a state machine, or mutable state throughout your application? |
| 15:06 | therealadam | gfredericks: is https://github.com/mmcgrana/clj-http still the canonical repo? |
| 15:06 | therealadam | derp, n/m |
| 15:06 | mmitchell | muhoo: ok good to know. I'll remove a bunch of my emacs config and see what happens |
| 15:07 | gfredericks | curious if anybody thinks this is terrible or knows an easier way: https://www.refheap.com/paste/8840 |
| 15:07 | borkdude | Does anyone using org-mode to write the answer to this one? http://stackoverflow.com/questions/14446157/writing-a-document-in-org-mode-is-it-possible-to-refer-to-a-code-fragment |
| 15:08 | amalloy | gfredericks: line 14 is crying out for fnil |
| 15:08 | gfredericks | I've never once thought to use fnil |
| 15:08 | gfredericks | you have to admit though that fnil technically creates a set that might not get used :P |
| 15:08 | frozenlock | amalloy: If your question was for me, it's mutable states. |
| 15:08 | gfredericks | but yeah it's a lot more readable |
| 15:08 | amalloy | and `wait` has a race condition that leads to deadlock |
| 15:09 | amalloy | i recommend using useful.state/wait-until, which doesn's |
| 15:11 | amalloy | gfredericks: (let [conj (fnil conj #{})] (defn run-job ...)) ;; now the set is only made once, you whiner |
| 15:13 | gfredericks | amalloy: oh I misunderstood how to use fnil there then |
| 15:13 | amalloy | well, i wasn't suggesting you actually do that. but if creating a set that might not get used bothers you, you can do this instead |
| 15:13 | gfredericks | I imagined a #{job-id} getting created but you're right |
| 15:13 | gfredericks | amalloy: amn't figuring out what the race condition is |
| 15:14 | amalloy | hmmmm, there might not actually be one because the keys in the map are thread ids |
| 15:15 | amalloy | but i think there is. line 27 runs, sees there's still a job waiting. so it creates a promise, then gets interrupted. some other thread finishes the last job, and updates the atom. now the first thread adds a watcher and blocks on it, but nobody ever updates the job list again |
| 15:16 | gfredericks | ah right |
| 15:16 | gfredericks | so another check before line 34 would do it? |
| 15:17 | amalloy | gfredericks: yes. that's basically what i do at https://github.com/flatland/useful/blob/develop/src/flatland/useful/state.clj#L54 |
| 15:17 | gfredericks | I was reading that |
| 15:17 | owengalenjones | can anyone explain why ( or point me in the direction of explanations why ) recur in this situation hangs the repl: http://d.pr/n/fOGk |
| 15:17 | amalloy | owengalenjones: recur points at your lambda, not at tree? |
| 15:18 | owengalenjones | amalloy: is there a way to have it escape the scope? |
| 15:18 | amalloy | no |
| 15:18 | owengalenjones | so in this situation you would always have to specify the parent fn |
| 15:18 | TimMc | gfredericks: So run-job fires off a job, and wait "joins" on all the jobs? |
| 15:18 | amalloy | recur doesn't consume stack space; there is no way to write what you want without stack space (ignoring CPS) |
| 15:19 | amalloy | thus, you can't use recur |
| 15:19 | owengalenjones | ok thanks |
| 15:22 | TimMc | gfredericks: It would be nice if this code were commented with descriptions of e.g. what the atom is supposed to contain, what invariants you expect to hold... |
| 15:23 | gfredericks | TimMc: yes and yes |
| 15:23 | gfredericks | well |
| 15:23 | gfredericks | wait joins on all jobs that originated from the current thread |
| 15:23 | TimMc | Mmm, I see. |
| 15:24 | gfredericks | come to think of it I don't actually have a use case for ignoring things from other threads |
| 15:24 | gfredericks | but just in case I even do... :) |
| 15:24 | gfredericks | s/even/ever/ |
| 15:26 | TimMc | Is the following correct? #'jobs is an atom containing maps of thread IDs to sets of IDs of jobs that may or may not have started yet, but definitely have not finished. |
| 15:26 | Sgeo | #'jobs is (var jobs) which is a var |
| 15:27 | TimMc | Yes, it's a var of an atom of a map of... |
| 15:27 | TimMc | I don't know why she swallowed the fly... I guess she'll die! |
| 15:28 | amalloy | TimMc: i think it's just as accurate to say the jobs have definitely started as to say they have definitely not finished. the process is like: (1) add to set; (2) run job; (3) remove from set. so there's space on either side of (2) |
| 15:29 | nDuff | Damn -- using Clojure gets me spoiled on having its features available. |
| 15:32 | TimMc | gfredericks, amalloy: I *think* that if the when-not empty? is moved to just be around the deref, then it's all good. |
| 15:32 | TimMc | However, I'm not entirely sure what the thread safety of watchers is. |
| 15:33 | amalloy | TimMc: sure. as i note in the comments of useful/wait-until, which i linked to, the first deref is only a performance optimization |
| 15:34 | TimMc | Haha, you're using the promise itself as the watch-key? Pretty non-obvious. |
| 15:36 | amalloy | TimMc: what else would you use? |
| 15:36 | TimMc | A gensym, as gfredericks did. |
| 15:36 | amalloy | feh |
| 15:36 | TimMc | I don't see anythign wrong with using the promise, I just would have made that choice more explicit. |
| 15:37 | TimMc | I also don't like the idea that the promise is escaping that scope. |
| 15:37 | TimMc | Seems dangerous. |
| 15:38 | amalloy | your first objection seems reasonable enough, but i don't understand what you mean by escaping that scope |
| 15:39 | TimMc | It's ending up in a watcher. |
| 15:39 | TimMc | Who watches the watchers? |
| 15:40 | amalloy | it has to end up in the watcher, or else the watcher couldn't deliver to it? |
| 15:40 | amalloy | you're objecting to it being a key in the map as somehow more dangerous than being closed over by a funciton that's a value in that same map? |
| 15:41 | TimMc | In gfredericks' version, the watcher holds a closure over the local scope, but someone outside that scope can't actually touch the promise. |
| 15:41 | amalloy | okay, fair enough |
| 15:42 | TimMc | I can't build a solid case for how that might make a program go pear-shaped, but I have this general sense that something might try to str-ify the promise somehow. |
| 15:42 | TimMc | (I don't worry that somthing would deliver to it.) |
| 15:43 | muhoo | wow, that's just bizarre. lein trampline :repl works on machine 1, but on machine 2, it gives a bizarre jboss error that 8080 is already in use, and doesn't actually start the nrepl listen port |
| 15:43 | amalloy | i'm not really worried about that. not least because, in order to get a list of all watchers on a ref, you have to use undocumented interop methods |
| 15:43 | muhoo | same profiles.clj, same version of lein. different versions of java though |
| 15:46 | Sgeo | o.O fogus is now into Racket |
| 15:46 | Sgeo | ....What's the name of that effect where you learn a word and now everyone is using it? |
| 15:46 | TimMc | Baader-Meinhoff? |
| 15:46 | Sgeo | I feel like I play with a programming language and then a little while later I see others playing with it |
| 15:46 | Sgeo | TimMc, I think so |
| 15:47 | TimMc | Baader-Meinhof |
| 15:50 | wink | Sgeo: but, most importantly: did you use Racket... before it was cool? :P |
| 15:51 | Sgeo | I wish there was a language with Racket as the language and something Smalltalk-like as the environment |
| 15:51 | Sgeo | I like Racket for the language (mostly) and Smalltalk for the IDE |
| 15:53 | wink | as I've never written any for-money production code in all those languages I find so cool.. I still can't say whether I find them practical or just nice :( |
| 15:53 | gfredericks | has anybody seen korma apply a transform function to a whole result set rather than one row at a time? |
| 15:54 | dnolen | wink: plenty of people have put Clojure code into for-money production |
| 15:54 | wink | dnolen: that's not at all what I was hinting at :P |
| 15:54 | AimHere | Don't you find Clojure cool? |
| 15:55 | wink | dnolen: for example I see no way in hell to even try to write any clojure code without quitting my day job |
| 15:55 | wink | much less anything like CL or Racket |
| 15:55 | dnolen | wink: sorry I missed some backlog context |
| 15:55 | dnolen | "sorry if" I mean |
| 15:56 | wink | dnolen: didn't say much before :P it was just about using/hearing about Racket |
| 15:57 | dnolen | wink: I see, doesn't Naughty Dog use Racket for all their game scripting (I get your point about the day job) |
| 15:58 | wink | dnolen: yeah, think so |
| 15:59 | wink | maybe I need a "just get shit done" job instead of a "write maintainable code" one :P |
| 16:00 | CrawfordComeaux | I'm trying to debug https://github.com/nathanmarz/storm-deploy, but I've never used clojure before (though slightly familiar with lisps). I'm reading that I can drop a repl in where the exception's coming up, but I'm not sure how to do that |
| 16:01 | gfredericks | amalloy: TimMc: thx for comments |
| 16:03 | wink | CrawfordComeaux: least specific way would be to $ lein repl and start your boilerplate code by hand |
| 16:03 | CrawfordComeaux | wink: not even sure what the boilerplate code would be...any other things I could try? |
| 16:06 | wink | CrawfordComeaux: https://github.com/nathanmarz/storm-deploy/blob/master/src/clj/backtype/storm/provision.clj is zthe enty point |
| 16:07 | wink | afaict ;) |
| 16:07 | CrawfordComeaux | so load up the repl & c/p lines from the source? |
| 16:08 | amalloy | CrawfordComeaux: nobody can help with "X doesn't work", for any X. at least a description of what's going wrong is necessary, and ideally a stacktrace and/or what you're doing that causes a problem |
| 16:08 | CrawfordComeaux | amalloy: this was an attempt to get a stack trace |
| 16:08 | CrawfordComeaux | but the bug's already been id'd.... |
| 16:08 | CrawfordComeaux | it's me :P |
| 16:09 | CrawfordComeaux | wrong argument when executing a command |
| 16:16 | seangrove | Hrm, really struggling here - it seems like clojurescript is affecting the javascript runtime globals |
| 16:17 | seangrove | Without my script, rapportive loads fine and does its thing. As soon as my script is injected into the page, rapportive falls apart - even if it's a delayed injection |
| 16:20 | TimMc | technomancy: Where did "locative1" come from as an example password? |
| 16:21 | dnolen | seangrove: sounds like a bad bug, we try to avoid messing with native prototypes (there are a couple of remaining cases), but I'm not aware of any global clobbering. |
| 16:22 | dnolen | seangrove: would be helpful if you could isolate. |
| 16:22 | seangrove | dnolen: Really struggling to isolate it. Will continue to try |
| 16:22 | dnolen | seangrove: the one place where much with native prototypes is String, we add an apply method. |
| 16:22 | dnolen | "where we muck" |
| 16:23 | devn | ls |
| 16:23 | lazybot | boot etc lost+found mnt opt proc root sbin srv swap sys tmp usr var |
| 16:23 | arrdem | rm -r / |
| 16:23 | Bronsa | i laughed pretty hard |
| 16:24 | seangrove | Hrm, wonder if that could be it. Rapportive calls .apply on objects for type-checking to see if they're objects, functions, strings, etc. |
| 16:24 | dnolen | seangrove: yes that propably is, but checking JS types that way sounds awful :P |
| 16:24 | amalloy | muahaha. lazybot strikes again |
| 16:25 | arrdem | ,({:foo :bar} :foo) |
| 16:25 | clojurebot | :bar |
| 16:25 | dnolen | seangrove: there is an open ticket for the String issue |
| 16:25 | seangrove | Yeah, looks like it's going to mistakenly think that strings are objects... not sure if that's the root cause or not though |
| 16:25 | seangrove | dnolen: Yeah, awful, but I have to find a way to be compatible with it, which is a bummer |
| 16:26 | dnolen | seangrove: http://dev.clojure.org/jira/browse/CLJS-381 |
| 16:26 | seangrove | Any other changes to prototypes like that? |
| 16:26 | dnolen | seangrove: nope |
| 16:26 | seangrove | definitely useful for knowing where to look next |
| 16:27 | dnolen | seangrove: it's there to support keyword invokes. The ticket outlines the temporary solution. Real keywrods & symbols is the proper fix. |
| 16:27 | seangrove | hrm, is there someway I can hijack that extremely early on, e.g. (set! (.-apply js/String) nil), to test out if that's the cause |
| 16:28 | dnolen | seangrove: I don't see why not, you can probably do that before you load rapportive |
| 16:28 | seangrove | Alright, let me give it a try... |
| 16:30 | gfredericks | underscore had a type-check that got broken by cljs, but they took a patch to allow for it |
| 16:30 | gfredericks | (wrt the string prototype) |
| 16:33 | dnolen | gfredericks: that was nice of them |
| 16:33 | gfredericks | it was nice of them. |
| 16:33 | gfredericks | I think there was some alternate argument for why it was a good idea as well |
| 16:33 | gfredericks | but I was only interested in cljs compat |
| 16:34 | dnolen | gfredericks: checking for apply is a horrible idea in general yes |
| 16:35 | gfredericks | in case anybody is curious: https://github.com/documentcloud/underscore/commit/2206092e25f66f3a0dbb05c24509a7831b1863fe |
| 16:36 | dnolen | gfredericks: oh yeah, checking for call is a terrible idea too |
| 16:36 | dnolen | gfredericks: nice patch! |
| 16:38 | arrdem | can I (:require :only :as)? |
| 16:38 | gfredericks | s/:only/:refer/, yes |
| 16:39 | gfredericks | arrdem: my favorite is (:require [jayq.core :refer [$] :as $]) |
| 16:40 | seangrove | Rapportive has: _.isFunction = function(obj) { return !!(obj && obj.constructor && obj.call && obj.apply); } |
| 16:40 | dnolen | seangrove: I looked a bit closer at what would be involved in a quick fix - I don't see one. |
| 16:41 | dnolen | seangrove: yes that's completely broken |
| 16:41 | seangrove | uhg |
| 16:41 | dnolen | seangrove: should (typeof obj == "function") |
| 16:41 | dnolen | should be |
| 16:41 | dnolen | seangrove: not much we can do CLJS side |
| 16:42 | dnolen | seangrove: well .. actually we can, but somebody needs to do the Symbol & Keyword work. |
| 16:42 | seangrove | dnolen: Other than not touching String ;) |
| 16:42 | dnolen | not a particularly small project |
| 16:42 | dnolen | seangrove: no can do w/o breaking every CLJS project. |
| 16:42 | seangrove | Yeah, let me see if this is the root cause first though |
| 16:43 | arrdem | gfredericks: isn't that eqivalent to (:use [ ... :only [$]])? |
| 16:43 | dnolen | seangrove: but really you should also file a bug w/ them. |
| 16:43 | gfredericks | arrdem: probably; :use is quasi-deprecated to :require |
| 16:43 | gfredericks | dnolen: switching symbol/keyword to a deftype breaks old projects? |
| 16:43 | dnolen | seangrove: or overwrite _.isFunction if you can. |
| 16:44 | gfredericks | I guess it means changing how IFn works too? |
| 16:44 | dnolen | gfredericks: no it wouldn't break old projects |
| 16:44 | seangrove | dnolen: It's inside of an anonymous function |
| 16:44 | dnolen | gfredericks: sorry to confuse - I just meant we can't just stop monkeypatching String. If we're going to fix it we need real Keywords & Symbols |
| 16:44 | seangrove | Interop between apps in js is unbelievably bad |
| 16:45 | gfredericks | dnolen: oh gotcha |
| 16:45 | dnolen | seangrove: seriously that implementation of _.isFunction makes no sense. |
| 16:46 | dnolen | seangrove: the whole thing should be replaced w/ typeof check |
| 16:46 | seangrove | dnolen: Yeah, but it is what it is. I'll email them and ask about their reasoning, but they're crazy slow to get back, so I always try to find a way to do it without going through them |
| 16:46 | technomancy | TimMc: the username in that example is Milgrim from https://en.wikipedia.org/wiki/Spook_Country, a book partly about locative art |
| 16:47 | technomancy | who works for Blue Ant and https://en.wikipedia.org/wiki/Hubertus_Bigend |
| 16:48 | dnolen | http://code.google.com/p/closure-library/source/browse/trunk/closure/goog/base.js?r=2#536 |
| 16:48 | dnolen | seangrove: I guess it's a bit more complicated. JS sucks. |
| 16:48 | technomancy | "he wears a suit in the color International Klein Blue which he likes because it is a color that cannot be represented on most computer monitors." |
| 16:49 | seangrove | dnolen: Yeah, I've come to rely on goog.isObject/Function/String/etc. |
| 16:50 | daviddpark | In a leiningen project, is it necessary to add some dependency for java libraries? I am getting "Unable to resolve classname: Properties" error when I attempt to run a repl with code: (ns myproj.core (:import (java.util Properties))) |
| 16:52 | amalloy | daviddpark: no, anything in the java core is already on the classpath |
| 16:52 | amalloy | probably you're running your repl in the user namespace, and so the myproj.core namespace clause doesn't matter |
| 16:53 | dnolen | seangrove: it boggles the mind how there can be so much variance in typeof behavior across JS implementations |
| 16:53 | dnolen | but perhaps it's not well defined in the spec ... |
| 16:55 | seangrove | dnolen: Yeah, it reminds me of this post, which is pretty upsetting http://www.futurealoof.com/posts/balance.html |
| 16:55 | gfredericks | I was about to start hacking on keywords/symbols until I remembered the concern about memory leaks |
| 16:55 | seangrove | "There is a balance to be found between correctness and accessibility and node.js seems to be finding it. Living with JavaScript, and all its faults, seems to have built an understanding in the community that nothing will ever be perfect. By embracing the warts of the language and of various operating systems node.js lives in a harsh reality" |
| 16:55 | gfredericks | I don't remember if there was an alternative approach to interning everything |
| 16:56 | daviddpark | amalloy: I am attempting to interact with system properties, and so need to import java.util.Properties in my leiningen project. The import statement is in the ns declaration since it is in myproj/core.clj |
| 16:56 | brehaut | gfredericks: i *think* that keyword interning now uses weak refs to avoid a space leak |
| 16:56 | gfredericks | brehaut: yes this is wrt cljs where I don't expect weak refs exist |
| 16:56 | brehaut | gfredericks: ah. my bad. |
| 16:57 | gfredericks | would punting on interning work, just having a separate copy like how it works now with strings? As long as hash and eq are defined correctly it'll still work? |
| 16:58 | gfredericks | I would think you could even intern the ones in the source code if that gives any advantages |
| 16:58 | therealadam | I'm trying to wrap my head around ->; it seems like (-> 1 inc #(inc %)) should give me 2 but it bonks trying to cast a symbol |
| 16:59 | seangrove | Yeah, appending: delete String.prototype.apply to the compiled cljs brings rapportive back to life |
| 16:59 | therealadam | what's my misunderstanding? |
| 16:59 | amalloy | ,'(-> 1 inc #(inc %)) |
| 16:59 | seangrove | Wow that was a long and crazy snipe hunt |
| 16:59 | brehaut | gfredericks: i think weakmaps are coming as part of 'Harmony', and mozilla might have an imp? |
| 16:59 | clojurebot | (-> 1 inc (fn* [p1__27#] (inc p1__27#))) |
| 16:59 | brehaut | gfredericks: aha https://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/WeakMap |
| 16:59 | dnolen | seangrove: good to know, I've been wanting to remove that wart from CLJS for a long time - but haven't had time for that particular mid-sized project. |
| 17:00 | amalloy | &(clojure.walk/macroexpand-all '(-> 1 inc #(inc %))) |
| 17:00 | lazybot | ⇒ (fn* (inc 1) [p1__26306#] (inc p1__26306#)) |
| 17:00 | seangrove | dnolen: Well, you have a lot on your plate |
| 17:00 | seangrove | Would love to see source maps too |
| 17:00 | amalloy | therealadam: make sense? |
| 17:00 | seangrove | I think that ticket is probably above my skill level for now though, or I'd go after it |
| 17:00 | dnolen | seangrove: I'm suprised that fixed it, don't you need to replace .call too? |
| 17:00 | therealadam | amalloy: no :( I looked at the macroexpanded version earlier and don't see an obvious problem |
| 17:01 | dnolen | seangrove: oh right, their _.isFunction checks call & apply |
| 17:01 | amalloy | (fn (inc 1) [x] (inc x)) doesn't look at all wrong to you? |
| 17:01 | therealadam | the arglist is out of place? |
| 17:01 | amalloy | there's an (inc 1) in a totally nonsense place |
| 17:02 | therealadam | ahh |
| 17:02 | amalloy | i think you're imagining that -> is function composition |
| 17:02 | amalloy | but it's not; it's a macro that rewrites your forms at the source-code level |
| 17:02 | therealadam | ahhh |
| 17:02 | amalloy | because of which, putting a lambda in generally results in nonsense |
| 17:02 | seangrove | dnolen: There's another call that checks for .call, so deleting that causing Rapportive to be fully healthy again |
| 17:02 | seangrove | Obviously kills my app though |
| 17:03 | bbloom | dnolen: i'll be in town next week, we should get together and try to get the keywords/symbols stuff working. i have an old branch we can use as a guide, but i'd appreciate your expertise in optimizing it |
| 17:03 | seangrove | I think we'll just have to cancel rapportive compatibility with this new release, I don't see much else we can do |
| 17:04 | therealadam | amalloy: so `comp` is for replacing f(g(x)) and `->` is for replacing a(b(c())) ? |
| 17:04 | amalloy | -> is best for functions that take multiple arguments |
| 17:05 | amalloy | (-> x (conj 10) (disj 20)) |
| 18:46 | bbloom | dnolen: well haskell relies on it's type system to eliminate all the thunks, so i don't see why it wouldn't be possible to make it perform comparably on something like v8 |
| 18:47 | bbloom | i dunno what (if any) runtime optimizations modern haskell implementations do |
| 18:51 | dnolen | bbloom: yes I don't see why it couldn't be done, but I would like to see it :) Fay is going down that path but as far as I can tell doesn't do much thunk elimination yet. |
| 18:53 | bbloom | dnolen: the more i experiment with factjor, the more i believe that the haskell approach to isolating side effects (monadic style) is a neat trick but an evolutionary dead end |
| 18:53 | bbloom | dnolen: it makes much more sense to me to figure out how to compose strict and impure programs and use functional abstractions to generate those programs for evaluation |
| 18:54 | bbloom | there are types of stateful operations that have properties that are similar to pure functions.... idempotent operations, for example |
| 18:55 | dnolen | bbloom: that maybe, don't have any opinions yet - just started really digging into Haskell a few days ago. It's fun. |
| 18:56 | ibdknox | the stunted repl made me sad |
| 18:56 | dnolen | ibdknox: heh yes, a lot of file reloading |
| 18:57 | bbloom | agreed, the file reloading is a necessity because 'def is really a side effect |
| 18:57 | dnolen | it's also funny that people complain about Clojure errors, Haskell type errors are pretty cryptic for a beginner as well. |
| 18:57 | ibdknox | dnolen: few people will ever make it to haskell :p |
| 18:57 | bbloom | dnolen: i think that the ppl complaining about clojure errors are mostly people coming from ruby/javascript/java/python |
| 18:57 | ibdknox | in terms of the language funnel |
| 18:57 | technomancy | ocaml compilation errors are pretty good except for the fact that they're translated from french |
| 18:57 | dnolen | technomancy: ha! |
| 18:58 | bbloom | technomancy: lol |
| 18:58 | ohpauleez | hahaha |
| 18:59 | ibdknox | ohpauleez: does your cljs impl of pprint exist somewhere? |
| 18:59 | dnolen | ohpauleez: yeah, what's story w/ that ;) |
| 19:00 | bbloom | ibdknox: i just grepped my fipp project for '\(\.' and got no hits... soo it should be trivial to run on cljs |
| 19:00 | bbloom | :-) |
| 19:01 | ohpauleez | dnolen: ibdknox: I was just walking through it with brenton ashworth a couple weeks ago |
| 19:01 | ohpauleez | I would go with bbloom's fipp if it fits the bill |
| 19:01 | ibdknox | bbloom: oh? I thought I looked at it when you mentioned and there were some classy things in there |
| 19:01 | ibdknox | if not |
| 19:01 | ibdknox | /win |
| 19:02 | ohpauleez | my port was only for the absolutely necessary parts to make the cl-format work |
| 19:02 | bbloom | ibdknox: do you need code-dispatch too? or just simple-dispatch (edn)? |
| 19:02 | ohpauleez | I went back and started porting the rest |
| 19:02 | ibdknox | bbloom: edn is sufficient for now |
| 19:02 | ohpauleez | but it's essentially like porting CL to Clojure |
| 19:02 | ibdknox | ohpauleez: lol yeah, not so much fun |
| 19:03 | ohpauleez | yeah, so I was re-writing parts of it - fipp is pretty close to what I was coming up with |
| 19:03 | ohpauleez | I kept some of the CL stuff |
| 19:03 | bbloom | ibdknox: the only "classy" things in there are in edn.clj which refers to the types from clojure.lang |
| 19:03 | bbloom | you can probably just rename clj to cljs and then rename those 5 or 6 class entries and it would work |
| 19:03 | bbloom | should take 5 minutes & if it takes any longer, let me know & i can tweak it |
| 19:03 | ohpauleez | I'd be more than happy to give people the cl-format piece, but it's probably not what most people want |
| 19:04 | ibdknox | bbloom: awesome. I'll let you know |
| 19:04 | ohpauleez | ibdknox: Yeah, not fun at all haha |
| 19:04 | technomancy | pretty sure cl-format only got into clojure because pprint needed it |
| 19:04 | technomancy | like clojure.walk |
| 19:04 | bbloom | i'm probably not going to do code-dispatch until i decide on some way to do something stylesheet-like |
| 19:04 | ibdknox | I <3 clojure.walk |
| 19:04 | bbloom | i want it to be trivial for people to supply indentation rules and the like for their libraries |
| 19:05 | ibdknox | bbloom: that's also something I would be really interested in at some point :) |
| 19:05 | ibdknox | anyone going to ICSE? |
| 19:05 | bbloom | ibdknox: i'll get to it eventually, it's very low priority now. all i needed was the damn pretty printer to be much much faster for some local diff tests that i'm doing :-) |
| 19:06 | ibdknox | I actually think that'd be useful at the community level |
| 19:06 | technomancy | ISTR clojure.walk has been disowned by its author? |
| 19:06 | ibdknox | it's one thing I thought they did very nicely for Go |
| 19:06 | bbloom | i also want to pretty print other stuff, like CSS or whatever |
| 19:06 | technomancy | not that it's bad from a user perspective; just the implementation |
| 19:07 | bbloom | and i'd also like colored output and other niceties |
| 19:07 | ohpauleez | technomancy: Yeah, those libs are pretty terrible, even for CL-style code |
| 19:07 | bbloom | but all that stuff is queued up behind real work ;-) |
| 19:07 | ibdknox | lein format would be nice :) |
| 19:08 | ibdknox | damn priorities ;) |
| 19:08 | bbloom | ibdknox: yeah it would :-) |
| 19:08 | technomancy | bbloom: wait, does yours work in a comment-preserving fashion? |
| 19:08 | technomancy | I thought only sjacket did that? |
| 19:09 | bbloom | technomancy: i don't have a parser of any kind |
| 19:09 | bbloom | technomancy: that's another reason i haven't done code-dispatch |
| 19:09 | ibdknox | technomancy: it probably wouldn't be too hard to add comment preservation to blind |
| 19:10 | bbloom | i want to be able to re-use the formatting rules for data-structures->pretty-printed as well as string-or-file->ast->pretty-printed |
| 19:11 | bbloom | i need some time to think about how to do stylesheets. it needs to 1) be data 2) be easy to create new styles 3) compose cleanly 4) perform well during printing |
| 19:14 | bbloom | ibdknox: what are your pretty printing needs for LT? |
| 19:14 | ibdknox | CLJS results right now :) |
| 19:15 | bbloom | ibdknox: ie repl results? |
| 19:15 | ohpauleez | ibdknox: Strict edn? |
| 19:15 | pbostrom | does anyone run lein on an amazon ec2 micro instance? it seems like it takes up to 10-15 minutes to start up, but ec2 small instances run fine, I'm wondering if there's something I need to tweak, I've tried a few -Xmx and -Xms opts in vain |
| 19:15 | ibdknox | ohpauleez: it may contain non-printable things that could be [object object] or whatnot, but yeah more or less |
| 19:15 | ibdknox | bbloom: more or less, yes |
| 19:16 | bbloom | ibdknox: so i assume you need controls like depth, item limits, etc ? fipp doesnt do that yet |
| 19:18 | ibdknox | bbloom: at some point those things would be nice, but there are other ways for me to deal with that in the mean time :) |
| 19:18 | ibdknox | meantime* |
| 19:19 | bbloom | ibdknox: heh, mental image of an angry clock |
| 19:19 | ibdknox | haha |
| 19:20 | bbloom | ibdknox: both of those things should be relatively easy to add, but again, i was waiting until i thought about stylesheets b/c i want those things to be stylable |
| 19:20 | bbloom | ibdknox: ie argument lists are vectors, but they should never be elided if you set the list print limit to 6 or whatever |
| 19:20 | ibdknox | makes sense |
| 19:21 | bbloom | ibdknox: we probably have a lot of stuff in common... i think it's possible that I'm gonna be building the Blend to complement your Visual Studio, heh |
| 19:22 | bbloom | lots of *needs* in common, in terms of components, that is |
| 19:22 | ibdknox | yeah probably :) |
| 19:23 | seangrove | bbloom: What're you building? |
| 19:24 | cheezey | all right guys |
| 19:24 | cheezey | oops wrong channel |
| 19:37 | seangrove | bbloom: Well, I suppose I'll see it when I see it then :) |
| 19:40 | bbloom | interestingly, angular does a fair amount metaprogramming to achieve optimal performance. There are places where they call Function(...) with a string of code |
| 19:55 | seangrove | bbloom: Are you using angular from cljs? |
| 19:56 | bbloom | seangrove: no, i'm just studying it |
| 19:56 | bbloom | i've used it from coffeescript |
| 19:57 | seangrove | Yeah, I've heard good things about it, but haven't thought much about how it would fit in the cljs world |
| 19:58 | seangrove | I hate debugging javascript in firefox, it's such a bad experience: http://dl.dropbox.com/u/412963/Screenshots/a-.png |
| 20:01 | SegFaultAX | seangrove: In fairness, javascript can be painful to debug in general. :) |
| 20:01 | seangrove | SegFaultAX: True, and this is with the caveat that I've sworn off IE as a target at all for now |
| 20:02 | seangrove | So I suppose it gets worse |
| 20:02 | SegFaultAX | I find the browser that gives me the most trouble is usually opera. |
| 20:03 | SegFaultAX | I think it's because they are more "standards-nazis" than the other vendors. |
| 20:03 | SegFaultAX | Although I definitely don't do a lot of javascript development day-to-day, so that could just be my suckiness. |
| 20:05 | bbloom | callbacks are the real source of hard to track bugs |
| 20:06 | kovas | I'm getting into angular these days |
| 20:06 | kovas | my theory re: cljs is |
| 20:06 | kovas | that its all about defining the directives, rather than the controllers |
| 20:07 | kovas | defining the directives using js is a pretty shitty experience |
| 20:07 | kovas | but we can do a lot better |
| 20:11 | bbloom | kovas: you gonna be at clojure/west ? we can talk about what "better" looks like |
| 20:11 | kovas | bbloom: yup will be there |
| 20:11 | kovas | bbloom: my immediate concept of better is: macros |
| 20:12 | kovas | bbloom: that eliminate the 100 ways to shoot yourself in the foot |
| 20:12 | bbloom | heh |
| 20:12 | kovas | bbloom: have you seen the angular videos |
| 20:12 | kovas | ? |
| 20:12 | bbloom | i'm thinking bigger :-) |
| 20:12 | bbloom | no, which videos? |
| 20:12 | kovas | bbloom: its basically one example of a gotcha after another |
| 20:12 | bbloom | kovas: link? |
| 20:12 | kovas | one sec |
| 20:13 | kovas | http://www.youtube.com/watch?v=WqmeI5fZcho&list=UUbn1OgGei-DV7aSRo_HaAiw |
| 20:13 | kovas | http://www.youtube.com/watch?v=iB7hfvqyZpg |
| 20:13 | kovas | i mean, i give them a ton of credit for understanding the problems |
| 20:13 | bbloom | kovas: sheesh, long videos :-P but definitely a topic i'm interesting in, so i'll probably get around to watching them at some point |
| 20:13 | kovas | but making JS do the things they want is a feat |
| 20:13 | kovas | yeah |
| 20:14 | kovas | bbloom: in terms of doing better, they are an enumeration of the flaws |
| 20:14 | kovas | bigger is better |
| 20:14 | kovas | but its hard to see the bigger picture when bogged down in all the incidental complexity |
| 20:15 | bbloom | kovas: in your opinion, what are the primary sources of incidental complexity? |
| 20:15 | bbloom | at the directive level, that is |
| 20:16 | kovas | bbloom: the way scope is set up is kindof a mess |
| 20:16 | kovas | bbloom: since they can't introduce a higher level language construct |
| 20:16 | SegFaultAX | So is Backbone.js dead? |
| 20:16 | SegFaultAX | (And did Angular kill it?) |
| 20:16 | bbloom | SegFaultAX: it's not dead, it's just a simpler tool for smaller problems |
| 20:17 | bbloom | SegFaultAX: backbone is great for a few rich components on top of a REST API |
| 20:17 | bbloom | SegFaultAX: but it always has been woefully inadequate for large apps |
| 20:17 | talios | brehaut: nice blog post :) one thought tho - an HttpRequest and DatabaseRecord are still types, mostly modelled as maps with extras, so you can still do static typing there - maybe not CustomerRecord tho |
| 20:18 | kovas | being able to define your own tags always seemed like the missing thing to me |
| 20:18 | bbloom | kovas: i agree that the scopes are complex. i think it's mainly an attempt to preserve the javascript mutable getter/setter experience for working with models |
| 20:18 | bbloom | kovas: which is more pleasant than the model.get('prop') approach |
| 20:19 | kovas | bbloom: i think conceptually they are doing the right thing, its just the expression of the concept that is a disaster |
| 20:19 | bbloom | kovas: i wouldn't call it a disaster |
| 20:19 | kovas | watch the videos :) |
| 20:19 | bbloom | i will :-) |
| 20:19 | brehaut | talios: thanks. the bit i glossed over is that if your code is marshalling from HttpRequest to DatabaseRecord with only a tiny bit of logic in the middle (ie from roughly two different Universal types), theres boiler plate you gain is traded off against everything else |
| 20:19 | bbloom | kovas: my goal is to have the "scope hierarchy" be a single immutable data structure and that it's accessed via update-in or assoc-in etc |
| 20:19 | kovas | I'm gonna watch them again and take notes. theres about 10-15 wacky things |
| 20:20 | bbloom | so you bind to paths |
| 20:20 | bbloom | i think it will enable pretty fast dirty checking too, since we have fast equality for our data structures |
| 20:20 | talios | brehaut: true, but if you're mapping directly from request->database query, are you not also walking into a Ruby On Rails style security f**k up? ( potentially ) |
| 20:20 | kovas | bbloom: that would be pretty cool. i spent a lot of time last summer trying to do something similar but couldn't figure it out |
| 20:21 | bbloom | kovas: it's a really hard problem, but i have some cool stuff actually working |
| 20:21 | kovas | bbloom: awesome |
| 20:21 | bbloom | kovas: i feel like i wouldn't have been able to pull it off if i didn't have the very particular (and very unlikely) collection of past professional experiences :-P |
| 20:22 | kovas | bbloom: is it the times that make the man, or the man that makes the times |
| 20:22 | brehaut | talios: i dont disagree that there is potential for bugs. i would however be leary of any system that pushes all security concerns to the type system |
| 20:23 | kovas | bbloom: my pov is that if you can crack the directives, you can then program them to fit with clojure datastructures |
| 20:23 | kovas | bbloom: rather than the other way around |
| 20:24 | kovas | bbloom: also if you have a nice high-level directive language, thats interesting to everyone doing angular dev |
| 20:24 | bbloom | kovas: well, my though is that there are really multiple classes of directives |
| 20:24 | brehaut | talios: tbh, i think the bigger issue with not having static types is that systemic changes over the long term can be harder |
| 20:24 | talios | brehaut: depending on how you model it, if you did (let [db-record (map request db-func)] ...) you can still type shift/validate/sanitize there, or it could just return a modified/restructured map |
| 20:24 | bbloom | kovas: there are those that work with the dom and then there are higher level ones that operate in the domain of applications |
| 20:24 | bbloom | s/though/thought/ |
| 20:25 | brehaut | talios: oh absolutely, not validating and sanatizing the data would be mental |
| 20:25 | kovas | what would be an example of the latter? |
| 20:25 | bbloom | kovas: i expect that a macroexpand-like behavior for templates/views/whatever can be leveraged to mean that writing "directives" is often really simple, unless you need to directly interface with the dom |
| 20:25 | talios | brehaut: true, the counter to that is you get fast-fail of API breakages - if/when you break APIs. if you silently change a map structure, you leaving that to the hope that someone else also has tests covering it, not only you having tests |
| 20:25 | bbloom | kovas: examples of non dom interacting directives? |
| 20:25 | kovas | yeah |
| 20:25 | bbloom | basically anything that doesn't need to, itself, bind event handlers |
| 20:26 | brehaut | talios: thats exactly what im saying. |
| 20:26 | bbloom | you need some higher level concepts that are missing from angular currently |
| 20:26 | kovas | but if they bind data, they are also interacting with the dom right |
| 20:26 | bbloom | kovas: not directly |
| 20:26 | bbloom | consider, Triggers in WPF for example: |
| 20:26 | talios | brehaut: nah, I 1/2 read your line :) |
| 20:26 | bbloom | kovas: http://wpftutorial.net/Triggers.html |
| 20:27 | talios | brehaut: lack of typing is good to starting up, getting going, but on the long term I'm not so sure. |
| 20:27 | bbloom | kovas: that sort of stuff can be expressed *abstractly* and different backends can be provided |
| 20:27 | talios | brehaut: overheard a conversation here yesterday about naming, and about clojures re-match functions etc. etc. if you're prepending function names with type information, you may as well have types :) |
| 20:27 | kovas | ok, i think i understand |
| 20:28 | bbloom | talios: those name prefixes also help in reading and understanding |
| 20:28 | talios | true |
| 20:28 | bbloom | talios: types aren't necessarily apparent at the call site |
| 20:28 | bbloom | names, generally, are |
| 20:29 | kovas | bbloom: by abstractly, you mean as a protocol, as a element tag, or as something else? |
| 20:29 | bbloom | kovas: something else |
| 20:29 | bbloom | kovas: i'm separating directives into two concepts: properties and passes |
| 20:29 | kovas | bbloom: a pass is some metaprogramming transform? |
| 20:29 | bbloom | kovas: pretty much |
| 20:30 | kovas | cool |
| 20:30 | bbloom | kovas: the premise is that you have a schema that defines facts about properties. how to validate them, how to compose them, how they are inherited via hierarchy or via templating, etc |
| 20:30 | kovas | yeah, the interaction between directives seems like one of the under defined aspects of angular |
| 20:30 | bbloom | kovas: then you define passes, which effectively macro expand properties until you get properties in terms of the target platform |
| 20:31 | kovas | interesting |
| 20:31 | bbloom | and once you have that data structure in the fully expanded form, you need a runtime to operate on it |
| 20:31 | bbloom | and that runtime is what does the real event binding |
| 20:31 | kovas | right |
| 20:31 | bbloom | and each pass captures its inputs and outputs, such that expansion can be resumed at any point in the transformation |
| 20:32 | bbloom | so that you can efficiently re-expand only the bits that have chnaged |
| 20:32 | kovas | at runtime? |
| 20:32 | bbloom | yup |
| 20:32 | kovas | thats great |
| 20:32 | bbloom | i'm excited about it :-) |
| 20:32 | bbloom | it's A LOT OF WORK to get it all designed right |
| 20:32 | kovas | symbolic programming FTW |
| 20:32 | bbloom | been working on it for months |
| 20:32 | bbloom | i've got about 2,000 lines of production quality code haha |
| 20:32 | bbloom | getting all the abstractions right is really difficult |
| 20:32 | kovas | no doubt |
| 20:33 | kovas | github that baby :) |
| 20:33 | bbloom | kovas: you worked at wolfram for a while, right? |
| 20:33 | kovas | bbloom: yup |
| 20:33 | bbloom | i'll open source it eventually :-) |
| 20:34 | bbloom | kovas: symbolic everything, huh? haha |
| 20:34 | kovas | symbolic all the things |
| 20:34 | bbloom | yeah, i'm becoming a big believer in that |
| 20:34 | kovas | recursive substitution is powerful |
| 20:34 | bbloom | i'm not really sold on rewrite systems though, although they make a ton of sense for algebraic systems |
| 20:35 | kovas | rewrite systems will never perform like function calls |
| 20:35 | bbloom | yeah, it's recursive substitution, but not generalized pattern matching & rewrites |
| 20:35 | kovas | but i truly believe its a higher level paradigm |
| 20:35 | bbloom | each "pass" has a special set of behavior for substitution and for delegating to the next pass |
| 20:35 | kovas | interesting |
| 20:36 | kovas | i've been thinking a lot about how to do that in clojure |
| 20:36 | bbloom | after i write a whole bunch of passes, i'll see what i can do about a more generalized rewrite mechanism for making it easier to create passes |
| 20:36 | kovas | is that something that happens in your concatenate language, or in this unpublished library? |
| 20:36 | bbloom | i've only got 6 or so passes right now and they are pretty different |
| 20:36 | bbloom | unpublished |
| 20:36 | kovas | thats interesting stuff |
| 20:37 | kovas | seems relevant for the cljs compiler as well |
| 20:37 | bbloom | the concatenative library is being used in the platform-specific runtime layer, not in the expansion/substitution system |
| 20:37 | kovas | i see |
| 20:37 | kovas | is it all about core.walk? |
| 20:37 | bbloom | yeah, i think the approach is generally applicable: in theory the tree being expanded could be something like an AST. if you can capture the inputs you could incrementally recompile |
| 20:38 | bbloom | but i'm focused on user interfaces for v1 |
| 20:38 | kovas | by capturing the inputs, you mean caching them and associating with the output? |
| 20:38 | bbloom | yes |
| 20:38 | bbloom | which is what i need to do for performant data binding |
| 20:38 | kovas | so this is like recursive substitution & dynamic recomputation |
| 20:38 | bbloom | precisely what it is |
| 20:39 | bbloom | i assume mathematica does all that internally :-) |
| 20:39 | kovas | mathematica takes the easy way out |
| 20:39 | kovas | you tell it what the recompilation points are explicitely |
| 20:39 | bbloom | re-expand/substitute from the root? |
| 20:39 | kovas | with Dynamic[] |
| 20:39 | bbloom | ah, i see |
| 20:40 | kovas | its powerful, but still a hack |
| 20:40 | kovas | it only applies to rendered content, rather than to general expressions |
| 20:40 | bbloom | the goal is: model <-> view-model <-> view <-> platform |
| 20:40 | bbloom | where view-model == angular scopes basically |
| 20:40 | bbloom | and model is optional for really simple systems |
| 20:40 | kovas | right |
| 20:40 | bbloom | and the <-> arrows express two way communication |
| 20:41 | bbloom | and it's intentionally linear |
| 20:41 | kovas | linear? |
| 20:41 | bbloom | ie platform doesn't talk to view-model |
| 20:41 | bbloom | it talks through view |
| 20:41 | bbloom | it's a bidirectional pipeline, but it's a pipeline, not a cyclic system |
| 20:41 | kovas | what is the platform in the case of the browser |
| 20:42 | kovas | is it the dom? |
| 20:42 | bbloom | yes |
| 20:43 | kovas | nice. well I'm glad this is getting solved without me doing the work :) |
| 20:43 | bbloom | haha |
| 20:43 | bbloom | it's complex stuff, but it's fun |
| 20:44 | bbloom | my hope is that i can build a pretty bitching UI toolkit with this, but you're right, this could be even more broadly applicable |
| 20:44 | kovas | the symbolic substitution is definitely a general tool |
| 20:45 | kovas | i won't be totally happy with clojure until we have that |
| 20:45 | kovas | but UI is the immediate need |
| 20:45 | kovas | I'm dying here |
| 20:45 | bbloom | kovas: ha! yeah, my stuff would hopefully be very useful for session |
| 20:45 | bbloom | i think that UI is an immediate need in general |
| 20:45 | bbloom | it's sorta like an unsolved problem |
| 20:45 | kovas | i just started rewriting session in angular |
| 20:45 | bbloom | it's just *fucking hard* |
| 20:46 | kovas | yup |
| 20:46 | bbloom | that's a bummer, but understandable |
| 20:46 | kovas | thats the bottleneck right now |
| 20:46 | bbloom | hmm, are you NYC based too? |
| 20:46 | kovas | i think its just gonna take a weekend. (famous last words) |
| 20:46 | kovas | for another week or so |
| 20:46 | kovas | then i move to bay area |
| 20:46 | kovas | where are you? |
| 20:47 | bbloom | heh, aw, we'll just miss each other. i'm moving to NYC next week :-) |
| 20:47 | kovas | I'm gone on the 1st |
| 20:47 | kovas | same deal? |
| 20:48 | bbloom | nah, like 29th ha, but i'll be pretty busy the first few days |
| 20:48 | kovas | no doubt |
| 20:50 | kovas | bbloom: are you gonna release this b4 clojure west? |
| 20:50 | bbloom | kovas: unlikely, but i'll probably have something to demo there |
| 20:51 | kovas | bbloom: ok, i will continue my rewrite then ;) |
| 20:51 | bbloom | haha |
| 20:51 | bbloom | kovas: please keep some notes & share them with me, i'm curious how it goes |
| 20:53 | akhudek | bbloom: that sounds very interesting. Looking forward to learning more! |
| 20:54 | kovas | wiill do |
| 20:55 | bbloom | akhudek: i'll be sure to make lots of noise about it when it's ready to show off :-) |
| 20:56 | kovas | bbloom: i suggest doing that prior to the conf |
| 20:56 | ibdknox | bbloom: we should talk again |
| 20:56 | kovas | bbloom: lets other announcements suck up the oxygen |
| 20:56 | kovas | lest |
| 20:56 | ibdknox | bbloom: because I'm thinking even bigger I believe ;) |
| 20:57 | bbloom | ibdknox: free free to talk here or msg me |
| 20:58 | bbloom | kovas: i don't expect to have anything to announce or release until some time after the conference |
| 20:59 | bbloom | ibdknox: what's "bigger"? :-) |
| 20:59 | ibdknox | a different programming paradigm :) |
| 20:59 | gdev | what's going on? |
| 20:59 | bbloom | ibdknox: heh, i'm not quite there yet. one step at a time :-P |
| 21:00 | AtKaaZ | where are the logs? cause sounds interesting |
| 21:00 | akhudek | bbloom: any similarity to http://goo.gl/lIOWF |
| 21:00 | bbloom | http://clojure-log.n01se.net/ |
| 21:00 | akhudek | ? |
| 21:00 | kovas | I'm pretty convinced symbol rewriting is the simplest programming paradigm possible |
| 21:00 | AtKaaZ | thanks;) |
| 21:00 | kovas | and pretty ideal for working with on e.g. an ipad |
| 21:01 | bbloom | akhudek: i'll take a peek at that paper, give me a sec |
| 21:01 | ibdknox | kovas: example? |
| 21:01 | ibdknox | what I've been thinking (and prototyping) is also ideal for an ipad |
| 21:02 | akhudek | different application, but some of your descriptions above sounded similar to basic technique |
| 21:02 | kovas | ibdknox: i'm thinking about a simplified version of the mathematica language |
| 21:02 | bbloom | ibdknox: i figure that declarative UIs in edn is a reasonable starting point & that the implementation is totally secondary to getting the abstractions right |
| 21:02 | bbloom | ibdknox: if you magically come up with another programming paradigm that lets me get the same behavior and perf with less code, i'll be happy to evaluate it :-) |
| 21:03 | kovas | ibdknox: something like scratch, but far more powerful |
| 21:03 | bbloom | akhudek: i don't really have time to dig into this paper now. is there something in particular you thought paralleled what i'm talking about? |
| 21:04 | kovas | ibdknox: if the UI is represented symbolically, then you can see the substitutions in code simultaneously with their visual interpretation |
| 21:04 | gdev | sounds like light table |
| 21:04 | bbloom | kovas: and you can provide single-step debugging of the expansion process :-) |
| 21:04 | ibdknox | kovas: yep, I'm making that work |
| 21:04 | bbloom | expansion -> substitution |
| 21:04 | kovas | ibdknox: aww yeah |
| 21:04 | bbloom | i guess it can *shrink* not just expand, but 90% of the time it expands haha |
| 21:05 | akhudek | the basic idea there is to compile a query by a sort of step-wise graph expansion. You stop expanding when you've mapped the input concepts to the target concepts. |
| 21:05 | akhudek | that's a gross simplification, but sounded a lot like what you were describing with passes |
| 21:05 | bbloom | heh, that's an interesting parallel to a thought discussed in IRC a week ago or so: reducers don't always reduce, sometimes they expand: ie mapcat |
| 21:05 | bbloom | and similarly, macroexpand doesn't always expand |
| 21:06 | bbloom | ,(macroexpand '(-> 1)) |
| 21:06 | clojurebot | 1 |
| 21:06 | bbloom | :-) |
| 21:06 | bbloom | substituters and macrosubstitute doesn't really have the same ring to them |
| 21:07 | kovas | yeah I've been struggling with good names for that as well |
| 21:07 | bbloom | akhudek: yeah, that's what i'm describing, but that's similar to any symbolic program... in particular: compilers |
| 21:07 | kovas | the words are hopelessly overloaded |
| 21:08 | bbloom | names are fucking hard |
| 21:08 | bbloom | that's why haskell people just give up and pick some symbols |
| 21:08 | bbloom | heh |
| 21:08 | akhudek | bbloom: yes, though the devil is always in the details. :-) Proving that you've genuinely achieved a correct mapping under your constraints is the hard part. |
| 21:09 | brehaut | yup, its one of the two hard problems, along with cache invalidation and off by one errors |
| 21:09 | akhudek | nevermind the graph search problem itself |
| 21:10 | bbloom | akhudek: luckily, there is no *correct* mapping in UIs |
| 21:10 | ibdknox | kovas: this is a relatively new endeavor, but I was hoping to maybe demo something at the liveprogramming workshop: http://liveprogramming.github.com/2013/ |
| 21:10 | bbloom | akhudek: consistency is more important |
| 21:10 | bbloom | akhudek: as long as the expansion process is clear, understandable, consistent, and produces testable output, then the developer can tweak until they get a UX they like |
| 21:11 | bbloom | akhudek: unlike queries, which are being optimized, there is no consistent output |
| 21:11 | kovas | ibdknox: cool. I'm gonna hit that up |
| 21:11 | bbloom | ibdknox: can you give a couple sentence overview? |
| 21:13 | akhudek | Interesting. Still looking forward to seeing what you've cooked up. :-) |
| 21:14 | ibdknox | bbloom: your program as a datastructure ;) Basically what would a truly declarative approach to building *real* software look like? And more interestingly, what does that allow you to do with tools? |
| 21:14 | bbloom | ibdknox: very cool. it's definitely something i have extreme interest in |
| 21:14 | kovas | if you program is declarative, that makes it a lot more trivial to share |
| 21:14 | craigbro | van roy? haridi? |
| 21:14 | ibdknox | the demo I was thinking of for ICSE is building todoMVC |
| 21:15 | ibdknox | on a touch screen :) |
| 21:15 | craigbro | am I correct to think you mean something other than declartive programming? |
| 21:15 | bbloom | ibdknox: HA! I have a (mostly) working todoMVC |
| 21:15 | bbloom | it seems we are playing in the same sandbox :-) |
| 21:15 | bbloom | my thought is that declarative programming for real software is strictly harder than declarative UI, and real tools need real UI |
| 21:16 | bbloom | in the chicken and egg cycle, one of us has chosen the chicken and the other has chosen the egg, ha |
| 21:16 | bbloom | i also have a pong game :-) |
| 21:16 | ibdknox | I agree, though I think there's an underlying solution that actually addresses both |
| 21:16 | bbloom | ibdknox: i think that underlying solution is symbolic expansion |
| 21:16 | kovas | declarative UI quickly devolves into declarative programs |
| 21:16 | kovas | you need to save the state somewhere, first of all |
| 21:17 | ibdknox | kovas: yeah, that's what I ran into |
| 21:17 | kovas | ibdknox: i gave up until datomic free came out |
| 21:17 | bbloom | kovas: nah, you can isolate that into "commands" where the declarative bit is only what named command (1) to execute on what path in the state data structure (2), with what arguments (3) |
| 21:17 | ibdknox | bbloom: any reading you can suggest on symbolic expansion? |
| 21:17 | bbloom | ibdknox: install mathematica :-P |
| 21:17 | kovas | +1 |
| 21:18 | ibdknox | why don't we use mathematica for everything? |
| 21:18 | bbloom | b/c it is largely backwards compatable with v1 |
| 21:19 | bbloom | looong before persistent data structures were common place :-) |
| 21:19 | ibdknox | but you think they've solved the underlying problem? |
| 21:19 | kovas_ | its slow and proprietary |
| 21:19 | bbloom | no, i think that mathematica is the best known example of symbol substitution |
| 21:19 | bbloom | and hence mathematica is worth studying |
| 21:19 | craigbro | commercial example... |
| 21:19 | kovas_ | and doesn't have the abstractions that go down to the platform |
| 21:19 | ibdknox | got it |
| 21:20 | craigbro | matlab |
| 21:20 | bbloom | this topic is extremely interesting to me, but sadly, i gotta run |
| 21:20 | kovas_ | ibdknox: if you implement Manipulate, that will be considered a heroic act |
| 21:21 | kovas_ | later! |
| 21:21 | bbloom | Manipulate is super cool |
| 21:21 | bbloom | kovas_: & ibdknox: we should all definitely get together and talk about this the next time i'm in the bay area |
| 21:21 | kovas_ | would love to |
| 21:21 | ibdknox | sure thing |
| 21:22 | ibdknox | kovas_: as in turning values into sliders and such? That's manipulate? |
| 21:22 | craigbro | present/ |
| 21:22 | craigbro | accept |
| 21:22 | kovas_ | ibdknox: theres maybe 3 aspects |
| 21:22 | craigbro | seperates presentation types from data types |
| 21:22 | kovas_ | ibdknox: first is auto-generating an interface that is relevant to the parameters being manipulated |
| 21:22 | craigbro | is in effect a declarative layer sitting on top of a procedural layer for UI |
| 21:23 | kovas_ | ibdknox: second is rendering values as UI without any intermediate nonsense |
| 21:23 | craigbro | CLIM was totally baroque tho |
| 21:23 | kovas_ | ibdknox: third is the dynamic recomputation |
| 21:23 | ibdknox | got it |
| 21:23 | ibdknox | well |
| 21:24 | ibdknox | from watching these couple videos and from what you guys are saying, that sounds like what I intended to be able to do |
| 21:24 | ibdknox | lol |
| 21:24 | ibdknox | I prototyped an engine for this stuff this weekend, just really simple stuff |
| 21:25 | ibdknox | working on what primitive notions you need to build the vast majority of programs |
| 21:25 | kovas_ | sweet |
| 21:25 | kovas_ | what are the primitives? |
| 21:27 | ibdknox | I've been thinking of it as a system that has two things in it |
| 21:28 | ibdknox | you need to define the "things" in your program - objects |
| 21:28 | ibdknox | and then you need to define the relationships between them |
| 21:29 | ibdknox | the things in your program are sinks for IO basically |
| 21:29 | kovas_ | this is for all programs, or mainly UI-driven ones? |
| 21:29 | kovas_ | ok |
| 21:29 | ibdknox | I've been primarily thinking about the entire web stack, which encompasses both UI and non-UI things |
| 21:30 | ibdknox | I was focusing on figuring out the types of relationships that exist, because I think there are very very few |
| 21:30 | kovas_ | are the relationships constraints, or rules for evolution |
| 21:31 | ibdknox | more akin to constraints I think |
| 21:31 | ibdknox | though again, this is a first pass |
| 21:31 | kovas_ | how do you make it run? |
| 21:32 | ibdknox | feed the datastructure into the (run ...) function, of course ;) |
| 21:32 | kovas_ | right :) |
| 21:32 | ibdknox | every program has to have some entry point, something that kicks it off |
| 21:32 | craigbro | really? |
| 21:32 | kovas_ | but in terms of turning constraints into updates i mean |
| 21:32 | craigbro | could just start a listener |
| 21:32 | ibdknox | craigbro: then the thing that kicks it off is that listener firing |
| 21:33 | ibdknox | bind your listener in run |
| 21:33 | ibdknox | and wait |
| 21:33 | craigbro | the litener need not be part of the program |
| 21:33 | akhudek | this sounds exactly like the project I've been part of for the last two years at UW, complete with IO black boxes. It's not an easy problem to solve, especially update. |
| 21:33 | ibdknox | kovas_: delayed binding of listeners |
| 21:33 | craigbro | if my program is a combination of a data structue, some more declaration of how to dispaly aspects of it etc.. |
| 21:34 | ibdknox | craigbro: I'm not sure I understand what you mean by the listener need not be part of the program. Can you give a concrete example? |
| 21:34 | craigbro | an html page |
| 21:35 | ibdknox | an html page runs |
| 21:35 | ibdknox | on load |
| 21:35 | craigbro | the browser runs it |
| 21:35 | craigbro | the onload in this case is a procedure description |
| 21:36 | kovas_ | ibdknox: so what are the identified relationships so far? |
| 21:36 | ibdknox | push, associate, and update |
| 21:36 | craigbro | but, this semantic distinction is, an aside |
| 21:37 | craigbro | another example would be a NetLogo program |
| 21:37 | kovas_ | is delete a special case of update? |
| 21:37 | craigbro | it's a blob of code, and a description of a UI |
| 21:37 | craigbro | no code is run until a user clicks on a button that calls something |
| 21:37 | ibdknox | kovas_: update can send messages |
| 21:38 | kovas_ | ibdknox: how is it different from _just_ sending messages? |
| 21:38 | craigbro | this distition of what is inside and outside the program is important when you want the program to run in lots of different contexts |
| 21:39 | craigbro | the same netlogo model can be run interactively, or run in the "lab" which will run in N times where N is the number of combinations of different parameters you tell the lab to run it with |
| 21:39 | ibdknox | kovas_: what are you referring to with "it" |
| 21:40 | kovas_ | ibdknox: update |
| 21:42 | ibdknox | kovas_: it depends on how you define the end points, but fundamentally it's a form of message passing |
| 21:43 | ibdknox | kovas_: update is a triggered push |
| 21:43 | ibdknox | a push relationship keeps all dependents in sync automatically |
| 21:44 | ibdknox | craigbro: that's just a property of the runner though, right? |
| 21:44 | kovas_ | ibdknox: i see. and assoc? |
| 21:45 | kovas_ | ibdknox: does that change the topology or something? |
| 21:45 | ibdknox | kovas_: you need a way to say that this thing has a copy of something |
| 21:45 | ibdknox | kovas_: each todo needs its own copy of a representation that is bound correctly and such |
| 21:45 | kovas_ | right |
| 21:46 | kovas_ | so assoc is for inserting identities, push is for inserting values. is that the idea? |
| 21:46 | ibdknox | yep |
| 21:46 | kovas_ | nice |
| 21:47 | ibdknox | very early still, but with just those, you can get surprisingly far |
| 21:47 | kovas_ | is update a pure function? |
| 21:47 | ibdknox | all pure functions |
| 21:48 | craigbro | ibdknox: Dclarative UIs are all about where you draw the distinction between the program, and the container, or "runner" |
| 21:48 | kovas_ | so the contract is update produces new state that you can perceive and hang out to (rather than arbitrary side effects) |
| 21:48 | craigbro | ibdknox: HTML is a perfect example of a declarative UI, which can do all kinds of things, even without js |
| 21:48 | ibdknox | kovas_: I think that's how it's going to play out |
| 21:49 | kovas_ | sounds pretty clean |
| 21:49 | craigbro | ibdknox: but I'm not so sure the point I'm making is germane to your experiment, or in any way a "revelation" in regards to it |
| 21:50 | ibdknox | craigbro: haha :) My thought is that I don't want to think about the container if I don't have to |
| 21:50 | craigbro | ibdknox: where cootainer is your mishmash of procedural/functional jQuery and clojurescript to make the pixels on the screen? |
| 21:50 | ibdknox | the completely ridiculous demo I want to do is to by changing one of the directives in my todoMVC it goes from a completely local (just an HTML page) program to spinning up a server and running remotely serving that and communicating changes back |
| 21:52 | kovas_ | hmm |
| 21:52 | kovas_ | that would be impressive |
| 21:52 | ibdknox | I agree - now to make it work :) |
| 21:52 | kovas_ | but its hard to know what conclusion to draw from that in terms of general capabilities |
| 21:53 | kovas_ | or is the point really the easy transition between client and server |
| 21:53 | ibdknox | no, more that it's able to figure that out |
| 21:53 | ibdknox | what do you think would show the more general capabilities? |
| 21:53 | kovas_ | by directive you mean like html tag? |
| 21:54 | ibdknox | I have a collection of todos, I change a piece of metadata on it from :local to :remote |
| 21:54 | kovas_ | i see |
| 21:54 | kovas_ | ok, that would be pretty sweet |
| 21:55 | ibdknox | basically that transition would cause a near complete rewrite in the normal case |
| 21:55 | kovas_ | right |
| 21:55 | ibdknox | because no matter how hard you try you must take architectural dependencies |
| 21:55 | ibdknox | but if you stop saying "how" and start saying "what" it doesn't matter |
| 21:55 | ibdknox | the architecture is decided JIT |
| 21:56 | kovas_ | right |
| 21:57 | kovas_ | interesting compilation problem |
| 21:57 | craigbro | CLIM again 8^) |
| 21:57 | kovas_ | do you have to analyze it at the source code level? |
| 21:58 | craigbro | (present my-todo-lisp 'todo-presentation-type +swing+) |
| 21:58 | ibdknox | haha |
| 21:59 | craigbro | (present my-todo-lisp 'todo-presentation-type (merge +htmlserver+ {:base-url "/todo" :authhandler (reify...)) |
| 21:59 | ibdknox | kovas_: I haven't thought too far down how that level of transformation will work yet :) |
| 21:59 | craigbro | to handle events you have input and output streams that read/write presentation records |
| 22:00 | ibdknox | but you have complete information, I believe it's possible |
| 22:00 | kovas_ | ibdknox: i imagined it as tagged literals rather than metadata. then its easy to bind the interpretation. but TLs not great for code-like things. |
| 22:00 | craigbro | i have a lightweight presentation system we use for our web apps, that renders to just a hiccup view |
| 22:01 | craigbro | metadata is a pain in the ass |
| 22:01 | craigbro | especially if you do symbolic operations on your data |
| 22:02 | kovas_ | what kind of operations? |
| 22:02 | craigbro | eq? |
| 22:02 | clojurebot | @ splices in a seq and foo# is a symbol, not a seq |
| 22:02 | craigbro | hehe |
| 22:03 | kovas_ | because it ignores metadata? |
| 22:03 | craigbro | for example, i tagged some symbol names for one data type with metadata |
| 22:03 | craigbro | I always have to go back to the original symbol object to get the metadata |
| 22:05 | kovas_ | i see. |
| 22:05 | kovas_ | you want them to be more like vars then |
| 22:05 | clojurebot | your idea of vars, symbols, and scoping is wackadoodle |
| 22:05 | craigbro | it gets to be a pain when you are doing thigns like spitting stuff out to a file |
| 22:05 | craigbro | and reading it back in |
| 22:06 | kovas_ | because every instance of the symbol is a distinct entity |
| 22:06 | craigbro | you want them to be more like vars then |
| 22:06 | craigbro | err |
| 22:06 | craigbro | trying to trigger clojurebot there |
| 22:06 | craigbro | eq? |
| 22:06 | clojurebot | Anyone can hack! http://images.wikia.com/pixar/images/0/0d/Http_alliedow-files-wordpress-com_2011-01_anyone-can-cook-445x355.png |
| 22:06 | kovas_ | I agree its a shame you can't directly attach stuff to symbols as identities |
| 22:07 | kovas_ | that would make things more symbolic for sure |
| 22:07 | craigbro | symbol properties! |
| 22:07 | craigbro | common lisp again |
| 22:07 | craigbro | lord save us all |
| 22:07 | kovas_ | i mean, its easy enough to do it yourself |
| 22:08 | kovas_ | without some programmatic meaning to the properties, its not that useful |
| 22:08 | kovas_ | but if its integrated with macros, then it is very useful |
| 22:09 | craigbro | programmating meaning to the properties? |
| 22:09 | craigbro | programmatic.. |
| 22:10 | kovas_ | yes, like mathematica attributes |
| 22:10 | craigbro | not familiar |
| 22:10 | kovas_ | its trivial to make symbols thread over lists by setting the attribute Listable |
| 22:10 | arrdem | ,\f |
| 22:10 | clojurebot | \f |
| 22:11 | kovas_ | http://reference.wolfram.com/mathematica/tutorial/Attributes.html |
| 22:11 | kovas_ | unfortunately in mathematica attributes are not extensible by the user |
| 22:11 | kovas_ | but they cover many of the cases we use macros for |
| 22:11 | kovas_ | in a much easier to use way |
| 22:12 | kovas_ | "Sometimes, however, you need to specify general properties of functions, without necessarily giving explicit values." |
| 22:12 | kovas_ | actually this is also relevant to ibdknox 's project |
| 22:13 | kovas_ | so what id like to figure out is how to have the concept of Attributes be made extensible |
| 22:13 | kovas_ | by attached metadata on the symbol, combined with some kind of macro protocol |
| 22:14 | craigbro | getting to be one too many transformation layers for my tastes |
| 22:14 | kovas_ | its more of a natural completion of the abstractions we have now |
| 22:14 | kovas_ | why can't macros have protocols? |
| 22:14 | kovas_ | that would make them a lot more interoperable |
| 22:15 | kovas_ | and symbols could specify what their own macro expansion should be |
| 22:15 | kovas_ | under a given macro |
| 22:15 | kovas_ | as it is, its pretty broken from the "program against abstractions" pov |
| 22:16 | kovas_ | if you want (foo [a b c]) -> [(foo a) (foo b) (foo b)] |
| 22:16 | kovas_ | its silly to not have an abstraction you can apply to the symbol foo to get that behavior |
| 22:17 | craigbro | write the function that way |
| 22:17 | kovas_ | craigbro: so layers of transformation is good for CLIM, but not for general programming ;) |
| 22:18 | craigbro | don't hide it in a property... |
| 22:18 | kovas_ | its more declarative as a property |
| 22:18 | kovas_ | "what, not how" |
| 22:19 | kovas_ | you can set the attribute in the function definition, so its not off somewhere else |
| 22:20 | craigbro | map is as much what as how |
| 22:21 | craigbro | so this is not decl. vs anything else |
| 22:21 | craigbro | syntactic mutability |
| 22:23 | craigbro | can't you not alrady do this with tagged literals? |
| 22:23 | kovas_ | i wish |
| 22:23 | craigbro | sure you could |
| 22:23 | kovas_ | i don't think so |
| 22:24 | craigbro | for listable |
| 22:24 | craigbro | your data reader fn would be given foo |
| 22:24 | kovas_ | i don't think TLs capture scope the way you want |
| 22:25 | kovas_ | i should play with that again, but theres some tricky issues |
| 22:25 | kovas_ | i mean, you can do it with a macro right |
| 22:26 | kovas_ | at least thats what we end up doing |
| 22:26 | kovas_ | but that isn't extensible. |
| 22:26 | kovas_ | the macro can't know, for each symbol, which positions should be listable |
| 22:26 | craigbro | seems to me you could do it in the fn itself |
| 22:27 | craigbro | a macro (listable-body... |
| 22:27 | kovas_ | yes, but then that information is lost to the symbol level |
| 22:28 | kovas_ | its just "this happens to be the behavior of the function, buts that a black box" |
| 22:29 | kovas_ | it wouldn't be so bad if you could have multiple function forms with the same arity |
| 22:29 | kovas_ | if you have a 1-arity function, you have to have a conditional first before you figure out if you map, or if you do the base case |
| 22:29 | craigbro | you could us your own defn |
| 22:29 | craigbro | since you're just talking about fns... |
| 22:30 | craigbro | we don't have symbol macro expansion anyways |
| 22:30 | kovas_ | i think we should |
| 22:30 | craigbro | sure, I do to actually |
| 22:30 | craigbro | your defn would be a fine way to experiment with this |
| 22:31 | kovas_ | yes thats a good point |
| 22:31 | craigbro | i do macros like that all the time |
| 22:31 | kovas_ | you mean like custom defns? |
| 22:31 | craigbro | a macro that defines a fn as the vlaue of the symbol, but also sets up alot of bookkeeping |
| 22:32 | craigbro | and metadata |
| 22:33 | craigbro | I prefer a global ref to a map |
| 22:33 | craigbro | keys on the symbol |
| 22:33 | craigbro | keyed... |
| 22:33 | craigbro | instead of metadata |
| 22:33 | kovas_ | yeah that solves your other problems |
| 22:33 | kovas_ | i gotta run |
| 22:33 | kovas_ | ttyl! |
| 22:34 | craigbro | latah |
| 22:54 | yedi | wow clojurescript up and running is a super quick read |
| 22:56 | ChongLi | yedi: yeah, it is |
| 22:57 | ChongLi | I hope they update it at some point when the tooling becomes more developed |
| 22:58 | ChongLi | setting up a browser repl in particular is a tricky process |
| 23:21 | TimMc | ibdknox: The difference between local and remote is more than just an implementation detail. You suddenly have to deal with network outages where before there was a simple function call. |
| 23:22 | bbloom | TimMc: agreed, i think that a more likely first step is something akin to the "himera model" that fogus talks about here: http://blog.fogus.me/2012/03/27/compiling-clojure-to-javascript-pt-3-the-himera-model/ |
| 23:23 | bbloom | that's what i'm going for: in that model<->viewmodel<->view<->platform chain, i want to be able to pick and choose where i draw the line on what parts of the pipeline go on which endpoint |
| 23:25 | bbloom | ie a mobile app may choose to run everything but the platform rendering on the server |
| 23:25 | bbloom | a desktop app may run everything on a single node |
| 23:25 | bbloom | a web app may run only the underlying model on the server |
| 23:26 | yedi | whats the decision process for making a library a core lib? |
| 23:27 | technomancy | yedi: it basically doesn't happen any more |
| 23:27 | ibdknox | TimMc: I'm not sure I understand the distinction you're drawing. There are well defined strategies for dealing with the network, I would just employ one of those? |
| 23:28 | yedi | so a core.matrix might be out of the question? |
| 23:28 | bbloom | ibdknox: i think the point he's making is that sometimes there are genuine *what* questions, not just *how* questions, to be answered about the behavior of an app in the face of latency |
| 23:28 | cjfrisz | So...is there documentation for Domina anywhere? |
| 23:28 | TimMc | ibdknox: What I mean is, suddenly there are parts of your program that have to know about non-local execution. |
| 23:28 | cjfrisz | Or is it all documentation by example? |
| 23:29 | technomancy | yedi: you mean a contrib? |
| 23:29 | ibdknox | bbloom: TimMc: can you give an example? |
| 23:29 | bbloom | ibdknox: like when you post a comment on facebook, it's rendered optimistically, but if the request times out, then the input form shows back up. however, there are options you wouldn't want to render optimistically, for example a sale of stock |
| 23:30 | technomancy | TimMc: are you referring to rich's "why Clojure isn't like Erlang" post? |
| 23:30 | TimMc | Well, it does depend on where you draw the app/framework boundary, but at a certain point you want to have business logic involved in error handling. |
| 23:30 | TimMc | technomancy: No, but that sounds like interesting reading. :-) |
| 23:31 | bbloom | ibdknox: when you introduce a partition, you introduce latency and failure. when you introduce latency and failure, you need to make decisions about trade offs and behavior |
| 23:31 | ibdknox | bbloom: that's a good one. I'll have to think about it |
| 23:32 | cark | technomancy: is that post on the mailing list ? |
| 23:32 | technomancy | TimMc, cark: http://bc.tech.coop/blog/081201.html |
| 23:32 | TimMc | thx |
| 23:32 | cark | thanks ! |
| 23:32 | technomancy | search down to "I chose not to use the Erlang-style actor model for same-process state management in Clojure for several reasons:" |
| 23:32 | yedi | technomancy: nvm, was getting the two confused |
| 23:33 | TimMc | https://groups.google.com/group/clojure/browse_thread/thread/2a2b24ffef5d1631/2ad59d1c4bb165ff#2ad59d1c4bb165ff |
| 23:35 | bbloom | technomancy: that's a good read |
| 23:35 | technomancy | yedi: I don't know what the process is, but I know it involves not completely hating Jira and trying to figure out how to get Hudson working with Maven and Sonatype OSS... so... yeah. |
| 23:36 | TimMc | I'll read that tomorrow. |
| 23:36 | TimMc | It looks interesting, but so does my bed. |
| 23:37 | amalloy | if your bed looks interesting, probably time to clean up, mate |
| 23:38 | bbloom | craigbro: thanks for mentioning CLIM, i hadn't seen it before. i'll study it |
| 23:39 | TimMc | amalloy: The fact that it contains my spouse probably factors in here somewhere. :-) |
| 23:40 | craigbro | bbloom: lots to pick from the cold cold corpse of common lisp |
| 23:41 | craigbro | TimMc: shush, you don't want to remind people of CORBA with all this talk of the difference btween local and remote |
| 23:45 | arrdem | do we have a -> that short-circuits on `nil`? |
| 23:45 | craigbro | not that I know of, but sounds innaresting |
| 23:45 | craigbro | hmmm |
| 23:45 | arrdem | it could be a 1.5.0 feature, but I know I've heard of it. |
| 23:45 | craigbro | can't you just do |
| 23:46 | craigbro | oops never mind |
| 23:46 | craigbro | there are a bunch of threading macros added in 1.5.0 right? |
| 23:47 | craigbro | https://github.com/clojure/clojure/blob/master/changes.md |
| 23:47 | craigbro | some-> |
| 23:47 | bbloom | craigbro: yeah, in particular cond-> is awesome |
| 23:47 | craigbro | there ya go |
| 23:47 | craigbro | I had a hard time warming up to threading macros |
| 23:47 | bbloom | i <3 them :-) |
| 23:48 | bbloom | i really enjoy thinking in steps |
| 23:48 | craigbro | (as-> I dig |
| 23:48 | bbloom | it makes it really easy to test some more complex multi-step algorithms |
| 23:48 | craigbro | and could totally use |
| 23:48 | craigbro | that clj-http wrapper I wrote uses them alot |
| 23:48 | arrdem | (some->) is what I want.. |
| 23:48 | arrdem | mmkay. |
| 23:48 | craigbro | the idea is you thread a map that represents a browser session |
| 23:49 | craigbro | arrdem: if you look around I bet you can find implementations you can load into 1.4.0 |
| 23:49 | craigbro | thru a bunch of calls that requests urls, save cookies or params, fill in forms, etc... |
| 23:50 | bbloom | hmmm no as->> |
| 23:50 | bbloom | ? |
| 23:50 | frozenlock | cljs: I have a js function with a callback. However the function I want to pass in the callback is inside a remote-callback (fetch) and is asynchronous. Is there a way to remain into the callback until the fetch is completed? |
| 23:50 | bbloom | frozenlock: you mean block? |
| 23:50 | TheBusby | anyone else following the drama in the clojurescript contribution thread on the ML? |
| 23:51 | noprompt | quick question about namespace naming conventions: is it ideal to use singular or plural names? i.e., if i have a ns that contains types should it be (ns foo.types) or (ns foo.type) |
| 23:51 | frozenlock | bbloom: I think... "By the nature of JavaScript letrem is an asynchronous block"-Fetch library |
| 23:52 | bbloom | noprompt: http://programmers.stackexchange.com/a/75929 |
| 23:52 | frozenlock | I could set an atom, then wait until the atom is changed... but it seems.. yuck |
| 23:52 | noprompt | bbloom: thanks :) |
| 23:53 | cjfrisz | Sorry for asking twice, but got no answer... |
| 23:53 | cjfrisz | Is there domina documentation anywhere? |
| 23:53 | frozenlock | cjfrisz: besides the github readme? |
| 23:54 | noprompt | so just to make sure i'm understanding this, in this case i'm looking for (ns foo.type) since it only contains records? |
| 23:55 | cjfrisz | frozenlock: yes, besides that |
| 23:55 | cjfrisz | And I already looked through ClojureScript One |
| 23:56 | technomancy | TheBusby: it appears with fairly predictable regularity |
| 23:56 | cjfrisz | Maybe I'm just having trouble coming at it from not having done much JavaScript |
| 23:56 | technomancy | it's getting to be more predictable than the "hey guys what if we did clojure but with whitespace instead of parens" posts |
| 23:56 | cjfrisz | Not good enough at guessing the translation from JS to CLJS+domina |
| 23:56 | arrdem | technomancy: oh gods you get those? |
| 23:57 | technomancy | arrdem: used to be every 6 months |
| 23:57 | TheBusby | technomancy: don't imagine it'll be going away either. :( |
| 23:57 | technomancy | but it's been a while |
| 23:57 | frozenlock | cjfrisz: I don't think there's anything else. But there's an API section in the source code which is quite straightforward https://github.com/levand/domina/blob/master/src/cljs/domina.cljs#L108 |
| 23:57 | technomancy | TheBusby: not till every last potential contributor's hope is crushed |
| 23:57 | TheBusby | haha, we'll see |
| 23:57 | arrdem | I guess if you use Python-style four space indentation... but I'm thoroughly revolted. |
| 23:58 | TheBusby | I was curious if you can submit patches to core members and have them take care of it? |
| 23:58 | technomancy | arrdem: "you know, for newbies" http://www.dwheeler.com/readable/sweet-expressions.html |
| 23:58 | technomancy | TheBusby: maybe if you submit them along with a bribe |
| 23:59 | TheBusby | technomancy: a nice scotch maybe? or Sake? |
| 23:59 | cjfrisz | frozenlock: thanks |
| 23:59 | technomancy | TheBusby: try it and let me know if it works =) |
| 23:59 | arrdem | I mean... it's a solid syntax proposal... but for the part where you count whitespaces. |