“Yo, check out this new shiny piece of technology!”

“Why?”

“Because it is functional, distributed, cloud enabled, big data, IoT, bla, bla, bla platform”

“But what problem does it solve?”

When I see product descriptions, I often have no idea, what problems do those products solve. Take docker for example: “An open platform for distributed applications for developers and sysadmins”. Now I know why people like docker, but it is only because I used it.

Recently, I’ve been talking with friends about elm and they asked questions like: “Can I use it with Angular or other framework?” or “Is is hard to debug generated JavaScript?” I used elm a little bit and those questions simply do not make sense. People ask them because they tend to think about languages compiled to JavaScript as of syntactic sugar making JS less painful. Elm is so much more than that! Elm makes writing browser apps enjoyable! Lets see what problems does it solve.

Debugging runtime exceptions

Elm forces you to write correct code. Static typing and functions without side effects force the developer to structure the code nicely. If it compiles, it will run without errors. 100% guarantee! The program logic may still be wrong, but hey! We are talking about compilers – not oracles. If someone asks you, how do you debug JavaScript provided by elm, the answer is: you don’t. I was never forced to read generated JavaScript and I don’t have to know, how it works. It just does. Fixing compilation errors is much simpler than dealing with JS errors, because of great error messages.

Templating

One of standard elm libraries is called Html, which is used to generate (surprise, surprise!) HTML. Every element is a function, that takes two arguments: a list of attributes and a list of child elements. Check it out!. This is seriously huge! No more templating languages with their limitations. I have the full power of a real language. I can easily print recursive structures and group elements or entire widgets as functions, that can be parameterized. All things that are hard to do in templating languages, become easy. The notation is also very succinct and readable.

CSS preprocessor

SASS, LESS and other CSS preprocessors give me variables, arithmetic operations and other things, that make CSS more manageable. In Elm I can do the same things out of the box, because style is simply one of attributes. If my templating language gives me the full power of a regular programming language, then I can use it for CSS too! I am not sure, if it is good idea… But it is possible!

Semantic package versioning

Have you ever upgraded a library (only minor release) to see, that it actually changed API? Elm static typing can detect, if the library API changed and enforce incrementing the major version number. Sweet!

Updating DOM

Updating DOM is painful in JavaScript. Multiple functions can update a DOM element. Some of them are triggered by changing some other DOM elements. It can lead to a big mess. John Carmack once said: “Everything that is syntactically legal that the compiler will accept will eventually wind up in your codebase”. It is not enough to be careful. It is natural, that JavaScript/JQuery apps become a mess.

Elm has only one way of updating DOM. It is a function that takes application model and returns Html. No messing with the state – everything is generated from scratch on every model update. OK, not exactly. It works like in ReactJS. It generates a virtual dom, diffs it with the previous virtual dom and applies a minimal set of changes to the actual DOM. It is fast and it is conceptually simple.

Structuring code

Elm doesn’t allow circular dependencies between the modules. Hurray! There is also tutorial about creating reusable code and composition in elm.

Testing

Testing is much easier, when I don’t have to deal with the state. No more mocks! Only functions with arguments and return values.

Signals

Learning elm requires learning couple of unfamiliar concepts too. Functions in elm do not have side effects, so how can I change something on the screen? I can define values changing over time. They are called Signals. The user inputs are signals. Combining user input with the current model produces a new model, so there is a signal of models. Models are translated into views to produce a signal of HTML. In elm every application is just a signal of HTML. It may sound very formal, but it really makes sense.

Signal of user inputs -> user input + previous model = new model -> Signal of models -> model renders to Html -> Signal of Html.

Higher order functions on signals

I use functional programming in my day job, so I am used to transforming lists with higher order functions. The same concept is applied to Signals. It took me some time to grasp, that stream of events can be processed with the same set of functions as normal lists. Beautiful idea!

Addresses and mailboxes

Signals have their mailboxes with addresses. If an element will be used to generate user input, it needs to have an address. It looks a little bit like in Erlang, so I like it very much, but it may seem foreign for newcomer.

Interacting with JS libraries

JavaScript can be hard to write, but there are too many proven libraries to throw it all away. Elm lets developers interact with JS libraries, but they need to show, what types are expected on the elm side of things. It requires some boilerplate, but is easy to do.

Summing up

Elm is really easy to learn, much easier than Haskell for example. Still, it is not exactly effortless. On the other hand, it promises easy to extend, maintainable code. It is not only a language better than JavaScript. It is a full platform for writing browser applications, better than anything I’ve seen so far! And I haven’t even mentioned time traveling debugger yet!

After only couple of days of learning, I felt much more productive writing webapps. So? What are you waiting for?