Navigation

Patch vs Navigate

What each navigation mode actually does to the socket

  • Link
  • handle_params

Key concepts

patch and navigate both keep the browser on the same page without a full reload, but they do different things to the LiveView process underneath: patch calls handle_params/3 on the LiveView that's already running; navigate mounts a brand new one, in the same connection.

link_demo_live.ex
defmodule MyAppWeb.LinkDemoLive do
  use MyAppWeb, :live_view

  def mount(_params, _session, socket) do
    # Stored in the process dictionary, not an assign, specifically so it
    # survives a remount: every route in this app's router lives in the
    # single default (unnamed) live session, so `navigate` reuses the same
    # BEAM process even though it calls `mount/3` again from scratch.
    mount_count = Process.get(:link_demo_mount_count, 0) + 1
    Process.put(:link_demo_mount_count, mount_count)

    socket = assign(socket, mount_count: mount_count, params_update_count: 0, current_path: "")
    {:ok, socket}
  end

  def render(assigns) do
    ~H"""
    <.react
      name="LinkDemo"
      currentPath={@current_path}
      mountCount={@mount_count}
      paramsUpdateCount={@params_update_count}
      socket={@socket}
    />
    """
  end

  def handle_params(_params, uri, socket) do
    %{path: path} = URI.parse(uri)

    socket =
      assign(socket,
        current_path: path,
        params_update_count: socket.assigns.params_update_count + 1
      )

    {:noreply, socket}
  end
end

How it works

mount_count is stored in the process dictionary, not in an assign, specifically so it survives a remount — every route in this app's router lives in the single default (unnamed) live session, so navigate reuses the same BEAM process even though it calls mount/3 again from scratch.

Click "patch": the URL changes, params_update_count goes up, mount_count does not — same process, same mount, only handle_params/3 ran again. Click "navigate": mount_count goes up too — a fresh LiveView, reusing the connection but not the state.