HTML templates vs the IO Monad

Dario Mannu - May 7 - - Dev Community

Can an HTML template be thought of a Monad, somehow? Maybe the IO Monad in particular?

const CoordsDisplay = (initial: Coords = [0, 0]) => {

  const coords$ = new BehaviorSubject(initial).pipe(
    map(([x, y]) => `( ${x} : ${y} )`)
  );

  return rml`
    <div onmousemove="${eventXY(coords$)}"></div>
    <span>${coords$}</span>
  `;
};
Enter fullscreen mode Exit fullscreen mode

Full source here

Comparing a Rimmel template (a rml tagged template literal) to the IO Monad can help in understanding the side-effects management and data-driven nature of UI rendering in functional programming, but there are some distinctions to consider.

IO Monad

The IO Monad in languages like Haskell is a construct used to manage side effects, ensuring that they remain pure until executed in the main program. It encapsulates operations that would otherwise cause them (e.g.: reading from or writing to the console) and only executes them as part of the program's run sequence. This way, even side-effectful operations can be composed and passed around like pure functions until they are explicitly executed.

RML Template in Rimmel.js

A Rimmel template does render HTML based on the current state, which is typically reactive data streams (e.g.: using RxJS Observables).

This process:

  • Transforms reactive data into a DOM representation.
  • Manages side effects (DOM manipulations) inherently because rendering alters the state of the webpage.
  • Remains declarative, specifying what the UI should look like for a given state rather than how to build the UI step-by-step.

Comparison

  • Encapsulation of Side Effects: Both the IO Monad and Rimmel templates manage side effects. The IO Monad does so by encapsulating side effects that don't execute until the monad is "run" at the application's outermost layer. Rimmel templates encapsulate DOM updates, which can be seen as side effects, in a way that they're only applied when the data streams emit new values.
  • Declarative Nature: The IO Monad is about defining operations that will happen, keeping them pure until execution. Rimmel templates are also declarative, describing what the DOM should look like based on the state but abstracting away the direct manipulative steps.

  • Execution Context: IO operations in the IO Monad remain inert until they are explicitly invoked in the application's main execution context. Rimmel templates react automatically to changes in the underlying data streams; their "execution" (DOM updates) is triggered by these changes, not by an explicit call at the application's entry point.

While there are parallels in managing side effects and maintaining a declarative style, Rimmel templates act more automatically and are deeply integrated with reactive programming patterns, differing from the IO Monad's manual and explicit control flow.

Thus, while not a perfect match, thinking of Rimmel templates in light of the IO Monad can be useful for understanding the separation and management of side effects in a declaratively structured environment.


Rimmel.js is a functional-reactive UI library that supports and encourages the use of purely functional models, view-models and components, taking care of the DOM manipulation, making their integration natural and seamless.

. . . . . . . . . . . . . . . . . .