Documentation, Formatting & Code Quality
28.1 Documentation
mix docs (ExDoc) generates HTML/EPUB. Published packages get docs on hexdocs.pm. Access in IEx: h MyLib.hello.
defmodule MyLib do
@moduledoc """
Utilities for **awesome** things.
## Examples
iex> MyLib.hello()
:world
"""
@doc """
Says hello. Returns `:world`.
"""
@doc since: "1.1.0"
@spec hello() :: :world
def hello, do: :world
@doc false # hide from docs
def internal, do: :ok
end28.2 Formatter
mix format — no style debates.
[inputs: ["{mix,.formatter}.exs", "{config,lib,test}/**/*.{ex,exs}"], line_length: 98,
import_deps: [:ecto, :phoenix], plugins: [Phoenix.LiveView.HTMLFormatter]]28.3 Static analysis
Credo (mix credo --strict): style & consistency.
Dialyxir: type discrepancies.
Sobelow: Phoenix security analysis.
mix_audit: vulnerable dependencies.
mix compile --warnings-as-errors in CI.
🧪 Part II Exercises
Write WordCount.count/1 returning a map of word frequencies (case-insensitive, punctuation removed).
Model a BankAccount struct with deposit/2, withdraw/2 returning {:ok, acc} / {:error, :insufficient_funds}.
Implement a Shape protocol with area/1 and perimeter/1 for Circle, Rectangle, Triangle structs.
Parse a CSV file with File.stream! into a list of maps (header row = keys).
Implement Enumerable for a binary tree struct.
Write a Storage behaviour with InMemory and File implementations; select via config.
Group a list of people by age decade using Enum.group_by/3.
Write a comprehension that generates all Pythagorean triples with sides ≤ 30.
Build an escript that counts lines/words/chars of files (like wc), using OptionParser.
Write full ExUnit tests (with doctests and a property test) for exercises 1–3.