Strange `CaseClauseError`

There are no more errors @benwilson512!
Only that the generated token seems to not have a payload when I paste it into the debugger in http://jwt.io.
I might be doing something wrong along the way. Something like a logical error

You’re passing in nil as the payload.

2 Likes

You mean jwt is not the payload? This is the one aspect I find it hard to understand with Joken even after going thru its documentation. I am using 2.0

What version of Joken are you on?

2 Likes

Joken 2.0 @benwilson512

Right, so your issue is that https://hexdocs.pm/joken/Joken.html#generate_and_sign/4 isn’t really built to be called explicitly, the docs call for you to have a MyApp.Token module that handles this stuff. The first arg to https://hexdocs.pm/joken/Joken.html#generate_and_sign/4 is the token configuration. If you look at some examples you’ll see that if you want to encode stuff like the user id and email that should be done as so:

extra_claims = %{"user_id" => "some_id"}
token_with_default_plus_custom_claims = MyApp.Token.generate_and_sign!(extra_claims)
2 Likes

So with my case it should be

token_with_default_plus_custom_claims = MyApp.Token.generate_and_sign!(jwt)

?

Yes, after you create that module in accordance with the Joken docs.

2 Likes

I actually already have gone thru the documentation but what I can’t seem to do is the conversion of

%{data: %{id: user.id, email: user.email, username: user.username}, sub: user.id}

into a format that I can easily convert into

def token_config do
    default_claims()
    |> add_claim("some_claim", nil, &(&1 == "some value"))
  end

should I add each claim one by one lilke

...
|> add_claim("id", nil, &(&1 == user.id))
|> add_claim("email", nil, &(&1 == user.email))
|> add_claim("username", nil, &(&1 == user.username))
...

?

I’m not a JWT power user or anything but can’t you just do

  def render("token.json", %{user: user}) do
    data = %{id: user.id, email: user.email, username: user.username}
    jwt = %{data: data, sub: user.id}
    token = MyAppWeb.Token.generate_and_sign!(jwt)
    %{token: token}
  end
3 Likes

The user case as the most generic clause has to come last, alternatively you could make it user = %User{} or something similar.

2 Likes

yes @NobbZ thank you so much!
Is user = %User{} -> offering the same advantage as somewhat like ensuring that the input is of the same User struct?

It is basically the same as an imaginary user when is_struct(user, User) -> ….

I’m not sure what you otherwise mean by " offering the same advantage as somewhat like ensuring that the input is of the same User struct".

I guess @NobbZ I was referring to somewhat like a typesafety advantage that is :slight_smile: