Programming Phoenix LiveView: B6.0 pg 56 - current-user not set

It seems the second code snippet is missing the code to set the current_user:

current_user: Accounts.get_user_by_session_token(session["user_token"]),

and on the previous page (55), the last sentence repeats the word “also”

it is also also protected

You are correct! Check out the corrected code here Programming Phoenix LiveView: Session Data B6.0 (p. 56)

ok thanks, and while we are on the subject, I am having a problem with the live_session work flow not going the way the book says. Im on Phoenix 1.6.0, and if I implement AuthLive the way the book has it, I first get an exception that UserAuthLive doesn’t implement mount/3

Request: GET /guess
** (exit) an exception was raised:
** (UndefinedFunctionError) function PentoWeb.UserAuthLive.mount/3 is undefined or private

I tried adding a trivial mount function

def mount(_, _, socket) do
      {:cont, socket}
  end

which clears the error, but on_mount is never called, so current_user never gets put into the assigns. I thought maybe I would try grabbing the data in mount since that one is being called, but it is being called with empty maps on &1 and &2.

My route is just like in the book:

live_session :default, on_mount: PentoWeb.UserAuthLive do
    live "/guess", PentoWeb.WrongLive
  end

Any ideas about what I might be doing wrong? I realize this is not necessarily the forum to ask for debugging help but I am doing exactly what is in the book and figured I would ask here first in case it’s something simple.

Hmm interesting. I’m not having that same issue. I’m running Phoenix 1.6.2 and LiveView 0.17.5.

Here’s my router:

scope "/", PentoWeb do
    pipe_through [:browser, :require_authenticated_user]

    live_session :default, on_mount: PentoWeb.UserAuthLive do
      live "/guess", WrongLive
    end
#...

and my UserAuthLive module:

defmodule PentoWeb.UserAuthLive do
  import Phoenix.LiveView
  alias Pento.Accounts

  def on_mount(_, params, %{"user_token" => user_token} = _session, socket) do
    socket =
      socket
      |> assign(:current_user, Accounts.get_user_by_session_token(user_token))
    if socket.assigns.current_user do
      {:cont, socket}
    else
      {:halt, redirect(socket, to: "/login")}
    end
  end
end

Ok I have it working now but not really sure if I did it right. First I had to update live view to 0.17.0, because according to the docs this feature was only added in 017.0, which I think is odd because surely the book was written against an older version. Then I used the on_mount directive in WrongLive:

defmodule PentoWeb.WrongLive do
  use  Phoenix.LiveView
  alias PentoWeb.Router.Helpers, as: Routes
  alias Pento.Accounts
  on_mount PentoWeb.UserAuthLive

and modify the signature of on_mount in UserAuthLive according to the docs:

def on_mount(:default, _, %{"user_token" => user_token} = session, socket) do

That got on_mount being called, but it was getting called without any data:

Request: GET /guess
** (exit) an exception was raised:
** (FunctionClauseError) no function clause matching in PentoWeb.UserAuthLive.on_mount/4
(pento 0.1.0) lib/pento_web/live/user_auth_live.ex:5: PentoWeb.UserAuthLive.on_mount(:default, %{}, %{}, phoenix.LiveView.Socket<assigns: %{changed: %{}, flash: %{}, live_action: nil}, endpoint: PentoWeb.Endpoint, id: “phx-FtRahGg3HTi5cqYk”, parent_pid: nil, root_pid: nil, router: PentoWeb.Router, transport_pid: nil, view: PentoWeb.WrongLive, …>)

I then removed the live_session declaration from router.ex:

 # live_session :default, on_mount: PentoWeb.UserAuthLive do
 #   live "/guess", PentoWeb.WrongLive
 # end

and added back the original route:

scope "/", PentoWeb do
    pipe_through [:browser, :require_authenticated_user]

    live "/guess", WrongLive
    get "/users/settings", UserSettingsController, :edit
    put "/users/settings", UserSettingsController, :update
    get "/users/settings/confirm_email/:token", UserSettingsController, :confirm_email
  end

And now it works, I am getting the current_user through the whole flow.

Hi,
I have the same problem and I solved it updating the version of live_view.
In your mix.exs you have to set another version. (I used the same version of [SophieDeBenedetto])

{:phoenix_live_view, "~> 0.17.5", override: true},

Then, you have to execute this in your project

mix deps.get

I hope it helps

I had the same problem. At the top of Router I had alias PentoWeb.WrongLive that was cause of the problem.

For the code addition to be made to file auth/pento/lib/pento_web/router.ex on p58 (by page numbering) change:
“Add this live_session definition in the router within the scope “/”, PentoWeb scope definition:”

to:
“Add this live_session definition in the router within the scope “/”, PentoWeb scope definition above where you specify the actual route (live “/guess”, WrongLive):”

or similar wording, or include the route in the code snippet. Otherwise, the map will not be updated prior to hitting the user’s function, which may not be obvious to beginners :slight_smile:

For the code, pp 79-80:
generators/pento/priv/repo/seeds.exs

When you copy/paste the code example from the PDF you miss the part:
name: “Table Tennis”,
description: “Bat the ball back and forth. Don’t miss!”, sku: 15_222_324,
unit_price: 12.00

because it somehow falls at end of the page, outside of the rest of the code entry.