cevado

cevado

Extending IEx to have nREPL capabilities

IEx is a very powerfull shell and it would be awesome to have all this power integrated inside a code editor. Clojure enables something like that with nREPL.
nrepl has a set of operations that it support. I think for Elixir a good initial point would be the IEx helpers and autocomplete.

what I envision is:
you can run IEx on “network mode”, this way there is a port where IEx can receive operations and eval it and return the result of the operation to the caller.
this way any language(lua for nvim, js for vscode, elisp for emacs) could have a client that issues those commands and can use the response to extend the capabilities of the editor.

difference from LSP:
language servers are limited to what the protocol allows you to do. in other words, if there is no way to expose a functionality through LSP to the editor, it won’t be available. in the other hand with a “network iex” we could handle all the IEx helpers and shell tools directly to the editor.

advantages of that approach:
new features and functionalities added to IEx could easily become new features and capabilities in the editor. instead of the herculean job of interfacing elixir functionalities to the LSP.

there other nrepl approaches:

it’s not listed there but there is a ruby one too:

Most Liked

mauricio.szabo

mauricio.szabo

Author here, ask me anything :).

So, the project itself is not that hard. nREPL itself is very simple to implement, and even bencode is not that hard (having implemented it in Clojure and ClojureScript, in a purely functional way). It give a huge benefit to development, too.

The most complicated part, for Ruby at least, was (and still is) the actual editor part - parsing code and identifying where we are in the source, and what exactly do we need to evaluate, especially considering all special syntax that Ruby have.

For Ruby, things work quite well because the “binding” of the current “context” (like, inside a method which variables are visible, what are their values, etc) is first-class - meaning that I can “store” this binding in the nREPL side and then evaluate code as if I was still running that method (again, huge debugging capabilities here!). I don’t know how much IEx exposes, but considering that Elixir is a functional language, maybe we don’t even need these “hacks” because we don’t need to create a class, then set attributes, mutate stuff, before we can actually run some function :slight_smile:

mjrusso

mjrusso

Hi :wave: Thanks for pinging me. Some really great discussion here.

(For posterity: I just updated the nexREPL README to include a link to the simple demo I shared earlier today on Twitter, and to also link to this thread.)

Having been immersed in this for the past few days, a few thoughts:

  • The biggest advantage of working in the existing nREPL ecosystem (IMO) is access to the editor-specific clients. However, after surveying the landscape of existing client implementations, and excluding the ones that aren’t Clojure-exclusive, there’s not a lot of options.
  • Eval’ing the expression at the given point/cursor position is pretty essential. The clients I tested don’t send all the necessary information over-the-wire to properly implement this on the server (there are optional parameters in the nREPL protocol for the “eval” operation for the file name, line number, column number, etc., which conceivably could let you put the logic on the server, but you still run into trouble with handling unsaved files etc).
  • All that being said, the relative simplicity of the nREPL protocol means that it isn’t a huge stretch to build a custom client. But at that point, why not build something fully custom that directly integrates with IEx and doesn’t have any Clojure baggage?
  • I am bullish on the idea of mediating this through LSP (as described at a high level in the nexREPL README), where LSP is the protocol that a custom “eval code” code action is sent through, the LSP server figures out the context and exactly what code you need to eval, and then sends the code directly to an existing IEx session. This of course is only one path of many options, but it solves the client issues and could reasonably be something built in to a language server (which would really help with adoption).
cevado

cevado

@mauricio.szabo that works on the nrepl for ruby and wrote the client for clojure nrepl on atom/pulsar did a video showing the powers of nrepl in ruby, i think that’s a good way to see how different and helpful a nrepl is from a usual language server.

mauricio.szabo

mauricio.szabo

@mjrusso problem of integrating in LSP is that we don’t actually solve client issues. I don’t believe any LSP client that exists now expects an “evaluate” operation, and while that can be added, clients don’t actually have any logic for this kind of interaction to happen - meaning there are no UI design to handle evaluations, for example.

The great advantage to reuse some nREPL client is that if the client/plug-in doesn’t send all the information, the only actual change they need to add is to send that info - every other task related to “evaluate something and get back a result”, like some “awaiting result” state, or a command to “break” the evaluation, are probably already present. Piggiebacking on something that exists, even if it needs some adjustment, can be a huge advantage compared to start something fully custom that will need to start up implementations from scratch.

I know this is kind of a weird chicken-and-egg situation, where we need client support to justify a server implementation, and we need server support tonikplement the ckient side too :slight_smile:

mauricio.szabo

mauricio.szabo

Great news then - I’m cureently using TreeSitter to parse Ruby in the Lazuli project :smile:

Where Next?

Popular in Proposals: Ideas Top

MeerKatDev
many times we do stuff like (e.g. test setups, json views in phoenix) aaa = ... bbb = ... ccc = ... %{aaa: aaa, bbb: bbb, ccc: ccc} and...
New
rhcarvalho
Hi all, I would like to gather some feedback before a more intentional proposal to add a new :depth option when specifying a Git depende...
New
rekkice
I’m building an editor integration to evaluate Elixir code in an IEx session. While Code.eval_string/3 allows tracking variable bindings,...
New
kip
Sumary of proposal DateTime.from_iso8601/3 adjusted to: set all numeric fields to the values as parsed (not shifted to UTC), preservi...
New
pdgonzalez872
Hi! There has been some discussion about hiring/jobs on here and I thought about running this by everyone. I wanted to try to help recr...
New
dli
Ecto currently supports some data-modifying WITH statements / CTEs for Postgres: Options: […] :operation - one of :all , :update_all ,...
New
winsalva
Hello all. First of all i’m running this using termux on an android phone. Running mix assets.setup shows this message 06:54:08.450 [de...
New
bartblast
This could resolve to {[a: 1, b: 2]}. Was it ever considered to allow such syntax? Notice this: {:abc, a: 1, b: 2} and this: my_fun(:abc,...
New
sezaru
When writing my code, I always find __MODULE__ very useful to use as alias of that module “inner dependencies”, ex: alias __MODULE__.{Im...
New
dkuku
This is a proposal to make the map key mismatch errors a bit better: Every time I have a typo It’s very challenging for me even when I u...
New

Other popular topics Top

SoCreat
i’m a new one to elixir which editor can i use vs code? or atom? Thanks! :smiley:
New
sergio
In Ruby, I can go: User.find_by(email: "foobar@email.com").update(email: "hello@email.com") How can I do something similar in Elixir? ...
New
yawaramin
In the Dialyzer docs ( http://erlang.org/doc/man/dialyzer.html#requesting-or-suppressing-warnings-in-source-files ), there is a way to tu...
New
albydarned
Hello all! I am typing this post from my new MacBook Pro with the M1 chip. I’m loving it so far, and will probably use it as my daily dr...
New
jerry
Good day to you all. I have been struggling to get a query involving like and ilike to work. Can anyone assist me on this, please? pro...
New
_russellb
I want to try my hand at web scraping. What tools/libraries do I need to use. I’m hoping to turn this into something professional so don’...
New
malloryerik
Hi, this is for people who, like me, have had some friction using .html.heex templates in VSCode. The solution seems to be, in a hyphena...
New
KronicDeth
Elixir plugin for JetBrain’s IntelliJ Platform (including Rubymine) This is a plugin that adds support for Elixir to JetBrains IntelliJ...
289 35421 110
New
jay1
Why is it that the mnesia database isn’t the most preferred database for use in Elixir/Phoenix?
New
magnetic
Hey :wave:t3: Elixir community, I’ve been learning Elixir, and working on some side projects. My editor of choice is VSCode, and althoug...
New

We're in Beta

About us Mission Statement