Graphql-go: custom scalar type

Created on 25 Oct 2016  路  6Comments  路  Source: graph-gophers/graphql-go

Is it possible to define and register a custom scalar type.

http://graphql.org/graphql-js/type/#graphqlscalartype

In graphql-go, I do it like,

var Time *graphql.Scalar

func init() {
  Time = graphql.NewScalar(graphql.ScalarConfig{
    Name: "DateTime",
    Description: `Scalar type representing a date and time with offset, serialized as a string
     in ISO-8601 date format.\n\ne.g. "2016-05-05T20:16:06Z"`,
    // Serialize: gets invoked when serializing the result to send it back to a client.
    // adapted from time.MarshalJSON https://golang.org/src/time/time.go?s=26891:26934#L918
    Serialize: func(value interface{}) interface{} {
      t, ok := value.(time.Time)
      if !ok {
        panic("TODO")
      }
      return formatTime(t)
    },
    // parseValue: gets invoked to parse client input that was passed through variables.
    // value is a a plain type
    ParseValue: func(value interface{}) interface{} {
      str, ok := value.(string)
      if !ok {
        panic("TODO")
      }

      t, err := parseDate(str)
      pkg.Check(err)
      return t
    },
    // parseLiteral: gets invoked to parse client input that was passed inline in the query.
    // value is ast.Value
    ParseLiteral: func(valueAST ast.Value) interface{} {
      switch valueAST := valueAST.(type) {
      case *ast.StringValue:
        t, err := parseDate(valueAST.Value)
        if err != nil {
          panic("TODO")
        }
        return t
      }
      return nil
    },
  })
}

Most helpful comment

@bsr203 Please take a look at d8035494e68ba43c6c09c9a46d1852f458b8cfc3. This is a new approach for custom types. It decouples the GraphQL declaration of the type (scalar Time in schema) from its implementation (ImplementsGraphQLType and UnmarshalGraphQL methods). This also allows more than one implementation for a GraphQL type, for example one can implement a different Go type for ID, which would resolve #40 nicely. It is still a WIP, the API may change some more, eventually it may also help with #17 and #28. What do you think about this?

All 6 comments

It's not yet possible. Good suggestion though.

Not sure it is formally defined anywhere, but reading through the tutorial, I see the syntax we could use to represent it in the schema language.

http://graphql.org/learn/schema/#scalar-types

In most GraphQL service implementations, there is also a way to specify custom scalar types. For example, we could define a Date type:

scalar Date

Then it's up to our implementation to define how that type should be serialized, deserialized, and validated. For example, you could specify that the Date type should always be serialized into an integer timestamp, and your client should know to expect that format for any date fields.

Good to know, thanks! I'll definitely add this option at some point.

Thank you. that looks great and terse. cheers. Hopefully the builder interface would be expanded to build the schema programmatically, not just through string. thanks again.

@bsr203 Please take a look at d8035494e68ba43c6c09c9a46d1852f458b8cfc3. This is a new approach for custom types. It decouples the GraphQL declaration of the type (scalar Time in schema) from its implementation (ImplementsGraphQLType and UnmarshalGraphQL methods). This also allows more than one implementation for a GraphQL type, for example one can implement a different Go type for ID, which would resolve #40 nicely. It is still a WIP, the API may change some more, eventually it may also help with #17 and #28. What do you think about this?

@neelance from the user perspective it looks cleaner, and with all the added benefits you listed, definitely +1. Thank you also for the great learning opportunity by looking through how you evolve the API.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

thewillhuang picture thewillhuang  路  5Comments

rogchap picture rogchap  路  5Comments

JitinGuglani picture JitinGuglani  路  6Comments

estutzenberger picture estutzenberger  路  4Comments

aquiseb picture aquiseb  路  4Comments