Reputation: 332
This is a question about the name of what appears to me to be a very common pattern in functional programming.
In pure functional programming languages like Haskell, you often have an "outer" part of the program allowed perform IO side effects like printing to the screen or writing to a data base (e.g. the IO monad), and then an inner part of the program consisting of just pure functions.
If the pure functions want to perform some kind of side effect, like printing, it can be represented as a value of an algebraic data type that is returned to the outer IO part, where it will then be executed.
Here's a somewhat contrived example:
data Command = PutStrLn String
fizz :: Int -> Command
fizz n | n `mod` 15 == 0 = PutStrLn "FizzBuzz"
| n `mod` 3 == 0 = PutStrLn "Fizz"
| n `mod` 5 == 0 = PutStrLn "Buzz"
| otherwise = PutStrLn (show n)
runCommand :: Command -> IO ()
runCommand (PutStrLn str) = putStrLn str
main :: IO ()
main = mapM_ runCommand $ map fizz [1..100]
The fizz
function is completely pure, but instead of just returning a String
I've opted for the string as well as the intended effect. Using fizz buzz here is just a toy example to show the relation between the Command
type and the effectful runCommand
function.
In a more complicated program, fizz
would be some part of my application logic, and the Command
could be e.g. representing a web API or OS calls or some other IO effect.
Is there a name for representing effectful APIs with data in this manner?
Upvotes: 4
Views: 107
Reputation: 233125
I've often seen the pure part described as an Abstract Syntax Tree (AST) of a Domain-Specific Language (DSL), and the 'run' function as an interpreter of that language.
As Fyodor Soikin mentions in the comments, free monads can be viewed as an example of that style of programming.
Gary Bernhardt calls it Functional Core, Imperative Shell.
Often the AST is defined as a recursive sum type, and since sum types are isomorphic to the Visitor pattern, you may also view the interpreter as a Visitor if you're in a more object-oriented mood. (To be clear, not in Haskell, but in other contexts.)
It seems to me that this style of programming pops up in several places independently, and often one author/inventor is unaware of prior art. Thus, you'll find different names even though there's lots of overlap.
Upvotes: 3