Skip to content
This repository has been archived by the owner on Apr 17, 2023. It is now read-only.
/ graphql-testx Public archive

A GraphQL server for testing GraphQL applications or libraries based on Graphback

License

Notifications You must be signed in to change notification settings

aerogear/graphql-testx

Repository files navigation

graphql-testx

graphql-testx is a full-featured GraphQL server, based on Graphback and Apollo Server. With the minimum configuration required, you have a server ready for testing GraphQL client applications or libraries. Unlike mocking alternatives, graphql-testx offers persistent data between queries and mutation using in-memory SQLite database.

graphql-testx

Getting Started

Installation

Using npm:

npm install graphql-testx

or yarn:

yarn add graphql-testx

Usage

// create the server using a data model
const server = new TestxServer({
  schema: `
    type Item {
      id: ID!
      name: String!
      author: String
    }`
});

// start the server
await server.start();

// retrieve the server url
console.log(`Running on ${await server.httpUrl()}`);

// ...

// close the server once you finish otherwise it
// will not allow nodejs to exit
await server.close();

Under to hood we use Graphback to parse the Type Definitions/Data Model and generate the GraphQL schema and resolvers. See the Graphback Docs on Data Model Definition

Create the client

graphql-testx doesn't provide any graphql client, which means that you can use the server.httpUrl() graphql endpoint with your preferred client or your own developed client.

What's next?

Going throw the Examples is the best way to start, we have different examples that shows how to use graphql-testx using different graphql clients and javascript test frameworks.

Examples

Contributing

Read our contributing guide if you're looking to contribute.

Documentation

TestxServer

Generate the GraphQL server form the given Data Model and provides a set of useful methods. The database and the GraphQL resolvers are generated by Graphback.

Example

import { TestxServer } from "graphql-testx";

const server = new TestxServer({
  schema: `
    type Item {
      id: ID!
      name: String!
    }`
});

await server.start();

console.log(`Running on ${await server.httpUrl()}`);

await server.close();

options

The TestxServer constructor accept multiple options.

new TestxServer(options);

schema: string

The Graphback Data Model Definition used to generate the database and the server.

database: Database

A custom database object that implement the Database and will substitute the default SQLiteDatabase.

serviceBuilder: ServiceBuilder

A custom ServiceBuilder method to create a custom GraphbackCRUDService that will be used by the TestxServer.

bootstrap(): Promise<void>

Generate the GraphQL server, the GraphQL resolvers, the client queries/mutations/subscriptions and the database.

// server: TestxServer
await server.bootstrap();

start(): Promise<void>

Start or re-start the GraphQL server.

// server: TestxServer
await server.start();

If used without calling the bootstrap() method it will do it for you.

If used at the first time or after the close() method it will start the server to a random port on localhost.

If used after the stop() method it will re-start the server on the previous port.

If the server is already running it will return immediately.

stop(): Promise<void>

Stop the GraphQL server, so that it can be restarted on the same port, and also preserve the database.

// server: TestxServer
await server.start();
await server.stop();
await server.start(); // re-start

It is useful to test the client behavior when the GraphQL server is not reachable.

If the server is not running it will return immediately.

close(): Promise<void>

Close the GraphQL server and the database.

// server: TestxServer
await server.start();
await server.close();

httpUrl(): Promise<string>

Return the http url to the GraphQL server after starting the server.

// server: TestxServer
await server.start();
console.log(`Running at ${await server.httUrl()}`);

wsUrl(): Promise<string>

Return the websocket url to the GraphQL server after starting the server.

// server: TestxServer
await server.start();
console.log(`Running at ${await server.wsUrl()}`);

The websocket url can be used to subscribe to the server like in this example: ./examples/apollo-client/test/subscriptions.spec.ts

cleanDatabase(): Promise<string>

Remove all data from the database.

// server: TestxServer
await server.start();

// some mutations

await server.cleanDatabase();

It can be useful to reset the server state to a known point before each tests.

setData(data: ImportData): Promise<void>

Clean the database and insert the passed data directly to the database without passing through GraphQL mutations.

// server: TestxServer
await server.bootstrap();
await server.setData({
  item: [
    { id: 1, name: "one" },
    { id: 2, name: "two" }
  ]
});

It can be useful to reset the server to an initial state before each tests without triggering subscriptions, or data business logics.

If you don't know the database structure you can use the getDatabaseSchema() method.

getGraphQlSchema(): Promise<string>

Return the generated GraphQL schema.

// server: TestxServer
await server.bootstrap();
console.log(await server.getGraphQlSchema());
type Item {
  id: ID!
  name: String!
}

input ItemInput {
  name: String!
}

input ItemFilter {
  id: ID
  name: String
}

type Query {
  findItems(fields: ItemFilter!): [Item!]!
  findAllItems: [Item!]!
}

type Mutation {
  createItem(input: ItemInput!): Item!
  updateItem(id: ID!, input: ItemInput!): Item!
  deleteItem(id: ID!): ID!
}

type Subscription {
  newItem: Item!
  updatedItem: Item!
  deletedItem: ID!
}

getDatabaseSchema(): Promise<{[table: string]: string[]}>

Return the generated database schema.

// server: TestxServer
await server.bootstrap();
console.log(await server.getDatabaseSchema());
{
  item: ["id", "name", "created_at", "updated_at"];
}

getQueries(): Promise<{[query: string]: string}>

Return ready-to-use client queries.

// server: TestxServer
await server.bootstrap();
console.log((await server.getQueries()).findAllItems);
query findAllItems {
  findAllItems {
    ...ItemFields
  }
}

fragment ItemFields on Item {
  id
  name
}

getMutations(): Promise<{[query: string]: string}>

Return ready-to-use client mutations like for getQueries().

getSubscriptions(): Promise<{[query: string]: string}>

Return ready-to-use client subscriptions like for getQueries().

TestxController

Controls the TestxServer remotely using the TestxDirector.

The TestxController is used in combination with the TestxDirector in the Karma example in order to start/stop the server, and clean the database from the browser.

 TestxDirector.start()     | Browser
          |
POST / { name: "start" }
          |
    TestxController        |
          |                | Node.js
  TestxServer.start()      |
import { TestxServer, TestxController } from "graphql-testx";

// server: TestxServer
const controller = new TestxController(server);
await controller.start();

console.log(`Controller running on ${await controller.httUrl()}`);

await controller.close();

start(port?: number): Promise<void>

Start the TestxController API to a random available port on localhost or to the passed port.

httpUrl(): Promise<string>

Return the http url to the TestxController API.

stop(): Promise<void>

Stop and close the TestxController and the TestxServer

TestxDirector

Client API for the TestxController that implements all TestxServer methods.

Is used in combination wit the TestxController.

import { TestxDirector } from "graphql-testx/director";

// controller: TestxController
// controllerHttpUrl = await controller.httpUrl();
const director = new TestxDirector(controllerHttpUrl);

await director.start(); // start the TestxServer
await director.httUrl(); // TestxServer http url
// ... all others TestxServer methods
await director.close(); // close the TestxServer