question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

It is not possible to pass Authorization header to WebSocket

See original GitHub issue

Intended outcome:

Since Apollo Client 2 it is not possible to pass custom HTTP Header to WebSocket connection. In Apollo Client 1 it was possible by Middleware, but since version 2 it is not. I tried with additional link concat, or by applying Middleware to subscriptionClient.

Sample with authorized link:

  const httpLink = createHttpLink({ uri: `https://ws.server.local/graphql` });
  const wsLink = new WebSocketLink({
    uri: `wss://ws.server.local/graphql`,
    options: {
      reconnect: true,
    },
  });

  const middlewareLink = new ApolloLink((operation, forward) => {
    operation.setContext({
      headers: {
        authorization: getBearerToken() || null,
      },
    });
    return forward(operation);
  });

  const authorizedLink = middlewareLink.concat(wsLink);

  const link = split(
    ({ query }) => {
      const { kind, operation } = getMainDefinition(query);
      return kind === 'OperationDefinition' && operation === 'subscription';
    },
    authorizedLink,
    httpLink,
  );

  const client = new ApolloClient({
    link: link,
    ...
  });

Sample with subscriptionClient Middleware

  const httpLink = createHttpLink({ uri: `https://ws.server.local/graphql` });
  const wsLink = new WebSocketLink({
    uri: `wss://ws.server.local/graphql`,
    options: {
      reconnect: true,
    },
  });

  const subscriptionMiddleware = {
    applyMiddleware(options, next) {
      console.log(options);
      options.setContext({
        headers: {
          authorization: getBearerToken() || null,
        },
      });
      next();
    },
  };

  wsLink.subscriptionClient.use([subscriptionMiddleware]);

  const link = split(
    ({ query }) => {
      const { kind, operation } = getMainDefinition(query);
      return kind === 'OperationDefinition' && operation === 'subscription';
    },
    wsLink,
    httpLink,
  );

  const client = new ApolloClient({
    link: link,
    ...
  });

Versions

  System:
    OS: macOS High Sierra 10.13.6
  Binaries:
    Node: 9.5.0 - /usr/local/bin/node
    npm: 5.6.0 - /usr/local/bin/npm
  Browsers:
    Chrome: 69.0.3497.100
    Firefox: 60.0.2
    Safari: 12.0
  npmPackages:
    apollo-boost: ^0.1.3 => 0.1.15 
    apollo-client: ^2.4.2 => 2.4.2 
    apollo-link-ws: ^1.0.9 => 1.0.9 
    react-apollo: ^2.0.4 => 2.1.11 

Issue Analytics

  • State:closed
  • Created 5 years ago
  • Reactions:11
  • Comments:17

github_iconTop GitHub Comments

233reactions
pyankoffcommented, Dec 27, 2018

Struggled with adding async function for connection params, was getting start received before the connection is initialised error. Fixed it by adding lazy: true to connection options:

const wsLink = new WebSocketLink({
  uri: WS_URL,
  options: {
    lazy: true,
    reconnect: true,
    connectionParams: async () => {
      const token = await getToken();
      return {
        headers: {
          Authorization: token ? `Bearer ${token}` : "",
        },
      }
    },
  },
})

Just in case someone having the same issue.

19reactions
LermanRcommented, Feb 13, 2020

@dreamer01 If i understand currently your question is like mine. If so then on WebSocketLink you can only pass tokens on connect. if your token expires and you get a new one, you need to reconnect with the new tokens. here is an example. And if that wasn’t your question, then maybe it will help someone else… 😃

Read more comments on GitHub >

github_iconTop Results From Across the Web

HTTP headers in Websockets client API - Stack Overflow
Sending Authorization header is not possible. Attaching a token query parameter is an option. However, in some circumstances, it may be undesirable to...
Read more >
Authentication - websockets 10.4 documentation
Assume the web application obtained authentication credentials, likely a token, from the HTTP server. There's four options for passing them to the WebSocket...
Read more >
Why can't websockets support custom headers?
Note that the WebSockets protocol itself supports custom headers since it starts with a HTTP handshake similar to a normal HTTP request.
Read more >
Creating the Web Socket Connection - FICO
You must supply the bearer token for the authorization header when opening the socket. ... It is not possible to reconnect to the...
Read more >
Token-based Header Authentication for WebSockets behind ...
The RFC6455 spec that defines WebSockets definitely allows for passing back token-based authentication through the request header.
Read more >

github_iconTop Related Medium Post

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found