unrepl

discussing specification of an edn-based repl and its implementations.
cgrand 2017-11-21T10:35:50.000367Z

@pesterhazy ^^ not like Chez

volrath 2017-11-21T10:48:28.000315Z

@cgrand last night I was wondering about your thoughts on what can clients do to show objects in a "pretty way", or put in a different way: it'd be nice to be able to show objects 'a la pr'.. for example, in clojure.main/repl, the print function is prn, so if I eval + i get #function[clojure.core/+] back, and I would like to show the same in unrepl.el, but it's not derivable from the current #unrepl/object tagged literal

volrath 2017-11-21T10:50:29.000463Z

the only thing I could think of was extending the #unrepl/object so that it includes its pr, but I don't know if there's a better way

cgrand 2017-11-21T10:52:12.000190Z

#function seems very new as it’s not in beta 3

cgrand 2017-11-21T10:52:21.000429Z

(haven’t tried on RC)

volrath 2017-11-21T10:54:04.000235Z

hmm didn't noticed, I thought it was already stable

cgrand 2017-11-21T10:54:38.000151Z

you are on RC1?

volrath 2017-11-21T10:55:32.000055Z

actually no.

volrath 2017-11-21T10:55:34.000080Z

sec

cgrand 2017-11-21T10:55:47.000040Z

*clojure-version*

volrath 2017-11-21T10:56:06.000474Z

oss/unrepl [ JVM_OPTS='-Dclojure.server.myrepl={:port,5555,:accept,clojure.core.server/repl}' lein repl                                                                                        master * ] 11:54 >
nREPL server started on port 46374 on host 127.0.0.1 - <nrepl://127.0.0.1:46374>
REPL-y 0.3.7, nREPL 0.2.12
Clojure 1.8.0
Java HotSpot(TM) 64-Bit Server VM 1.8.0_101-b13
    Docs: (doc function-name-here)
          (find-doc "part-of-name-here")
  Source: (source function-name-here)
 Javadoc: (javadoc java-object-or-class-here)
    Exit: Control+D or (exit) or (quit)
 Results: Stored in vars *1, *2, *3, an exception in *e

user=&gt; +
#function[clojure.core/+]

volrath 2017-11-21T10:56:41.000291Z

user=&gt; +
#function[clojure.core/+]
user=&gt; *clojure-version*
{:major 1, :minor 8, :incremental 0, :qualifier nil}

volrath 2017-11-21T10:57:10.000327Z

although if I start the repl using the clojure 1.8.0 jar, I get #object

volrath 2017-11-21T10:57:27.000326Z

oss/unrepl [ java -Dclojure.server.myrepl="{:port 5555,:accept,clojure.core.server/repl}" -jar ~/.m2/repository/org/clojure/clojure/1.8.0/clojure-1.8.0.jar                                    master * ] 11:52 &gt;
Clojure 1.8.0
user=&gt; +
#object[clojure.core$_PLUS_ 0x4c2bb6e0 "clojure.core$_PLUS_@4c2bb6e0"]

volrath 2017-11-21T10:59:09.000104Z

(if I run cider for the unrepl repo, I also get #function )

cgrand 2017-11-21T10:59:27.000218Z

lein repl
Initializing NoDisassemble Transformer
nREPL server started on port 52727 on host 127.0.0.1 - <nrepl://127.0.0.1:52727>
REPL-y 0.3.7, nREPL 0.2.12
Clojure 1.8.0
Java HotSpot(TM) 64-Bit Server VM 1.8.0_05-b13
    Docs: (doc function-name-here)
          (find-doc "part-of-name-here")
  Source: (source function-name-here)
 Javadoc: (javadoc java-object-or-class-here)
    Exit: Control+D or (exit) or (quit)
 Results: Stored in vars *1, *2, *3, an exception in *e

user=&gt; +
#object[clojure.core$_PLUS_ 0x4ce1ff96 "clojure.core$_PLUS_@4ce1ff96"]

cgrand 2017-11-21T10:59:54.000495Z

so it’s cider

volrath 2017-11-21T11:00:23.000143Z

everything I sent was outside cider

volrath 2017-11-21T11:02:04.000165Z

I do have cider as a global lein plugin

volrath 2017-11-21T11:02:10.000356Z

let me try without it

cgrand 2017-11-21T11:02:20.000223Z

>>> ;; Extending print-method defined in clojure.core, to provide ;; prettier versions of some objects. This applies to anything that ;; calls print-method, which includes return values, pr, print ;; and the likes.

cgrand 2017-11-21T11:02:34.000468Z

(def ^:dynamic *pretty-objects*
  “If true, cider prettifies some object descriptions.
  For instance, instead of printing functions as
      #object[clojure.core$_PLUS_ 0x4e648e99 \“clojure.core$_PLUS_@4e648e99\“]
  they are printed as
      #function[clojure.core/+]
  To disable this feature, do
      (alter-var-root #’cider.nrepl.print-method/*pretty-objects* not)”
  true)

cgrand 2017-11-21T11:03:14.000108Z

monkey-patching print-method, so cute

volrath 2017-11-21T11:03:28.000389Z

right, yeah I tried without the plugin and got #object

volrath 2017-11-21T11:04:36.000157Z

I feel cheated haha

cgrand 2017-11-21T11:05:33.000190Z

So they just demunge the classname

volrath 2017-11-21T11:06:34.000176Z

so it seems

cgrand 2017-11-21T11:12:36.000034Z

the thing with their #function tag is that: 1/ it’s not namespaced 2/ it loses identity information, so you can’t tell if two closures created by the same function are the same or not

volrath 2017-11-21T11:16:54.000043Z

yes, agreed

cgrand 2017-11-21T11:18:35.000202Z

(partial map inc)
#function[clojure.core/partial/fn--4759]

cgrand 2017-11-21T11:35:18.000334Z

@volrath + now prints #unrepl/object [#unrepl.java/class clojure.core$_PLUS_ “0x774afe65” clojure.core/+ {:bean {#unrepl/... {:get (unrepl.replG__997/fetch :G__1443)} #unrepl/... nil}}]

volrath 2017-11-21T11:36:19.000252Z

awesome, maybe what I can do is print the demunged version and have the #object show as a tooltip 🙂

cgrand 2017-11-21T11:37:18.000218Z

I would keep the hash out of the tooltip

volrath 2017-11-21T11:37:32.000054Z

makes sense

volrath 2017-11-21T11:37:34.000101Z

alright

cgrand 2017-11-21T11:38:02.000289Z

as long as your rendering hints that magic happens (special color whatever), I’m ok with it

volrath 2017-11-21T11:38:16.000027Z

👍

volrath 2017-11-21T11:38:31.000268Z

here's another related question

cgrand 2017-11-21T11:38:53.000351Z

principle of least surprise (unlike #function that you assumed was standard)

volrath 2017-11-21T11:41:20.000324Z

pretty printing in general.. cider also does it with cider-nrepl.. so that if I have a very long map or whatever, I get a pretty version of it... I was thinking on how to enable that only in my blob

volrath 2017-11-21T11:41:49.000018Z

and maybe only on demand, so that I can give users the ability to opt out of it

cgrand 2017-11-21T11:42:28.000418Z

unrepl-make-blob does not yet offer a way to plug in the printer (so you have to resort to the hacksaw)

volrath 2017-11-21T11:43:11.000011Z

i figured...

cgrand 2017-11-21T11:44:49.000022Z

To me pretty printing should be done on the client side. Traditional pretty printing is a bit at odd with elisions anyway (if you plan to transclude them — whic I guess you do given how you treated string elisions)

volrath 2017-11-21T11:46:58.000400Z

yeah I looked around for clj (or even lisp) pretty printers written in elisp, but without much luck. so that's the thing on relaying pretty printing on an elisp client.

volrath 2017-11-21T11:47:41.000252Z

there are definitely some border cases with pretty printing and elision, but i think it's manageable.

cgrand 2017-11-21T11:48:15.000133Z

what are your requirements for PP?

volrath 2017-11-21T11:48:43.000050Z

Yes, I was thinking on something like middlewares or interceptors... or a function you could define with a session action

volrath 2017-11-21T11:51:41.000393Z

I haven't thought about it too much.. from a user point of view, I guess pp-ing lists, vectors, maps, and sets, will do..

volrath 2017-11-21T11:52:23.000146Z

I'd like to look a bit more on how cider does it, maybe see if there's something that can be improved there

cgrand 2017-11-21T11:57:36.000048Z

@volrath think a bit more as how as a user you like your stuff printed, when you want to transition from line to column etc.

cgrand 2017-11-21T11:58:49.000187Z

think also about interactivity: we already have elisions but maybe we can toggle the display mode of a collection, collapse it etc. (This doesn’t make up for good defaults.)

cgrand 2017-11-21T11:59:17.000033Z

What if we had the option to render a list of similarly keyed maps as a table?

volrath 2017-11-21T12:04:02.000233Z

so, taking collapsing out of the equation, I see that either done in elisp (not my fav option), or as possible :aux actions to be sent to unrepl and have the processing be done in clojure

volrath 2017-11-21T12:05:03.000397Z

I say taking out collapsing because hiding information that it's already there should be pretty straight forward

cgrand 2017-11-21T12:08:24.000046Z

Implementing stuff in: • Clojure: just require your helper ns on an aux connection and send it forms: pros easy cons when CLJS will come you’ll have to rewrite it (hopefully it will be cljs) • Elisp: pros works with any blob, any lang; cons elisp (it could be vim^Hworth).

dominicm 2017-11-21T12:09:29.000083Z

Clojure pro: Vim can use it for free

dominicm 2017-11-21T12:09:43.000033Z

cider-nrepl has been a valuable asset to vim users.

cgrand 2017-11-21T12:11:01.000287Z

if you don’t like your host lang spawn a CLJS repl

volrath 2017-11-21T12:12:06.000207Z

right, the thing about the aux helper is that I wouldn't have a way to use it as a default.. so for example, let's say I allow users to choose they want their stuff PPed, then I would have to send each client input wrapped in a helper?

volrath 2017-11-21T12:12:27.000249Z

it's an option for sure, not discarding it, but just wondering if there's a better way

cgrand 2017-11-21T12:13:16.000304Z

“each client input output” you meant?

volrath 2017-11-21T12:17:00.000204Z

input.. maybe I'm under/overthinking this. I was thinking, user types: user=&gt; *code that generates -long- data* ; the elisp client will send (my-custom-wrapper-for-pprint *code that generates -long- data*) so that I get the result pp-ed

volrath 2017-11-21T12:17:46.000378Z

I know the other option could be to wait for the :eval message and then send an aux helper like (pprint-me-this &lt;eval result&gt;)

volrath 2017-11-21T12:17:55.000102Z

but I was thinking on avoiding the roundtrip

cgrand 2017-11-21T12:20:26.000095Z

:thinking_face:

cgrand 2017-11-21T12:22:11.000262Z

(my-custom-wrapper-for-pprint *code that generates -long- data*) looks like a bad idea (unrepl-wise) because in a sense you are framing input.

volrath 2017-11-21T12:22:29.000412Z

yes

cgrand 2017-11-21T12:23:55.000342Z

you could customize the blob (and with enough persuasion I will make it easier) to emit your own [:unrepl.el/pprinted xxx id] messages.

volrath 2017-11-21T12:23:55.000352Z

(btw, I wasn't planning on working on pp soon, it is down the road.. but just thought on bringing up the topic)

cgrand 2017-11-21T12:24:32.000169Z

The thing is: if your code generates long data do you want to display all the data at once?

volrath 2017-11-21T12:25:33.000364Z

I also thought about that a little bit yesterday.. I think the answer is maybe. I thought on making it customizable in the elisp client, let the user decide

volrath 2017-11-21T12:26:23.000099Z

at least at the beginning it could be as easy as a boolean value: the client will either resolve all elisions automatically or won't

volrath 2017-11-21T12:27:37.000229Z

I also plan to make the max-print-length customizable inside emacs.. the user can decide it there and I'll use the session helpers to adjust when I receive :hello

👍 1
volrath 2017-11-21T12:28:58.000078Z

tbh, I think of elision as pretty printing, both are great, but should be optional

cgrand 2017-11-21T12:33:56.000110Z

I disagree but let’s experiment!

👍 1
cgrand 2017-11-21T15:00:34.000454Z

At the Conj @chouser asked about pair programming and unrepl, I jotted down some thoughts after chatting with him today https://github.com/Unrepl/unrepl/wiki/Pair-(or-more)-Programming

baptiste-from-paris 2017-11-21T16:26:25.000761Z

hello all, I am trying to install unravel but I got an Error: EACCES: permission denied, open 'lumo_mac.zip'

baptiste-from-paris 2017-11-21T16:26:29.000791Z

sounds familiar ?

baptiste-from-paris 2017-11-21T16:37:17.000264Z

nevermind it’s working, was a rights issue on node

baptiste-from-paris 2017-11-21T16:37:30.000829Z

and unravel looks awesome ^^

baptiste-from-paris 2017-11-21T16:39:26.000244Z

the doc right above the repl is really cool

cgrand 2017-11-21T16:46:16.000372Z

@baptiste-from-paris you built from master?

baptiste-from-paris 2017-11-21T16:55:51.000850Z

yep

cgrand 2017-11-21T17:01:58.000449Z

could you give a try to parfix (multiline + paren completion)?

baptiste-from-paris 2017-11-21T20:04:19.000061Z

@cgrand could you send a link for parfix ?

baptiste-from-paris 2017-11-21T20:04:46.000313Z

don’t find it

volrath 2017-11-21T20:50:07.000460Z

I believe he's referring to the parfix branch: https://github.com/Unrepl/unravel/tree/parfix, you should have multiline and paren completion there

cgrand 2017-11-21T20:53:24.000599Z

Yeah it’s the name of the branch.

baptiste-from-paris 2017-11-21T21:17:17.000265Z

ah

baptiste-from-paris 2017-11-21T21:17:18.000097Z

ok

baptiste-from-paris 2017-11-21T21:20:05.000372Z

@cgrand how many open-source projects do you manage and are you humain ? 😄

cgrand 2017-11-22T08:22:12.000079Z

Thanks to you I have a sudden urge of listening to Daft Punk’s “Human after all” and Katerine’s “Robots après tout” LPs 😉

cgrand 2017-11-22T08:22:40.000177Z

It would be cool to create a modern Bourbaki 🙂

baptiste-from-paris 2017-11-21T21:23:34.000319Z

ok, working great with ident

baptiste-from-paris 2017-11-21T21:24:34.000382Z

and that’s almost the best REPL XP that I had in a terminal

baptiste-from-paris 2017-11-21T21:25:31.000340Z

it seems that history does not work anymore

baptiste-from-paris 2017-11-21T21:25:56.000397Z

on this branch

baptiste-from-paris 2017-11-21T21:29:32.000451Z

I don’t get where unrepl is loaded in unravel, no lein/boot project file

cgrand 2017-11-22T08:23:22.000382Z

You mean as a dep when building unravel?

cgrand 2017-11-22T08:24:34.000355Z

Well unrepl is a protocol so you don’t have to require it. The unrepl repo is also a built tool to create server implementations of this protocol.

cgrand 2017-11-22T08:24:52.000229Z

The artifact produced is the famous blob.

cgrand 2017-11-22T08:26:03.000465Z

See scripts/update-unrepl and resources/unrepl/blob.clj

cgrand 2017-11-21T21:59:17.000119Z

@baptiste-from-paris on this branch it’s ctrl up/down for history.

baptiste-from-paris 2017-11-21T22:13:32.000155Z

ok