Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

allow access to handshake headers #648

Closed
benzen opened this issue Mar 14, 2014 · 19 comments
Closed

allow access to handshake headers #648

benzen opened this issue Mar 14, 2014 · 19 comments

Comments

@benzen
Copy link

benzen commented Mar 14, 2014

When establishing the connection, i can 'access' to query string via io.connect(url, {query:'key=value'})

I expected to be able to do something similar with the headers.

I would like to use this to build webapi, with token authentication.

@oddui
Copy link

oddui commented May 5, 2014

Would like to have this as well.

I think it might be better to say to 'set' the headers when making the request.

@rauchg
Copy link
Contributor

rauchg commented May 5, 2014

The problem with expecting header changes is that certain transports don't allow them:

  • WebSocket does not allow custom headers
  • JSONP Polling (aka <script>) don't allow them

The only condition that would allow us to set specific headers is by forcing socket.io to only use XHR Polling

@facundoolano
Copy link

I was expecting something similar to be able to authenticate the clients. Sending an authorization token (or a password) in the query string is not a good idea.

@facundoolano
Copy link

I've created a module to send credentials in the body instead: https://github.com/invisiblejs/socketio-auth

@mcm-ham
Copy link

mcm-ham commented Jan 15, 2015

@rauchg can you explain that further, the documentation at https://github.com/Automattic/socket.io/wiki/authorizing#handshaking says:

The handshake is initiated with either an XHR request or a JSONP request

Because:

Users might want to authorize the clients based on information from the headers or IP address

Since:

Not all transports sends headers when they attempt to establish a real time connection with the server

So doesn't this indicate it can still establish a WS connection even though handshake was in XHR, and therefore using request headers for authorization is fine?

@mcm-ham
Copy link

mcm-ham commented Jan 18, 2015

It looks like you did have code for it at one stage #344 (comment)

So I'm guessing there were issues so it never made it to the main repo apart from cookies which looks like it has since been removed. In which case it'd be good to update the server documentation which is a bit misleading http://socket.io/docs/server-api/#namespace#use%28fn:function%29:namespace

var io = require('socket.io')();
io.use(function(socket, next){
  if (socket.request.headers.cookie) return next();
  next(new Error('Authentication error'));
});

as it indicates cookies (i.e. headers) can be used for authentication. And add a replacement to the obsolete authentication wiki document on the main site with examples for authentication and mention of problems with other approaches as I'm sure it's a common scenario.

@ruzz311
Copy link

ruzz311 commented Feb 9, 2015

+1 for some resolution to this. The docs and examples ate up my time as I expected better access to setting headers for token auth as well.

@ktoh
Copy link

ktoh commented Oct 9, 2015

+1. There is an upcoming release of engine.io client which enables access to headers, which should facilitate resolving this issue.
socketio/engine.io-client#379

@netpoetica
Copy link

Is this available from the client JS library as well? Also, did it ever actually get in? I see it is merged but I don't think it's operational, could be wrong

@vvatikiotis
Copy link

+1. I've run into a similar situation where I need to authenticate browser clients. socket.io-client doesn't seem to allow it.

@WestleyArgentum
Copy link

+1 any updates on this?

@oooookk7
Copy link

Any updates on this?

1 similar comment
@calidion
Copy link

Any updates on this?

@darrachequesne
Copy link
Member

darrachequesne commented Jun 4, 2017

Since 2.0.0, you can now provide an extraHeaders object:

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

Added to the documentation here.

@4nubhav
Copy link

4nubhav commented Aug 29, 2019

Since 2.0.0, you can now provide an extraHeaders object:

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

Added to the documentation here.

I'm getting the following CORS error with this although I'm using cors with express:

Response to preflight request doesn't pass access control check: It does not have HTTP ok status.

@neg3ntropy
Copy link

@4nubhav you have to pass a handlePreflightRequest function like this:

    handlePreflightRequest: (request, response) => {
        const headers = { ... };
        response.writeHead(200, headers);
        response.end();
    }

@rohitnishad613
Copy link

rohitnishad613 commented May 27, 2020

Since 2.0.0, you can now provide an extraHeaders object:

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

Added to the documentation here.

I use .of("/path") in the Socket server then what I do where I declare URL.

@alielmajdaoui
Copy link

@4nubhav you should allow that header with handlePreflightRequest on the server-side.

const options = {
	handlePreflightRequest: (req, res) => {
	 	res.writeHead(200, {
	 		'Access-Control-Allow-Headers': 'x-clientid', // <<< this
	 	});
	 	res.end();
	 },
};
const io = require('socket.io')(server, options);

@darrachequesne
Copy link
Member

Update: in Socket.IO v3, the transportOptions is not needed anymore, you can simply use:

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

Documentation for CORS:

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests