I believe the feature you are asking for is called "live queries" which are not yet implemented (in 11/02/2018). For now the best is to use subscriptions to approximate to that.
What I would like is to run all my queries through websockets. I.E. the database is the source of truth and all data is refreshed when the websocket emits a change.
Let's try to go with this approach: let's say you have only 1 subscription and you will emit a notification on that subscription everytime something changes on the database.
In most use cases, people receive the modified object and integrate it manually into the local data. Your approach seems to suggest to avoid that manual integration and just refetch the entire query anew.
For that approach, you could build a High-Order-Component (HOC) that listens to that single subscription and when it emits something, the component will force a refetch of the Apollo Query. To help us, we will use helper methods that Apollo provides to allow you to do some manual work. https://www.apollographql.com/docs/react/basics/queries.html#default-result-props
Actually, the documentation from https://www.apollographql.com/docs/react/features/subscriptions.html seems out of sync with the API documentation. Therefore, I will use a method where I start a subscription without connecting it to a component.
import { graphql } from 'react-apollo';
import gql from 'graphql-tag';
import React from 'react';
import PT from 'prop-types';
//
// Create an observable to a standalone graphql subscription.
// Any component can then observe that observable.
//
const ANYTHING_SUBSCRIPTION = gql`
subscription onAnythingChanged() {
onAnythingChanged { id }
}
`;
let anythingObservable = apolloClient.queryManager.startGraphQLSubscription({
query: ANYTHING_SUBSCRIPTION,
variables: {},
});
//
// End of observable creation.
//
const ALL_COMMENTS_QUERY = gql`
query AllComments() {
comments { id content }
}
`;
const withComments = graphql( ALL_COMMENTS_QUERY, { name: 'comments' } );
let Component = React.createClass({
propTypes: {
comments: PT.shape({
refetch: PT.func.isRequired
}),
}
componentWillMount: function () {
let anythingSubscription = anythingObservable.subscribe({
next: ( data ) => {
console.log("SUBSCRIPTION EMITTED:", data );
this.props.comments.refetch(); // Refetch comment query
},
error: ( err ) => {
console.log("SUBSCRIPTION ERROR:", err );
}
});
// In real code you should save anythingSubscription somewhere
// to destroy it in the future.
}
}
let ComponentWithCommentsAndRefetchSubscription = withComments(Component);
export default ComponentWithCommentsAndRefetchSubscription;
I hope this gives you a good starting point.
Remember that refetching all queries when anything changes is a not very efficient method. You could improve it by making the component just observe a specific category (Comments, Posts, etc.) and skip the refetch otherwise.
You can also opt to add a subscription for every component or have a global subscription somewhere in global memory (eg. Redux) that all components listen to.