This journal is generated by AI
Haskell: Typeclassopedia, IO, and Documentation
This week was heavily Haskell-focused. I worked through the Typeclassopedia, Learn You a Haskell Chapter 9 (Input and Output), and Real World Haskell Chapter 7 (IO), plus the Haddock markup guide.
- Monad vs Applicative: The structure of an Applicative computation is fixed; a Monad’s structure can depend on intermediate results. That’s why
(>>=)(bind) is strictly more powerful than(<*>). Prefer Applicative when you don’t need that—it can allow parallelization where monadic code cannot. - Reader, Writer, State: The
(->) ereader monad gives a read-only environment;Writeraccumulates a monoidal log;State s aiss -> (a,s)for stateful computations. All live inControl.Monadand the mtl library. - IO in practice:
getContentsdoes lazy I/O;interactcaptures the pattern of “read, transform, output.” UsewithFilefor handle-based file I/O. PreferMaybe/Eitherin pure code and reserve exceptions for the IO part; catch withSystem.IO.Error.catchand predicates likeisDoesNotExistError. - Haddock: Use
-- |before or-- ^after declarations; document arguments inline. Headings with-- *,-- **; link identifiers with single quotes/backticks and modules with double quotes; code blocks with@...@or bird tracks>.
Use Bun for Shell Scripts
I published a post on using Bun for cross-platform shell scripts on Windows. Bun avoids shebang and WSL/Git-bash setup while giving a single runtime for ad-hoc commands and full scripts.
- Single binary:
bun build ./script.ts --compile --outfile scriptproduces a native executable, so no shebang or interpreter is needed on Windows. - Bun Shell:
Bun.$builds shell commands from template literals (similar to zx). On Windows, Bun ships with MSYS for a consistent bash environment. - Extras:
Bun.secretsfor the OS keystore, built-in globs, YAML, ANSI. Fast startup (~5ms vs Node’s ~25ms for simple scripts) helps for small, frequent scripts.
Sources:
How I Estimate Work
Sean Goedecke’s post reframes estimation as a political and constraint-satisfaction problem rather than a pure “how long will this take?” question.
- Context first: Gather political context before looking at code—pressure on the project, what kind of estimate the chain wants, whether this is a casual ask or a must-have.
- Inversion: The job isn’t “break down work to get a duration.” It’s “find the set of software approaches that fit the timeline they already have in mind.”
- If you don’t estimate: Someone less technical will estimate for you. Engaging with the process lets you steer which approaches are in scope.
Obsidian Links
- Readwise Sync 2026-02-07
- Brent Yorgey - Typeclassopedia (Highlights)
- Miran Lipovača - Learn You a Haskell for Great Good Chapter 9. Input and Output (Highlights)
- Bryan O’Sullivan et al. - Real World Haskell Chapter 7. IO (Highlights)
- Haddock Authors - Documentation and Markup (Highlights)
- Sean Goedecke - How I estimate work (Highlights)
- JavaScript Shell Scripting