# Elixir Prelude: Packing up utility functions ## Introduction I've been spending the summer in China, head-deep in [Elixir](http://elixir-lang.org/), writing interactive scripts for an [EdX MOOC on inquiry and technology for teachers](https://www.edx.org/course/teaching-technology-inquiry-open-course-university-torontox-inq101x) ([screenshots](https://imgur.com/a/rAXVz)). I will have much more to share about that project later, but now I wanted to share a small Elixir package I released on Github called [Prelude](https://github.com/houshuang/elixir-prelude) ([documentation](https://houshuang.github.io/prelude)). This is a collection of utility functions for Elixir that I've extracted out of my code base. ## Organization I began by scattering these utility functions all over as small `defp`s, but when I wanted to reuse them in other modules, I began gathering them. Initially I had a single file called Prelude - modelled after the Haskell Prelude, just because it was the only file I'd ever wholesale `import` into my other modules. Eventually I began separating the code out into sub-modules, which meant I went from ```elixir import Prelude map_atomify(...) ``` to ```elixir Prelude.Map.atomify(...) ``` which seems cleaner. ## The point of gathering "trivial" functions Many of these functions are very simple, but yet things you use all the time - gathering them together both means less repetition and greater legibility. Compare: ```elixir x |> Enum.map(fn {k, v} -> {v, k} end) |> Enum.into(%{}) ``` to ```elixir x |> Prelude.Map.switch ``` The code in the first version is short enough that I wouldn't bother making it a separate function, but the intent of the second snippet is much clearer. I might also forget to do `Enum.into(%{})`, and somehow I always forget the `end` in anonymous functions. So, some quick time saving. ## Map functions Some of the functions are a bit more involved, mainly found in the [Prelude.Map](http://houshuang.github.io/prelude/Prelude.Map.html) module. I was inspired by the way Clojurists often work with deeply nested maps, sometimes keeping the entire application state in one `atom`. This has also become relevant in Javascript-land with experiments around immutable state such as [Baobab](https://github.com/Yomguithereal/baobab). I see deeply nested maps much less often in Elixir. Part of it might be the architecture (we use gen_servers, message passing, and ETS tables, rather than atom-swapping), but part of it might also be because of the syntax (`%{%{%{}}}` is not pretty). However, Elixir already has `get_in` and `put_in` to reach into deeply nested objects. Prelude provides `deep_put`, which is a parallel to `mkdir -p`, it will insert an object and create any part of the missing path. If you put to a path that already exists, it will turn it into an array. Built on top of `deep_put` is `group_by`. Building the Phoenix app, I often had to extract data from the database using Ecto, and render it in templates. Let's say you have a table of students, listing their group affiliation, and which class their in. You wish to list all students, sorted by class, and then by group. With `group_by`, you can get the data from Ecto like this: ```elixir MyRepo.all(Student) |> Prelude.Map.group_by([:class, :group]) ``` The result will be a map of classes. Each class will point to a map of groups, and each group will point to a list of students in that group. Then in an EEx template, you can display the list like this: ```elixir <%= for class <- @classes %>