We can't find the internet
Attempting to reconnect
Something went wrong!
Hang in there while we get back on track
Use `Ecto.Multi` for complex transactions in Phoenix contexts
Manual transaction management with nested operations becomes unreadable and error-prone. Ecto.Multi provides named operations, automatic rollback, and...
Live Sessions in Phoenix LiveView: Reducing navigation time between LiveViews
The main idea behind live sessions is to reduce navigation time when navigating a group of routes. Normally what happens when navigating between LiveV...
`File.stream!/1` processes large files with constant memory
File.read!/1 loads the entire file into memory. A 2GB log file? That's 2GB of RAM. Use File.stream!/1 to process files line-by-line with constant memo...
Stop using `Repo.preload` in loops - use `preload` in queries
Calling Repo.preload/2 inside Enum.map or comprehensions creates N+1 queries - one query to fetch the parent records, then one additional query for ea...
Use `Task.Supervisor` instead of bare `Task.async`
Bare Task.async creates linked tasks that can crash your process or leave zombie tasks running. Task.Supervisor provides supervised tasks with automat...
Prevent race conditions with `Ecto.Query.lock/2`
Two users buying the last item simultaneously can cause overselling. Use PostgreSQL row locks with lock: "FOR UPDATE" to prevent concurrent updates fr...
Use `temporary_assigns` for large lists in LiveView
Sending entire lists over the socket on every LiveView update kills performance. Mark list assigns as temporary to send them once and drop them from s...
Use `send_update_after/4` for delayed LiveComponent updates
Manual timer management with Process.send_after/3 in LiveComponents creates cleanup complexity. LiveView's send_update_after/4 handles delayed updates...
Use router `on_mount` hooks instead of duplicating LiveView mount logic
Copy-pasting the same assigns across every LiveView mount/3 function creates maintenance nightmares. Router-level on_mount hooks run automatically bef...
Stop mixing LiveView handlers with JavaScript hooks
Handling the same event in both Phoenix and JavaScript creates race conditions and unpredictable behavior. Keep server logic in LiveView handlers and ...
The amazing v/1 helper function
I may be late on this one but today I learned about the v/1, a helper function that retrieves the value from a previous expression by its line number ...
Phoenix contexts should return tuples, not raise
Phoenix context functions that raise exceptions break LiveView error handling and force try/catch everywhere. Tagged tuples enable composable error ha...
Prevent duplicate Oban jobs with `unique` worker options
Multiple button clicks or retries can enqueue the same background job multiple times, causing duplicate charges, emails, or API calls. Oban's built-in...
Stop rewriting Ecto queries from scratch - use `Ecto.Query.exclude/2` instead
Building complex queries often means starting with a base query, then customizing it for different use cases. Most developers duplicate the entire que...
Fixing `Ecto.StaleEntryError` with optimistic locking patterns
Race conditions in concurrent updates cause cryptic Ecto.StaleEntryError crashes in production. The error happens when multiple processes try to updat...
copied to clipboard