isomorƒ: an experimental structured editor for witing/deploying functional code

isomorƒ is attempting to bridge the divide between functional programming, serverless architecture, and cloud-based structured-editing with the grand hope of creating a simplified, beginner-friendly, but powerful IDE experience with easy microservice deployment.

The platform runs on a compact, pure, statically-typed functional AST with all the power in the IDE including a syntactic sugar layer, passively identified reuse ideas, exposte optimization, automatic versioning, and immediate cross-user sharing (all enabled by the guarantees of functional purity / referential transparency).

We currently have a prototype sandbox of the IDE available and a high-level vision at our blog.

We would love any feedback on the sandbox, the idea/implementation, academic/educational/commercial applications or anything else!


Comment viewing options

Select your preferred way to display the comments and click "Save settings" to activate your changes.

Looks slick, can’t figure it out

I wanted to write a small program to take a string "Hello, world!", reverse it, and return it to print it out.

It took me a while to figure out how to make a local function with only one argument—I had to select both the type and the argument, bring up the menu, and select the trash bin icon. Is that how it’s supposed to work? I couldn’t enter a string constant containing capital letters. The only way I could figure out how to enter a singleton list was to add a ? : ? node and fill it in with head and [], and it was then displayed as [head]. I then ended up with this code in the Haskell-style view, which looks correct to me:

demo.main :: -> String
demo.main =
  rev :: isomorf.list.List A -> isomorph.list.List A
  rev xs =
    case (xs) of
      ([]) -> []
      head : tail -> (rev tail) ++ [head]
  (rev "hello, world!")

It complains about [], saying it can’t match isomorf.list.List A with (-> isomorf.list.List ?), so I changed it to xs. However, it makes the same complaint about [head], and I saw no way to fix it.

I had a separate hunch that a string is not a list of characters, but I didn’t know how to find out. So I removed the A type variable from rev, and then it complained that indeed String is not List Char. There seems to be no way to convert between them yet.

The keyboard shortcut frame tends to cover up what I’m working on—everything is squashed at the bottom of the screen. I found the button to turn it off, but I don’t really know how to use the editor effectively without it, because the shortcuts (Option-0, -1, &c.) aren’t mnemonic.

In general the editor looks nice and feels snappy, but until it’s polished more, it suffers from the same problems as most structured editing tools—it’s a barrier between me and the code I’m trying to write. It’d also be nice to allow structured operations that fill the same role as common unstructured edits, like “add call to new local function”.

great feedback!

First of all, thank you for putting in what was clearly some serious time with the IDE. Your feedback is greatly appreciated.

To address some of the specifics you bring up:

  • The embarrassing bug that didn’t allow strings with caps will be fixed in our next release
  • Your insightful “add call to new local function” command will also be part of our next release. In fact, you can select multiple locations and simultaneously add calls to the new local function, and then the local function definition will be added at the lowest common ancestor among the points. These are exactly the kind of higher order edits (both conceptually and across locations) that we are actively looking for and we hope can push the efficiency of the structured editing to a level that is worth the adoption hurdle.
  • The legend covering the workspace has been a common complaint and we are discussing how to deal with it internally. We are trying hard to balance the ease of use with the plethora of windows of a traditional IDE like Eclipse.
  • Currently when creating a new function, we default to an arity of 2, although this should ultimately be specified along with the new name. Deleting the arg name should result in an atomic removal of the type being removed too, so that should be one keystroke. (Deleting the type however will just bring you back to bottom type / ?).

The sandbox does not yet expose all the details or knobs to customize sugars, just the broad “inspired by language X” dropdown. So as you discovered, it is not obvious what is an alias (which String is for List[Char], [] is for List.Nil, and : is for List.Cons), nor is it obvious what is sugar (which [?] is for ? : List.Nil). We plan to have those details in the “assistant” so they might be inspected and tweaked individually per top-level definition.

From the IDE's perspective, no types or function are native or assumed. So you may have noticed all the edit operations are currently type-agnostic, hence no way to write something List-specific like a singleton wrapper. As you discovered, you can apply cons (? : ?) but not (? : []). Making type-specific convenience edits is definitely on our roadmap (and ideally user configurable).

As far as what was keeping your code from compiling, I believe it is a ticklish issue we are still trying to find the best UX to deal with: 0-argument constructors (the difference of List.Nil between an application (Nil() :: List) vs a first order reference ( Nil :: ( -> List) ). Functions usually have a natural visual distinction in f() vs f. While still a crutch, we have on our roadmap that this should at least generate a refactoring idea suggestion (the light bulb).

Concerning the non-mnemonic shortcut keys, our strategy for keyboard use has been to focus more on keyboard place than mnemonic association. As such, we have most of the shortcuts on the left side of the keyboard so that one hand use is easier. (A notable exception to this is the use of the “+” key as that has a powerful association.) In addition, we wanted redundant keystrokes across contexts, i.e., “option+1” tends to perform the “most common” action in a given context. As the product matures we will have fully customizable keystrokes, so in the end all of our theorizing won’t be of much relevance.

Again, thank you for the input and please join the beta list if you’d like to follow as things continue to progress!

a tour

Based on feedback, we put together a little tour of the platform that more explicitly walks through features and potential.