• she/her

Principal engineer at Mercury. I've authored the Dhall configuration language, the Haskell for all blog, and countless packages and keynote presentations.

I'm a midwife to the hidden beauty in everything.

💖 @wiredaemon


discord
Gabriella439
discord server
discord.gg/XS5ZDZ8nnp
location
bay area
private page
cohost.org/newmoon

I'm preparing my slides for my upcoming talk on Fall-from-Grace and I spent a lot of time on just this one slide where I introduce the idea of "content-oriented" programming languages.

This is something I've been struggling to articulate for a while, but I think this explanation captures the idea best. I'm trying to explain what distinguishes a content-oriented language like Dhall/Nix/Fall-from-Grace from a "merely" purely functional language like Haskell. For example, in Haskell you mix content and presentation because you specify what to do with values (e.g. print them, save them to a file, store them in a database), but in a content-oriented language you don't specify what to do with values; the responsibility for what to do with them is delegated to something else.

One example of this is the Grace browser where the content is a pure Grace expression with no presentation logic, and the Grace browser provides the presentation half: it converts the pure Grace expression to an equivalent web form.


You must log in to comment.

in reply to @fullmoon's post:

Re: "content-oriented", a long-winded non troll question:

So in my grad pl course I'm gonna teach them to be mindful that some pl vocab have well-defined meanings, some are definable-ish, and others are very socially constructed, which is not bad. In the sense that it's easier to define "pure functional language" than "scripting language".

My question is: do you have a sense where "content oriented" falls on this spectrum? Is it the sort of notion that can be defined mathematically or does the difference elsewhere?

Yeah, I 100% get what you're referring to, which is why I spent so much time on this slide to define this in the way that would be least subject to misinterpretation. For example, the definition given here holds whether or not the "content" in question is "inert data", a function, or an effect modeled in a purely functional way.

The definition of "content-oriented" is somewhere in the middle of the spectrum ("definable-ish"). I believe you could mathematically formalize it by defining in terms of two languages (the "host" language responsible for presentation and the "guest" language responsible for content, which might be two separate languages) although I don't know if that formalization would illuminate the definition much further.

How would you compare this definition of 'content-oriented' programming from 'declarative' programming? I have often used the latter term to describe systems, languages and libraries behaving very much like you mention in your post. But declarative programming could be considered a broader category maybe? 🤔

One of the definitions I originally considered was programming free of an effect system (kind of like purely functional programming minus IO), but then I realized that definition was not satisfactory for two reasons:

  • you can still model effects in a purely functional setting (e.g. free monads, state, etc.)
  • content-oriented programming is not necessarily incompatible with effects modeled as pure code (e.g. your result can be an effect, if that's what the presentation half requires)

So what makes that different from Haskell, then? After all, one way to think about Haskell is that it's a purely functional program that returns an effect to be run. The distinction here is that the presentation half of a Haskell program (the part that executes main) is trivial (essentially the identity function): all the logic for what to do is already in the returned main expression.

If the Haskell runtime could accept mains with types other than IO and do something interesting with them then that would be more in the spirit of content-oriented programming. For example, imagine if you could have a Haskell main expression of type:

main :: Options -> IO ()

… and that would auto-generate a command-line interface for you that matched the Options type (like how optparse-generic does). That would be closer to content-oriented programming because now some of the presentation logic (the CLI interface in this case) is handled by the runtime and not the userland code.

An even more interesting content-oriented example would be if Haskell could accept a main function of type:

main :: Int -> Int

… and still do something interesting with that, depending on the context. See the Grace Browser for an example of what I mean by this.

Thank you! This makes it very clear!

One great example of something akin Haskell but with other types of 'main' functions that comes to mind is the Roc programming language. If I understood you correctly, it is a schoolbook application of the 'content-oriented' approach. For instance, programming with effects is possible in Roc exactly then when the platform exposes a hook (for 'main' function) with a signature that would accept effects.

(P.S. the link in your comment to the Grace Browser is broken; it resolves to a path relative to the cohost domain that does not exist.)

Not exactly. The idea is (sort of) that there are never userland effects (not even managed ones). The effects are always handled by the platform and every platform works with every user expression (i.e. there are no platform-specific hooks in the user code)

Another question: Can everything in which applicative functors is the most powerful abstraction that is used be considered 'content-oriented'? I think you need monads (or an equally powerful abstraction) to mix content and presentation. Or am I maybe looking at a slightly different axis of content vs. presentation than you are describing?

Using the applicative functor analogy, if you were to take an applicative expression like this:

someFunction <$> m₀ <*> m₁ <*> … <*> mₙ

… and throw away all of the ms and just keep the someFunction, that would be closer to content-oriented programming.