graphql-go
graphql-go copied to clipboard
To achieve the interface is strange.
GraphQL Schema for example
# A character from the Star Wars universe
interface Character {
# The ID of the character
id: ID!
# The name of the character
name: String!
# The friends of the character, or an empty list if they have none
friends: [Character]
# The friends of the character exposed as a connection with edges
friendsConnection(first: Int, after: ID): FriendsConnection!
# The movies this character appears in
appearsIn: [Episode!]!
}
type Human implements Character {
# The ID of the human
id: ID!
# What this human calls themselves
name: String!
# Height in the preferred unit, default is meters
height(unit: LengthUnit = METER): Float!
# Mass in kilograms, or null if unknown
mass: Float
# This human's friends, or an empty list if they have none
friends: [Character]
# The friends of the human exposed as a connection with edges
friendsConnection(first: Int, after: ID): FriendsConnection!
# The movies this human appears in
appearsIn: [Episode!]!
# A list of starships this person has piloted, or an empty list if none
starships: [Starship]
}
it's golang code
func (r *Resolver) Hero(args struct{ Episode string }) *characterResolver {
if args.Episode == "EMPIRE" {
return &characterResolver{&humanResolver{humanData["1000"]}}
}
return &characterResolver{&droidResolver{droidData["2001"]}}
}
type character interface {
ID() graphql.ID
Name() string
Friends() *[]*characterResolver
FriendsConnection(friendsConnectionArgs) (*friendsConnectionResolver, error)
AppearsIn() []string
}
type characterResolver struct {
character
}
func (r *characterResolver) ToHuman() (*humanResolver, bool) {
c, ok := r.character.(*humanResolver)
return c, ok
}
type humanResolver struct {
h *human
}
func (r *humanResolver) ID() graphql.ID {
return r.h.ID
}
func (r *humanResolver) Name() string {
return r.h.Name
}
func (r *humanResolver) Height(args struct{ Unit string }) float64 {
return convertLength(r.h.Height, args.Unit)
}
func (r *humanResolver) Mass() *float64 {
if r.h.Mass == 0 {
return nil
}
f := float64(r.h.Mass)
return &f
}
func (r *humanResolver) Friends() *[]*characterResolver {
return resolveCharacters(r.h.Friends)
}
func (r *humanResolver) FriendsConnection(args friendsConnectionArgs) (*friendsConnectionResolver, error) {
return newFriendsConnectionResolver(r.h.Friends, args)
}
func (r *humanResolver) AppearsIn() []string {
return r.h.AppearsIn
}
func (r *humanResolver) Starships() *[]*starshipResolver {
l := make([]*starshipResolver, len(r.h.Starships))
for i, id := range r.h.Starships {
l[i] = &starshipResolver{starshipData[id]}
}
return &l
}
- define character interface
- define characterResolver
- define humanResolver & Implement interface(character)
- achieve characterResolver.ToHuman
- call func need Conversion: return &characterResolver{&droidResolver{droidData["2001"]}}
use graphql interface requires more than 5 steps,a bit cumbersome.
- define characterResolver interface (replace define character interface)
- define humanResolver & Implement interface(character)
- call func need Conversion: return &droidResolver{droidData["2001"]},but &characterResolver{&droidResolver{droidData["2001"]}}
E.g
func (r *Resolver) Hero(args struct{ Episode string }) characterResolver {
if args.Episode == "EMPIRE" {
return &humanResolver{humanData["1000"]}
}
return &droidResolver{droidData["2001"]}
}
type characterResolver interface {
ID() graphql.ID
Name() string
Friends() *[]*characterResolver
FriendsConnection(friendsConnectionArgs) (*friendsConnectionResolver, error)
AppearsIn() []string
}
type humanResolver struct {
h *human
}
func (r *humanResolver) ID() graphql.ID {
return r.h.ID
}
func (r *humanResolver) Name() string {
return r.h.Name
}
func (r *humanResolver) Height(args struct{ Unit string }) float64 {
return convertLength(r.h.Height, args.Unit)
}
func (r *humanResolver) Mass() *float64 {
if r.h.Mass == 0 {
return nil
}
f := float64(r.h.Mass)
return &f
}
func (r *humanResolver) Friends() *[]*characterResolver {
return resolveCharacters(r.h.Friends)
}
func (r *humanResolver) FriendsConnection(args friendsConnectionArgs) (*friendsConnectionResolver, error) {
return newFriendsConnectionResolver(r.h.Friends, args)
}
func (r *humanResolver) AppearsIn() []string {
return r.h.AppearsIn
}
func (r *humanResolver) Starships() *[]*starshipResolver {
l := make([]*starshipResolver, len(r.h.Starships))
for i, id := range r.h.Starships {
l[i] = &starshipResolver{starshipData[id]}
}
return &l
}
This be easier.
@neelance