python-socketio token authentication with tornado web server

Created on 14 Sep 2020  路  7Comments  路  Source: miguelgrinberg/python-socketio

I am using python-socketio with a tornado web server. I am trying to get the authentication token from the client and check it in tornado server via python-socketio. There is some example in JavaScript Client and NodeJS Server. I find out Flask SocketIO also has a kinda smooth implementation for token authentication. Is there any way to check the authentication token for tornado with python-socketio? Thanks.

question

All 7 comments

Do you get the token in a header? All headers are sent to you in the environ dictionary that you receive in the connect handler. This dictionary uses the standard WSGI format.

OK. I set the client URL with a token like this

        var token = "bcd"
        var socket = io.connect(location.protocol + '//' + document.domain + ':' + location.port + `?token=${token}`)

It is equivalent from the example I have seen in socketio JS client. So now I am trying to grab the token from environ['QUERY_STRING'] by slicing. But I exactly don't know when I put the real token on the client side how many I need to slice. In JS socketio server they are using middleware io.use. and get a token from it. Like this,

  let token = socket.handshake.query.token;

I want to know the equivalent implementation in Python SocketIO server.
The whole JS code client-server and middleware given below.

// client-side

const socket = io('http://localhost?token=abc');

// server-side
const io = require('socket.io')();

// middleware
io.use((socket, next) => {
  let token = socket.handshake.query.token;
  if (isValid(token)) {
    return next();
  }
  return next(new Error('authentication error'));
});

// then
io.on('connection', (socket) => {
  let token = socket.handshake.query.token;
  // ...
});

I also tried to implement these two methods on the client-side. But it's not working. Maybe I am missing something.

not working:
var socket = io("http://localhost", {
  extraHeaders: {
    Authorization: "Bearer authorization_token_here"
  }
});


not working:
const socket = io({
  transportOptions: {
    polling: {
      extraHeaders: {
        'x-clientid': 'abc'
      }
    }
  }
});

I tried this like that.

var socket = io.connect("http://localhost:8888", {
  extraHeaders: {
    Authorization: "Bearer authorization_token_here"
  }
});

But don't find Authorization or x-cliendid in environ.
So how can I get those on the server-side? Also, how can I implement the JavaScript client so those extra headers can be found in server. Thanks for your help.

Great. I have gotten what I need from the query. There is another question I have related to data updates and fetching in mongo via a specific URL. I almost see the example in nodejs express. But the issue is how I handle it in the tornado framework.

@kamranhossain are you asking me how to access your Mongo db from Tornado? I wouldn't know, that's not my area of expertise. I suppose any asyncio compatible Mongo library should work.

@miguelgrinberg , no. SocketIO, MongoDB, and auth system are working now. But I am thinking of a more better way to solve this problem. By the way, thanks for creating this amazing package. Great work. Really appreciated.

Was this page helpful?
0 / 5 - 0 ratings