27.09.2018 reveal.js GraphQL with Python frameworks GraphQL with Python frameworks Create next-generation API with ease Bartosz Kazuła http://0.0.0.0:8080/?print-pdf 1/56
27.09.2018 reveal.js About About mua mua Frontend/Backend/Mobile developer Software architect Highly focused on new technologies http://0.0.0.0:8080/?print-pdf 2/56
What is GraphQL? What is GraphQL? 27.09.2018 reveal.js A query language for your API http://0.0.0.0:8080/?print-pdf 3/56
27.09.2018 reveal.js How it works How it works http://0.0.0.0:8080/?print-pdf 4/56
27.09.2018 reveal.js How it works How it works Database http://0.0.0.0:8080/?print-pdf 5/56
27.09.2018 reveal.js How it works How it works Database REST API http://0.0.0.0:8080/?print-pdf 6/56
27.09.2018 reveal.js How it works How it works Database REST API Legacy API http://0.0.0.0:8080/?print-pdf 7/56
27.09.2018 reveal.js Is it production ready? Is it production ready? http://0.0.0.0:8080/?print-pdf 8/56
27.09.2018 reveal.js Data structures Data structures Schema Type Query Mutation http://0.0.0.0:8080/?print-pdf 9/56
27.09.2018 reveal.js Schema Schema type Schema { Entrypoint to API, defines queries and mutations that can be accessed via query: Query GraphQL mutation: Mutation } http://0.0.0.0:8080/?print-pdf 10/56
27.09.2018 reveal.js Type Type type Character { The most basic components of a GraphQL schema, which just represent a name: String! kind of object you can fetch from your appearsIn: [Episode]! service, and what fields it has } http://0.0.0.0:8080/?print-pdf 11/56
27.09.2018 reveal.js Query Query { Asking for fields and objects based on provided parameters. Here you can hero { define the shape of response. name } } http://0.0.0.0:8080/?print-pdf 12/56
27.09.2018 reveal.js Mutation Mutation The way to modify data. If the mutation field returns an object type, you can ask for nested fields. mutation CreateReviewForEpisode($ep: Episode!, $review: ReviewInput!) { createReview(episode: $ep, review: $review) { stars commentary } } { "ep": "JEDI", "review": { "stars": 5, "commentary": "This is a great movie!" } } http://0.0.0.0:8080/?print-pdf 13/56
27.09.2018 reveal.js GraphiQL GraphiQL A graphical interactive in-browser GraphQL IDE for testing and writing queries. http://0.0.0.0:8080/?print-pdf 14/56
27.09.2018 reveal.js Graphene Graphene GraphQL in Python made easy GraphQL in Python made easy https://graphene-python.org/ pip install graphene http://0.0.0.0:8080/?print-pdf 15/56
27.09.2018 reveal.js Let's build some API Let's build some API Add user / get user / get all users Add blog post / get post / get all posts http://0.0.0.0:8080/?print-pdf 16/56
27.09.2018 reveal.js Django Django http://0.0.0.0:8080/?print-pdf 17/56
27.09.2018 reveal.js pip install graphene graphene-django http://0.0.0.0:8080/?print-pdf 18/56
27.09.2018 reveal.js pip install graphene graphene-django INSTALLED_APPS = ( # ... 'graphene_django', ) GRAPHENE = { 'SCHEMA': 'app.schema.schema' # Path to main schema } http://0.0.0.0:8080/?print-pdf 19/56
27.09.2018 reveal.js pip install graphene graphene-django INSTALLED_APPS = ( # ... 'graphene_django', ) GRAPHENE = { 'SCHEMA': 'app.schema.schema' # Path to main schema } from django.urls import path from graphene_django.views import GraphQLView urlpatterns = [ # ... path('graphql/', GraphQLView.as_view(graphiql=True)), ] http://0.0.0.0:8080/?print-pdf 20/56
27.09.2018 reveal.js User model User model class User(models.Model): name = models.CharField(max_length=20) surname = models.CharField(max_length=30) age = models.IntegerField() http://0.0.0.0:8080/?print-pdf 21/56
27.09.2018 reveal.js User model User model class User(models.Model): name = models.CharField(max_length=20) surname = models.CharField(max_length=30) age = models.IntegerField() UserType UserType from graphene_django import DjangoObjectType class UserType(DjangoObjectType): class Meta: model = User http://0.0.0.0:8080/?print-pdf 22/56
27.09.2018 reveal.js User Query User Query class UserQuery(graphene.ObjectType): users = graphene.List(UserType) def resolve_users(self, info): return User.objects.all() http://0.0.0.0:8080/?print-pdf 23/56
27.09.2018 reveal.js Schema Schema app/schema.py schema = graphene.Schema(query=UserQuery) http://0.0.0.0:8080/?print-pdf 24/56
27.09.2018 reveal.js http://0.0.0.0:8080/?print-pdf 25/56
27.09.2018 reveal.js Getting one user Getting one user class UserQuery(graphene.ObjectType): users = graphene.List(UserType) user = graphene.Field(UserType, name=graphene.String()) def resolve_users(self, info): return User.objects.all() def resolve_user(self, info, name): return User.objects.filter(name=name).first() http://0.0.0.0:8080/?print-pdf 26/56
27.09.2018 reveal.js Getting one user Getting one user class UserQuery(graphene.ObjectType): users = graphene.List(UserType) user = graphene.Field(UserType, name=graphene.String()) def resolve_users(self, info): return User.objects.all() def resolve_user(self, info, name): return User.objects.filter(name=name).first() http://0.0.0.0:8080/?print-pdf 27/56
27.09.2018 reveal.js Getting one user Getting one user class UserQuery(graphene.ObjectType): users = graphene.List(UserType) user = graphene.Field(UserType, name=graphene.String()) def resolve_users(self, info): return User.objects.all() def resolve_user(self, info, name): return User.objects.filter(name=name).first() http://0.0.0.0:8080/?print-pdf 28/56
27.09.2018 reveal.js http://0.0.0.0:8080/?print-pdf 29/56
27.09.2018 reveal.js User mutation User mutation http://0.0.0.0:8080/?print-pdf 30/56
27.09.2018 reveal.js Plain GraphQL mutation Plain GraphQL mutation class UserMutation(graphene.Mutation): user = graphene.Field(UserType) class Arguments: name = graphene.String() surname = graphene.String() age = graphene.Int() def mutate(self, info, **kwargs): user = User.objects.create(**kwargs) return UserMutation(user=user) http://0.0.0.0:8080/?print-pdf 31/56
27.09.2018 reveal.js Add mutation to the schema Add mutation to the schema class Mutations(graphene.ObjectType): create_user = UserMutation.Field() schema = graphene.Schema(query=UserQuery, mutation=Mutations) http://0.0.0.0:8080/?print-pdf 32/56
27.09.2018 reveal.js Add mutation to the schema Add mutation to the schema class Mutations(graphene.ObjectType): create_user = UserMutation.Field() schema = graphene.Schema(query=UserQuery, mutation=Mutations) http://0.0.0.0:8080/?print-pdf 33/56
27.09.2018 reveal.js http://0.0.0.0:8080/?print-pdf 34/56
27.09.2018 reveal.js Django Forms-based mutation Django Forms-based mutation class UserForm(forms.ModelForm): class Meta: model = User fields = ('name', 'surname', 'age') class UserMutation(DjangoModelFormMutation): class Meta: form_class = UserForm http://0.0.0.0:8080/?print-pdf 35/56
27.09.2018 reveal.js http://0.0.0.0:8080/?print-pdf 36/56
27.09.2018 reveal.js Django FAQ Django FAQ I use REST Framework - how to live? Take a look at graphene_django.rest_framework package. How to validate data? When using forms - use built-in validation. When going plain - add your own validator. How to receive user data? Use info.context variable passed to every function. http://0.0.0.0:8080/?print-pdf 37/56
27.09.2018 reveal.js GraphQL with Django GraphQL with Django Q&A Q&A http://0.0.0.0:8080/?print-pdf 38/56
27.09.2018 reveal.js Flask Flask http://0.0.0.0:8080/?print-pdf 39/56
27.09.2018 reveal.js Installation Installation pip install graphene graphene_sqlalchemy Flask-GraphQL app.add_url_rule( '/graphql', view_func=GraphQLView.as_view( 'graphql', schema=schema, graphiql=True ) ) http://0.0.0.0:8080/?print-pdf 40/56
27.09.2018 reveal.js Post model Post model class Post(Model): __tablename__ = 'posts' id = Column(Integer, primary_key=True) name = Column(String) intro = Column(Text) content = Column(Text) author = Column(String) http://0.0.0.0:8080/?print-pdf 41/56
27.09.2018 reveal.js Type and query Type and query class PostType(SQLAlchemyObjectType): class Meta: model = Post http://0.0.0.0:8080/?print-pdf 42/56
27.09.2018 reveal.js Type and query Type and query class PostType(SQLAlchemyObjectType): class Meta: model = Post class Query(graphene.ObjectType): posts = graphene.List(PostType) def resolve_posts(self, info): return Post.query.all() http://0.0.0.0:8080/?print-pdf 43/56
27.09.2018 reveal.js http://0.0.0.0:8080/?print-pdf 44/56
27.09.2018 reveal.js Get one post Get one post class Query(graphene.ObjectType): posts = graphene.List(PostType) post = graphene.Field(PostType, id=graphene.Int()) def resolve_posts(self, info): return Post.query.all() def resolve_post(self, info, id): return Post.query.get(id) http://0.0.0.0:8080/?print-pdf 45/56
Recommend
More recommend