playwright-graphql
TypeScript icon, indicating that this package has built-in type declarations

1.0.0 • Public • Published

Playwright-graphql

This library provide playwright integration with graphql and typescript for efficient API tests. It helps you to get autogenerated graphql api client with autocomplete feature.

DEMO

To build graphql client, this library includes several graphql generators like:

Project setup:

  1. Installation.
  2. Generate schema and operations.
  3. Generate typescript types.
  4. Add graphql client fixture.
  5. Wright graphql tests with joy!

Installation

  • npm install playwright-graphql or for dev dependency
  • npm install -D playwright-graphql

Generate graphql schema from server under test

  • get-graphql-schema https://${baseUrl}/api/graphql > schema.gql

Pay attention that url should have graphql endpoint, it may be custom for your project. Now you should be able to find schema.gql file in your working directory.

Generate operations from schema

  • gqlg --schemaFilePath ./schema.gql --destDirPath ./gql/autogenerated-operations

New directory with .gql files generated gql/autogenerated-operations/.

Create codegen.ts file

Create codegen.ts file:

import type { CodegenConfig } from '@graphql-codegen/cli';

const config: CodegenConfig = {
  overwrite: true,
  schema: './schema.gql',
  documents: [
    'gql/autogenerated-operations/**/*.gql',
  ],
  generates: {
    'gql/graphql.ts': {
      plugins: ['typescript', 'typescript-operations', 'typescript-generic-sdk'],
      config: {
        scalars: {
          BigInt: 'bigint|number',
          Date: 'string',
        },
      },
    },
  },
};

export default config;

Generate types

  • graphql-codegen --config codegen.ts generates graphql.ts in gql directory.

In case you need to customize output check docs.

Add path to your tsconfig.json

Add "@gql": ["gql/graphql"] for easy import.

{
  "compilerOptions": {
    "target": "ESNext",
    "module": "ESNext",
    "moduleResolution": "node",
    "resolveJsonModule": true,
    "strict": true,
    "noUnusedLocals": false,
    "noUnusedParameters": false,
    "noFallthroughCasesInSwitch": true,
    "allowSyntheticDefaultImports": true,
    "baseUrl": "./",
    "paths": {
      "@fixtures/*": ["fixtures/gql"],
      "@gql": ["gql/graphql"]
    }
  }
}

Create gql fixture

fixtures/gql.ts

import { test as baseTest, expect, request, APIRequestContext } from '@playwright/test';
import { getSdkRequester } from 'playwright-graphql';
import { getSdk } from '@gql';

export { expect };

const getClient = (apiContext: APIRequestContext) => getSdk(getSdkRequester(apiContext));

type WorkerFixtures = {
    gql: ReturnType<typeof getClient>;
};

export const test = baseTest.extend<{}, WorkerFixtures>({
    gql: [
        async ({}, use) => {
            const apiContext = await request.newContext({
                baseURL: 'http://localhost:4000'
            });
            await use(getClient(apiContext));
        }, { auto: false, scope: 'worker' }
    ]
});

Now you are ready jump into writing tests!

tests/example.test

import { test, expect } from '@fixtures/gql';

test('playwright-graphql test', async ({ gql }) => {
    const res = await gql.getCityByName({
        name: 'Lviv'
    });

    expect(res.getCityByName).not.toBeNull();
})

More about configuration

In case you need to create custom operations for tests add one more path to documents section in codegen.ts file

import type { CodegenConfig } from '@graphql-codegen/cli';

const config: CodegenConfig = {
  overwrite: true,
  schema: './schema.gql',
  documents: [
    'gql/autogenerated-operations/**/*.gql',
    'gql/custom-operations/**/*.gql',
  ],
  generates: {
    'gql/graphql.ts': {
      plugins: ['typescript', 'typescript-operations', 'typescript-generic-sdk'],
      config: {
        scalars: {
          BigInt: 'bigint|number',
          Date: 'string',
        },
      },
    },
  },
};

export default config;

And it is recommended to put all dynamic generated files and directories into .gitignore.

gql/autogenerated-operations
gql/**/*.ts
gql/**/*.js

Graphql explorer

You can use apollo explorer to create custom queries.

Code generation scripts in package.json

  "scripts": {
    "generate:schema": "get-graphql-schema http://localhost:4000/api/graphql > schema.gql",
    "generate:operations": "gqlg --schemaFilePath ./schema.gql --destDirPath ./gql/autogenerated-operations --depthLimit 6",
    "generate:types": "graphql-codegen --config codegen.ts",
    "codegen": "npm run generate:schema && npm run generate:operations && npm run generate:types",
    "test": "npx playwright test"
  },

Second operation options parameter

Each generated operation accepts second optional parameter which represents options from post method in playwright except data and two extra options.

  • returnRawJson to return full payload in JSON format.
  • failOnEmptyData to not throw error in case of empty data. (Allows you to pars errors from payload)

That is how second parameter type is declared.

type PlaywrightRequesterOptions = {
    returnRawJson?: boolean;
    failOnEmptyData?: boolean;
} & Omit<PostOptionsType, 'data'>;

Negative test cases

By design graphql response has field data, and data is being converted to types.

In case of error graphql will not respond with 400x or 500x status codes but will add errors in to payload. That is why we need to use option: failOnEmptyData: false to verify errors.

import { test, expect } from '@fixtures/gql';

test('playwright-graphql test negative', async ({ gql }) => {
    const res = await gql.getCityByName({
        name: 'Lviv'
    }, { failOnEmptyData: false });

    expect(res).toHaveProperty('errors[0].message');
})

Template project: https://github.com/DanteUkraine/playwright-graphql-example

Readme

Keywords

Package Sidebar

Install

npm i playwright-graphql

Weekly Downloads

192

Version

1.0.0

License

MIT

Unpacked Size

11.7 kB

Total Files

5

Last publish

Collaborators

  • oleksandr-solomin