The Phoenix Chat, websockets

Client side, I am doing

  socket = new Socket('/socket', {
    params: { token: AuthService.loadToken() },
    logger: (kind, msg, data) => { console.log(`${kind}: ${msg}`, data); },
  });

I am storing the token into local storage.

To me, You just send a string, but not the value of the token.

params: { token: “channel_token” }

You need to store the token in the page, and retrieve it’s value. Sorry I don’t use your method for storing token in the page.

@kokolegorille How does your loadToken() function work?

Nothing too complicated… Just some methods inside a class

  loadToken() {
    return localStorage.getItem('phoenixAuthToken'); 
  }
  
  saveToken(token) {
    localStorage.setItem('phoenixAuthToken', token);
  }
  
  removeToken() {
    localStorage.removeItem('phoenixAuthToken');
  }

Do you have a repo I can review? I can’t get the token to be passed correctly.

I am not using the same flow as yours…

I am using React/Redux on the frontend, with a signin api that returns a token.

In your case, I would try to track your token.

<%= tag :meta, name: “channel_token”, content: Phoenix.Token.sign(@conn, “player auth”, @current_player) %>

First thing first, I woul not generate token inside the view, but in the controller, then pass it as a parameter to the view.

Then, in the rendered page, I would

<div><%= @token %></div>

Then, I would add an id

<div id="mytoken"><%= @token %></div>

Then I would see if I can get it with javascript…

alert(GIMME THAT TOKEN FROM id="mytoken)

I do not have a public repo for this. I don’t think it could help in your use case because of the SPA thing.

I have the token working, I wasn’t passing it in right. Now that it’s working I just need to figure out the correct"handle info" function so the Presence module can display the usernames. There are no more errors at this point though. I appreciate the help so far!

Glad You solved it

1 Like

If anyone else is having a similar issue:
This is the code to declare the token
socket.js

var token = $("meta[name=channel_token]").attr("content");
var socket = new Socket("/socket", {
    params: {
        token: token
    }
});

Sign the token in
app.html.eex:

    <%= tag :meta, name: "channel_token", content: Phoenix.Token.sign(@conn, "player auth", :player_id) %>

Then pass the token in user_socket.ex in the connect function:

    def connect(%{"token" => token}, socket) do

Any idea why how to solve, “websocket connection failed: Connection closed before receiving a handshake response” ?

1 Like

Sounds like a server issue, do you have anything between the client and phoenix, like a proxy or cache?