mcclure / emily

Git mirror of https://bitbucket.org/runhello/emily
Other
58 stars 5 forks source link

Very very minimal REPL is working. #1

Closed non closed 9 years ago

non commented 9 years ago

Launching ./emily -r will enter the REPL mode. This is a bit like ./emily - except that lines will be executed as they are written (unless they end with \, the line-continuation chararacter).

This is very, very raw, and needs a lot of work. But hopefully it's a good starting point.

non commented 9 years ago

Seems like whatever indenting was happening conflicted with the built-in. I need to clean up the diff at some point.

mcclure commented 9 years ago

This view is confusing! The one in Stash is better. Why can't I reply directly to comments.

Anyway, @non, re indenting, please see style.md, I have been using 4-space indents everywhere but your text editor most likely is going to prefer 2 for ocaml (I diverge from standard ocaml style on two points).

non commented 9 years ago

OK, so emily -i file.em will exec the file then drop you into a REPL. That makes sense.

Eventually, would you be open to having emily launch a REPL, like python does?

Other questions:

  1. Is there a prefix character you'd be OK with using for "magic" REPL commands at the start of input? ipython uses %.
  2. Do you think writing a paren/brace matcher is a good way to catch "continued" lines?
  3. Do you think inspecting the scope is the right way to see which names are defined (e.g. for tab-completion)?
  4. When executing code like f ^x = x + 1 does executeNext return something that gives me a clue to what happened? Right now the REPL doesn't create any ouptut (other then e.g. println) but it might be nice for x = 9 to output 9 or something like that.
mcclure commented 9 years ago
  1. I'd really rather "emily" by itself print help, and I'm still tempted by the idea of making the interpreter a separate executable. Even just telling people to run alias ei=emily -i is not so big a demand.
  2. Why not just make the "magic" commands symbols in the scope?
  3. Sure, alternately maybe tokenize.ml should be modified to be able to do this for you (i.e.: tokenize.ml should be able to read "until it gets a complete operation" then stop?) The thing is, in the absence of reader macros, it is guaranteed that paren-counting is sound. This is a guarantee made to make macro processing make sense but it helps you here.
  4. Yes.
  5. Yes. executeNext actually is the method called when you process a parenthesis. It would be simple to invoke executeNext in such a way that the entire expression is treated as a paren, and then you will get a value result. You might have to prepare the stack in a particular way though. I can try to work out a more detailed answer if you need one.
non commented 9 years ago

OK sorry, I just noticed these comments. I will back out of the magic commands.

I was also experimenting with making "magic" commands symbols in scope. The big downer is that (AFAIK) you have to write do help or help() to get it to do anything. I would probably have to intercept quit() and handle it in the REPL, but that's OK (if ugly) IMO. Do you think Emily will support enough introspection to make interesting magic commands (i.e. searching/completing names, looking at things in scope, and so on) possible to implement directly in Emily?

If paren counting is sound I'll just do that for now, great!

I'll try to play with manipulating the stack to get more data out of executeNext but if you are inspired to post a snippet that might be helpful.

Sorry again that the most recent commit probably moves in the wrong direction. Thanks for your feedback!

non commented 9 years ago

Known issues:

  1. Exceptions in Emily should not crash the REPL
  2. Need to use paren counting to support multi-line input in a less horrible way
  3. Control-C should not crash REPL
  4. Need to look into the previously mentioned strategy to get (and display) last value on the stack
non commented 9 years ago

One more question to add to the stack (sorry for the deluge): I think we are getting to the point where it would be possible to use something like Lambda-Term to get a nice line editing experience (arrow keys, control-A, control-E, history, and so on).

Is it worth it? I know you wanted to minimize dependencies so right now I'm not focusing on line editing. I'm happy to leave the current REPL very bare bones, but ultimately using something like Lambda-Term would be a lot nicer.

What do you think?

non commented 9 years ago

Progress report: I looked into how Token and TokenGroup work and feel like I have a pretty good handle on them at this point. However, I still haven't seen an obvious way to get Execute.executeStep to return a value for the REPL to use.

I was wondering embedding the user's input ... in something like res0 = (...); if res0 ^(println res0). However, this seemed really hacky, and would possibly throw off the code locations in error messages and things like that.

One nice benefit of doing something like this is that if successive results are stored in res0, res1`, and so on, it is easy to refer to previously-generated values while working in the REPL.

mcclure commented 9 years ago

Finally got a chance to read, this looks good! Very clean code. Um, I think I will need to get back to you (hopefully tonight or tomorrow night?) with an example of how to use executeNext.

I like the res0, res1 idea by itself, probably line position is not an issue if you use something like snippetClosure to turn their code into a function and then have your res0 = execute that. But I think it would be better to jut use executeNext.

Still thinking about lambda-term-- how would you feel about a separate emilyi (or something) executable that uses lambda-term? I haven't checked but I'm afraid lambda-term will pull in readline or something garbage.

non commented 9 years ago

Thanks!

I think planning to create a separate emilyi or emilyrepl executable with lambda-term makes a lot of sense. (To be honest I tried to quickly throw something together with lambda-term and utterly failed, so I think I need to learn a little bit more about how OCaml libraries work first.)

non commented 9 years ago

Any ideas on how to proceed? I'm not 100% sure what the next step for this is.

non commented 9 years ago

Do you have a sense of what more you'd want to see before considering a merge?

mcclure commented 9 years ago

I filed a PR: https://github.com/non/emily/pull/1 I think with those changes, all I'd need to merge is better handling of "open" lines. I will probably do that part myself.

non commented 9 years ago

Alright, at this point we are displaying tables/objects in a useful way, and also display numbers in the REPL without a dot.

If you'd like, I can make the number format changes happen throughout the code (and fix all the tests). Or I can leave it alone for now.

mcclure commented 9 years ago

That is wonderful, I'm going to manually merge this and push in a minute. Please do implement the number format changes but please do it as a new pull request (rooted from unstable would be most convenient, but whereever is fine).

mcclure commented 9 years ago

Now in the stable branch as of 6226251a4adb