Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Define resolver for Custom scalar type #9

Closed
valburyakov opened this issue Jan 28, 2018 · 6 comments
Closed

Define resolver for Custom scalar type #9

valburyakov opened this issue Jan 28, 2018 · 6 comments

Comments

@valburyakov
Copy link

valburyakov commented Jan 28, 2018

I'm trying to migrate my old nestjs app with graphQL to new GraphqlModule. And i faced with problem how to define resolver for scalar type, previously i had:

scalar Date

type User {
  _id: ID!
  fullName: String
  email: String
  hireDate: Date
  pictureUrl: String
}
import { GraphQLScalarType } from 'graphql';
import { Kind } from 'graphql/language';

export const resolver = {
  Date: new GraphQLScalarType({
    name: 'Date',
    description: 'Date custom scalar type',
    parseValue(value) {
      return new Date(value); // value from the client
    },
    serialize(value) {
      return value.getTime(); // value sent to the client
    },
    parseLiteral(ast) {
      if (ast.kind === Kind.INT) {
        return parseInt(ast.value, 10); // ast value is always in string format
      }

      return null;
    }
  })
};

So how do i define resolver for Date type using nestjs annotations ?
I've tried this but it doesn't work

@Resolver('Date')
export class DateResolver {

  @DelegateProperty('Date')
  getDate() {
    return new GraphQLScalarType({
      name: 'Date',
      description: 'Date custom scalar type',
      parseValue(value) {
        return new Date(value); // value from the client
      },
      serialize(value) {
        return value.getTime(); // value sent to the client
      },
      parseLiteral(ast) {
        if (ast.kind === Kind.INT) {
          return parseInt(ast.value, 10);
        }

        return null;
      }
    });
  }
}
@pawpartyka
Copy link
Contributor

@valburyakov I also had a problem with it.

Solution:

date-time.scalar-type.ts

// ...
export const GraphQLDateTime = new GraphQLScalarType({
  name: 'DateTime',
  parseValue(value) {
    return new Date(value);
  },
  serialize(value) {
    return moment(value).toISOString();
  },
  parseLiteral(ast) {
    if (ast.kind === Kind.STRING) {
      return new Date(ast.value);
    }

    return null;
  },
});

bootstrap.ts

/** Scalar types **/
import { scalarTypes } from './type-implementations';

// ....

export class AppModule {

  // .........

  private createSchema(): GraphQLSchema {
    const schema = this.graphQLFactory.createSchema({
      typeDefs: [
        this.graphQLFactory.mergeTypesByPaths('./**/*.graphqls'),
      ],
      resolvers: {
        ...scalarTypes,
      },
      directiveResolvers: {},
    });

    const delegates = this.graphQLFactory.createDelegates();

    return mergeSchemas({
      schemas: [
        schema,
      ],
      resolvers: delegates,
    });
  }
}

But resolvers in createSchema function have problem, because this function overwrite resolvers property. I created pull request to fix it. Maybe there are other better solutions, but I have not found one.

@valburyakov
Copy link
Author

@partyka95 Thx for the solution. But for me it still doesn't work, I did like in your example but no resolver for custom scalar is loaded:

app.module.ts

createSchema() {
    const typeDefs = this.graphQLFactory.mergeTypesByPaths('./**/*.graphql');
    const schema = this.graphQLFactory.createSchema({
      typeDefs,
      resolvers: {
        Date: GraphQLDateTime
      },
      directiveResolvers: {},
    });

    const delegates = this.graphQLFactory.createDelegates();

    return mergeSchemas({
      schemas: [
        schema,
      ],
      resolvers: delegates
    });
  }

Or this solution is working only with your fix in PR ? And show your scalarTypes .

@pawpartyka
Copy link
Contributor

@dcasier
Copy link

dcasier commented Feb 27, 2018

Another temporary solution :

  import { ResolversExplorerService } from '@nestjs/graphql/resolvers-explorer.service'
  import { makeExecutableSchema } from 'graphql-tools'

  const resolverFunctions = {
    CustomScalar: myCustomScalarType
  }

  (...)

  createSchema() {
    const typeDefs = this.graphQLFactory.mergeTypesByPaths('./**/*.gql')
    //const schema = this.graphQLFactory.createSchema(typeDefs)

    const resolvers = this.resolversExplorerService.explore()
    Object.assign(resolvers, customScalarsFunctions)

    const schema = makeExecutableSchema({
      typeDefs,
      resolvers: resolvers,
    })
    return schema
  }

@kamilmysliwiec
Copy link
Member

Fixed thanks to #8 pull request. I'll push it together with the incoming release 🙂

@lock
Copy link

lock bot commented Apr 25, 2020

This thread has been automatically locked since there has not been any recent activity after it was closed. Please open a new issue for related bugs.

@lock lock bot locked as resolved and limited conversation to collaborators Apr 25, 2020
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants