Graphene Django is an easy to use library for writing GraphQL APIs within Django. But some of the documentation for Graphene is less than great.
When I was learning Graphene Django, I originally found it very hard to expose an @property
value of my model to the GraphQL API. This article will look into how to do that, and also why it works.
Say you have a Poll object, and you added a URL property:
class Poll(models.Model):
...
@property
def url(self):
return 'https://pollsite/polls/' + id
Then you can simply add a line to specify its existence in the schema:
class PollType(DjangoObjectType):
class Meta:
model = models.Poll
interfaces = (relay.Node,)
# This is it, so simple and so functional:
url = graphene.String()
That's it. Just use the form property_name = graphene.DataType()
. You can even use more fancy datatypes, like a graphene.List(graphene.Int())
. There is a good reference to check it out.
First, we need to understand the resolver of the property. By default, the resolvers perform a getattr
lookup on the object. This means it would like be this if we were to write it manually:
url = graphene.String()
def resolve_url(self, args, context, info):
return self.url
But that code looks stupid! Isn't the url attribute the graphene.String()
? Isn't that code broken?
Well the self
in a resolver doesn't represent an instance of the class. Or maybe it does. Anyway; Graphene is a festival of metaclass programming. So the self
object is really the Django object, not your graphene object! Once I found that out, it all started to make a lot more sense to me.
Well, that's a very quick dive into the weird and wonderful world of the Graphene framework. Metaclass magic hey!
If you enjoy these random Graphene tips, make sure to subscribe below.
I hope you enjoyed this article. Contact me if you have any thoughts or questions.
© 2015—2024 Sam Parkinson