Building Better APIs with GraphQL

Building Better APIs with GraphQL

Let's talk RESTful

Resouce

URL

Recipe

GET /recipes/{id}

GET /recipes/074...


{
    "id":  "074ead4b87ac5f185d138d9574f8c4d6a74aadad",
    "title":  "Earl Grey Shortbread",
    "url": http://www.foodnetwork.com/recipes/food-network-kitchen/earl-grey-shortbread,
    "attribution": {
        "author": {
            "name":  "Food Network Kitchen",
            "url": http://www.foodnetwork.com/profiles/talent/food-network-kitchen,
        }
    },
    "chef": "Food Network Kitchen",
    "difficulty":  "Easy",
    "ingredients": [
        "1/4 cup Earl Grey tea leaves" ,
        "4 cups all-purpose flour" ,
        "1/2 teaspoon salt" ,
        "4 sticks unsalted butter, at room temperature" ,
        "3 1/2 cups confectioners¿ sugar" ,
        "2 teaspoons pure vanilla extract" ,
        "3 tablespoons milk" ,
        "Coarse sugar, for decorating"
    ] ,
    "tags": [
        http://www.foodnetwork.com/topics/cookie-recipes, »
        http://www.foodnetwork.com/topics/shortbread-cookie-recipes, »
        http://www.foodnetwork.com/topics/tea, »
        http://www.foodnetwork.com/topics/christmas-recipes, »
        http://www.foodnetwork.com/topics/holiday, »
    ],
    "time": {
        "Active":  "25 min" ,
        "Total":  "3 hr"
    },
    "yield":  "about 50 cookies"
}

Common Problems With Rest

Fetching More Than Needed


{
    "id":  "074ead4b87ac5f185d138d9574f8c4d6a74aadad",
    "title":  "Earl Grey Shortbread",
    "url": http://www.foodnetwork.com/recipes/food-network-kitchen/earl-grey-shortbread,
    "attribution": {
        "author": {
            "name":  "Food Network Kitchen",
            "url": http://www.foodnetwork.com/profiles/talent/food-network-kitchen,
        }
    },
    "chef": "Food Network Kitchen",
    "difficulty":  "Easy",
    "ingredients": [
        "1/4 cup Earl Grey tea leaves" ,
        "4 cups all-purpose flour" ,
        "1/2 teaspoon salt" ,
        "4 sticks unsalted butter, at room temperature" ,
        "3 1/2 cups confectioners¿ sugar" ,
        "2 teaspoons pure vanilla extract" ,
        "3 tablespoons milk" ,
        "Coarse sugar, for decorating"
    ] ,
    "tags": [
        http://www.foodnetwork.com/topics/cookie-recipes, »
        http://www.foodnetwork.com/topics/shortbread-cookie-recipes, »
        http://www.foodnetwork.com/topics/tea, »
        http://www.foodnetwork.com/topics/christmas-recipes, »
        http://www.foodnetwork.com/topics/holiday, »
    ],
    "time": {
        "Active":  "25 min" ,
        "Total":  "3 hr"
    },
    "yield":  "about 50 cookies"
}

All I want

GET /recipes/{id}?id,title,url


{
    "id":  "074ead4b87ac5f185d138d9574f8c4d6a74aadad",
    "title":  "Earl Grey Shortbread",
    "url": http://www.foodnetwork.com/recipes/food-network-kitchen/earl-grey-shortbread
}

Versioning


{
    "id":  "074ead4b87ac5f185d138d9574f8c4d6a74aadad",
    "title":  "Earl Grey Shortbread",
    "url": http://www.foodnetwork.com/recipes/food-network-kitchen/earl-grey-shortbread,
    "attribution": {
        "author": {
            "name":  "Food Network Kitchen",
            "url": http://www.foodnetwork.com/profiles/talent/food-network-kitchen,
        }
    },
    "chef": "Food Network Kitchen",
    "difficulty":  "Easy",
    "ingredients": [
        "1/4 cup Earl Grey tea leaves" ,
        "4 cups all-purpose flour" ,
        "1/2 teaspoon salt" ,
        "4 sticks unsalted butter, at room temperature" ,
        "3 1/2 cups confectioners¿ sugar" ,
        "2 teaspoons pure vanilla extract" ,
        "3 tablespoons milk" ,
        "Coarse sugar, for decorating"
    ] ,
    "tags": [
        http://www.foodnetwork.com/topics/cookie-recipes, »
        http://www.foodnetwork.com/topics/shortbread-cookie-recipes, »
        http://www.foodnetwork.com/topics/tea, »
        http://www.foodnetwork.com/topics/christmas-recipes, »
        http://www.foodnetwork.com/topics/holiday, »
    ],
    "time": {
        "Active":  "25 min" ,
        "Total":  "3 hr"
    },
    "yield":  "about 50 cookies"
}

{
    "id":  "074ead4b87ac5f185d138d9574f8c4d6a74aadad",
    "title":  "Earl Grey Shortbread",
    "url": http://www.foodnetwork.com/recipes/food-network-kitchen/earl-grey-shortbread,
    "attribution": {
        "author": {
            "name":  "Food Network Kitchen",
            "url": http://www.foodnetwork.com/profiles/talent/food-network-kitchen,
        }
    },
    "difficulty":  "Easy",
    "ingredients": [
        "1/4 cup Earl Grey tea leaves" ,
        "4 cups all-purpose flour" ,
        "1/2 teaspoon salt" ,
        "4 sticks unsalted butter, at room temperature" ,
        "3 1/2 cups confectioners¿ sugar" ,
        "2 teaspoons pure vanilla extract" ,
        "3 tablespoons milk" ,
        "Coarse sugar, for decorating"
    ] ,
    "tags": [
        http://www.foodnetwork.com/topics/cookie-recipes, »
        http://www.foodnetwork.com/topics/shortbread-cookie-recipes, »
        http://www.foodnetwork.com/topics/tea, »
        http://www.foodnetwork.com/topics/christmas-recipes, »
        http://www.foodnetwork.com/topics/holiday, »
    ],
    "time": {
        "Active":  "25 min" ,
        "Total":  "3 hr"
    },
    "yield":  "about 50 cookies"
}

GET /v2/recipes/074...

API Discoverability

Requiring multiple network requests to build a single view

GraphQL

A query language for your application

A Brief History

Data defined by schema

query {
  recipes(first: 2) {
    title,
    attribution {
      author {
        name
      }
    }
  }
}
{
  "data": {
    "recipes": [
      {
        "title": "Achiote Marinated Baby Chickens...",
        "attribution": {
          "author": {
            "name": "Aarón Sánchez"
          }
        }
      }
    ]
  }
}

Query for what you need

GET /graphql

Response

Deprecate old fields

Resolving a query

export default {
    recipes({ first }) {

        // Arbitrary api call
        return getAllRecipes('recipes', first)
    },

    recipeCount() { 
        return getTotalRecipes()
    }
}

Demos

Links to learn more

https://raw.githubusercontent.com/sogko/graphql-shorthand-notation-cheat-sheet/master/graphql-shorthand-notation-cheat-sheet.png


http://graphql.org/learn/


https://developer.github.com/early-access/graphql/explorer/


http://dev.apollodata.com/tools/


https://github.com/rmosolgo/graphql-ruby

Building Better APIs with GraphQL

By Justin Bennett

Building Better APIs with GraphQL

  • 819