4.0.0 • Published 4 years ago

graphql-merge-unmerge v4.0.0

Weekly downloads
120
License
MIT
Repository
github
Last release
4 years ago

graphql-merge-unmerge

A function to help you merge multiple graphql queries and then un-merge the result. This allows you to submit batched queries even if the backend does not support batch queries. e.g. for GitHub this could potentially save you from hitting their rate limit, by merging all your separate queries into one large query.

Installation

yarn add graphql-merge-unmerge graphql graphql-tag

Usage

Simple

import {Batch} from 'graphql-merge-unmerge';
import gql from 'graphql-tag';
import {print} from 'graphql';

const batch = new Batch(async ({query, variables}) => {
  const r = await callGraphQLServer({query: print(query), variables});
  if (!r.data) {
    throw new Error(JSON.stringify(r.errors));
  }
  return r.data;
});

const resultA = batch.queue({
  query: gql`
    query($id: Int!) {
      user(id: $id) {
        id
        teams {
          name
        }
      }
    }
  `,
  variables: {id: 3},
});

const resultB = batch.queue({
  query: gql`
    query($id: Int!) {
      user(id: $id) {
        id
        name
      }
    }
  `,
  variables: {id: 3},
});

await batch.run();

console.log(await resultA);
console.log(await resultB);

This will run a single query that looks like:

{
  query: gql`
    query($id: Int!) {
      user(id: $id) {
        id
        name
        teams {
          name
        }
      }
    }
  `,
  variables: {id: 3},
}

and then split out the results for you.

Advanced

import merge from 'graphql-merge-unmerge';
import gql from 'graphql-tag';
import {print} from 'graphql';

const merged = merge([
  {
    query: gql`
      query($id: Int!) {
        user(id: $id) {
          id
          teams {
            name
          }
        }
      }
    `,
    variables: {id: 3},
  },
  {
    query: gql`
      query($id: Int!) {
        user(id: $id) {
          id
          name
        }
      }
    `,
    variables: {id: 3},
  },
]);

const results = merged.unmergeAllQueries(
  (
    await Promise.all(
      // Even after merging, there could still be multiple "documents"
      // representing the queries that need to be sent to the server.
      // For fairly simple queries, there will almost always just be one
      // query at the top level.
      merged.allQueries.map(({query, variables}) =>
        callGraphQLServer({query: print(query), variables}),
      ),
    )
  ).map((r) => {
    if (!r.data) {
      throw new Error(JSON.stringify(r.errors));
    }
    return r.data;
  }),
);