1.7 KiB
1.7 KiB
Elixir Core Rules
Critical Mistakes to Avoid
- No early returns: Last expression in a block is always returned
- No list indexing with brackets: Use
Enum.at(list, i), notlist[i] - No struct access syntax: Use
struct.field, notstruct[:field](structs don't implement Access) - Rebinding in blocks doesn't work:
socket = if cond, do: assign(socket, :k, v)- bind the result, not inside %{}matches ANY map: Usemap_size(map) == 0guard for empty maps- No
String.to_atom/1on user input: Memory leak risk - No nested modules in same file: Causes cyclic dependencies
Pattern Matching & Functions
- Match on function heads over
if/casein bodies - Use guards:
when is_binary(name) and byte_size(name) > 0 - Use
withfor chaining{:ok, _}/{:error, _}operations - Predicates end with
?(notis_):valid?/1notis_valid/1 - Reserve
is_thingnames for guard macros
Data Structures
- Prepend to lists:
[new | list]notlist ++ [new] - Structs for known shapes, maps for dynamic data, keyword lists for options
- Use
Enumover recursion; useStreamfor large collections
OTP
GenServer.call/3for sync (prefer for back-pressure),cast/2for fire-and-forget- DynamicSupervisor/Registry require names:
{DynamicSupervisor, name: MyApp.MySup} Task.async_stream(coll, fn, timeout: :infinity)for concurrent enumeration
Testing & Debugging
mix test path/to/test.exs:123- run specific testmix test --failed- rerun failuresdbg/1for debugging output
Documentation Lookup
mix usage_rules.docs Enum.zip/1 # Function docs
mix usage_rules.search_docs "query" -p pkg # Search package docs