Do I need to bind to a component to use the apollo react client even if it has no UI?

You can use the withApollo() decorator exported from apollo-client to access the client as a prop inside a component. The ApolloProvider exposes the client to its child components through context. The withApollo() higher-order component accesses the client on context and passes it to its child as a prop.

So, if the auth.lock() function is being triggered by some type of UI interaction or one of the React lifecycle methods, you can access the client in that component and either call the mutation directly in the component or pass it as an argument through to the function that calls auth.lock().

However, since you want to access the client outside of the React tree, you have to access the client in a different way.

Alternatively, you can export the same client that you pass as a prop to ApolloProvider and import it wherever you need to use it in the app. Note, this singleton pattern won't work with server-side rendering. Example:

root.jsx

import React from 'react';
import { Router, browserHistory } from 'react-router';
import ApolloClient, { createNetworkInterface } from 'apollo-client';
import { syncHistoryWithStore } from 'react-router-redux';
import routes from './routes';

const networkInterface = createNetworkInterface({
  uri: '/graphql',
  opts: {
    credentials: 'same-origin'
  }
});

export const client = new ApolloClient({
  networkInterface
});
export const store = configureStore(browserHistory, client);
export const history = syncHistoryWithStore(browserHistory, store);

export default function Root() {
  <ApolloProvider client={client} store={store}>
    <Router
      history={history}
      routes={routes}
    />
  </ApolloProvider>
}

some-other-module.js

import { client } from 'app/root';

export default function login(username, password) {
  return client.mutate({
    // ...mutationStuff
  });
}

Tags:

React Apollo