Pothos GraphQL
Searching...

Scalars

Adding Custom GraphQL Scalars

To add a custom scalar that has been implemented as GraphQLScalar from graphql-js you need to provide some type information in SchemaTypes generic parameter of the builder:

const builder = new SchemaBuilder<{
  Scalars: {
    Date: {
      Input: Date;
      Output: Date;
    };
  };
}>({});

builder.addScalarType('Date', CustomDateScalar, {});

The Input type is the type that will be used when the type is used in an argument or InputObject. The Output type is used to validate the resolvers return the correct value when using the scalar in their return type.

Adding Scalars from graphql-scalars

Similarly to adding your own custom scalars, you can utilize scalars from the graphql-scalars library by also providing the types through the SchemaTypes generic parameter.

Note that when implementing the graphql-scalars library, the JavaScript/TypeScript Input and Output types are not always intuitive. For example, you might assume that the JSON type from graphql-scalars would utilize the JavaScript JSON type, which is incorrect (it uses any). If you have trouble with typing after implementing a scalar, you should check the codegenScalarType inside file where the scalar is defined by graphql-scalars (JSON scalar definition, for reference). You should aim to match that type unless it's any, in which case you should use unknown. These files are located inside src/scalars in the graphql-scalars GitHub repository.

import { DateResolver, JSONResolver } from 'graphql-scalars';

const builder = new SchemaBuilder<{
  Scalars: {
    JSON: {
      Input: unknown;
      Output: unknown;
    };
    Date: {
      Input: Date;
      Output: Date;
    };
  };
}>({});

builder.addScalarType('JSON', JSONResolver, {});
builder.addScalarType('Date', DateResolver, {});

Defining your own scalars

const builder = new SchemaBuilder<{
  Scalars: {
    PositiveInt: {
      Input: number;
      Output: number;
    };
  };
}>({});

builder.scalarType('PositiveInt', {
  serialize: (n) => n,
  parseValue: (n) => {
    if (n >= 0) {
      return n;
    }

    throw new Error('Value must be positive');
  },
});

Using scalars

builder.queryFields((t) => ({
  date: t.field({
    type: 'Date',
    resolve: () => new Date(),
  }),

  positive: t.field({
    type: 'PositiveInt',
    resolve: () => 5,
  }),
}));