Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Optimizing APIs for Consumers with GraphQL

Optimizing APIs for Consumers with GraphQL

Presented at Goruco

Brooks Swinnerton

June 24, 2017
Tweet

More Decks by Brooks Swinnerton

Other Decks in Technology

Transcript

  1. [ { "id": 1, "name": "Garden Of Eat In", "grade":

    "A", "camis": "40394054", "address": "1416 Avenue J, Brooklyn, New York 11230", "cuisine": "Jewish/Kosher", "url": "http://nyc-restaurant-grades.com/api/v1/restaurants/1", "inspections_url": "http://nyc-restaurant-grades.com/api/v1/restaurants/1/inspections" }, { "id": 2, "name": "Hunan Delight", "grade": "A", "camis": "41188631", "address": "752 Union Street, Brooklyn, New York 11215", "cuisine": "Chinese", "url": "http://nyc-restaurant-grades.com/api/v1/restaurants/2", "inspections_url": "http://nyc-restaurant-grades.com/api/v1/restaurants/2/inspections" }, ... ] http://nyc-restaurant-grades.com/api/v1/restaurants GET
  2. [ { "id": 1, "name": "Garden Of Eat In", "grade":

    "A", "camis": "40394054", "address": "1416 Avenue J, Brooklyn, New York 11230", "cuisine": "Jewish/Kosher", "url": "http://nyc-restaurant-grades.com/api/v1/restaurants/1", "inspections_url": "http://nyc-restaurant-grades.com/api/v1/ restaurants/1/inspections" }, ... ] http://nyc-restaurant-grades.com/api/v1/restaurants GET
  3. [ { "id": 1, "name": "Garden Of Eat In", "grade":

    "A", "camis": "40394054", "address": "1416 Avenue J, Brooklyn, New York 11230", "cuisine": "Jewish/Kosher", "url": "http://nyc-restaurant-grades.com/api/v1/restaurants/1", "inspections_url": "http://nyc-restaurant-grades.com/api/v1/ restaurants/1/inspections" }, ... ] http://nyc-restaurant-grades.com/api/v1/restaurants GET
  4. [ { "id": 1, "name": "Garden Of Eat In", "grade":

    "A", "camis": "40394054", "address": "1416 Avenue J, Brooklyn, New York 11230", "cuisine": "Jewish/Kosher", "url": "http://nyc-restaurant-grades.com/api/v1/restaurants/1", "inspections_url": "http://nyc-restaurant-grades.com/api/v1/ restaurants/1/inspections" }, ... ] http://nyc-restaurant-grades.com/api/v1/restaurants GET
  5. [ { "id": 1, "type": "Trans Fat / Initial Inspection",

    "score": 9, "grade": "A", "inspected_at": "2016-01-27T00:00:00.000Z", "graded_at": "2016-01-27T00:00:00.000Z", "url": "http://nyc-restaurant-grades.com/api/v1/restaurants/1/ inspections/1", "restaurant_url": "http://nyc-restaurant-grades.com/api/v1/ restaurants/1", "violations_url": "http://nyc-restaurant-grades.com/api/v1/ restaurants/1/inspections/1/violations" } ] http://nyc-restaurant-grades.com/api/v1/restaurants/1/inspections GET
  6. [ { "id": 1, "type": "Trans Fat / Initial Inspection",

    "score": 9, "grade": "A", "inspected_at": "2016-01-27T00:00:00.000Z", "graded_at": "2016-01-27T00:00:00.000Z", "url": "http://nyc-restaurant-grades.com/api/v1/restaurants/1/ inspections/1", "restaurant_url": "http://nyc-restaurant-grades.com/api/v1/ restaurants/1", "violations_url": "http://nyc-restaurant-grades.com/api/v1/ restaurants/1/inspections/1/violations" } ] http://nyc-restaurant-grades.com/api/v1/restaurants/1/inspections GET
  7. http://nyc-restaurant-grades.com/api/v1/restaurants/1/inspections/1/violations GET [ { "id": 62855, "description": "Food not protected

    from potential source of contamination during storage, preparation, transportation, display or service.", "code": "06C", "url": "http://nyc-restaurant-grades.com/api/v1/ restaurants/1/inspections/29572/violations/62855", "inspection_url": "http://nyc-restaurant-grades.com/api/v1/ restaurants/1/inspections/29572", "restaurant_url": "http://nyc-restaurant-grades.com/api/v1/ restaurants/1" } ]
  8. { me { firstName lastName email } } { "data":{

    "me":{ "firstName":"Brooks", "lastName":"Swinnerton", "email":"[email protected]" } } }
  9. { restaurant(name: "Cafe Ghia") { name cuisine } } {

    "data": { "restaurant": { "name": "Cafe Ghia", "cuisine": "American" } } } https://nyc-restaurant-grades.com/graphql POST
  10. { me { firstName lastName email } } type RootQuery

    { me: User } type User { firstName: String lastName: String email: String }
  11. { me { firstName lastName email } } type RootQuery

    { me: User } type User { firstName: String lastName: String email: String }
  12. { me { firstName lastName email } } type RootQuery

    { me: User } type User { firstName: String lastName: String email: String }
  13. type RootQuery { restaurant(name: String): Restaurant } type Restaurant {

    name: String! cuisine: String } { restaurant(name: "Cafe Ghia") { name cuisine } }
  14. type RootQuery { restaurant(name: String): Restaurant } type Restaurant {

    name: String! cuisine: String } { restaurant(name: "Cafe Ghia") { name cuisine } }
  15. type RootQuery { restaurant(name: String): Restaurant } type Restaurant {

    name: String! cuisine: String } { restaurant(name: "Cafe Ghia") { name cuisine } }
  16. type RootQuery { restaurant(name: String): Restaurant } type Restaurant {

    name: String! cuisine: String } { restaurant(name: "Cafe Ghia") { name cuisine } }
  17. type RootQuery { restaurants(borough: RestaurantBorough): [Restaurant]! } enum RestaurantBorough {

    BRONX BROOKLYN MANHATTAN STATEN_ISLAND QUEENS } type Restaurant { name: String! cuisine: String }
  18. type RootQuery { restaurants(borough: RestaurantBorough): [Restaurant]! } enum RestaurantBorough {

    BRONX BROOKLYN MANHATTAN STATEN_ISLAND QUEENS } type Restaurant { name: String! cuisine: String }
  19. type RootQuery { restaurants(borough: RestaurantBorough): [Restaurant]! } enum RestaurantBorough {

    BRONX BROOKLYN MANHATTAN STATEN_ISLAND QUEENS } type Restaurant { name: String! cuisine: String }
  20. { restaurant(name: "Mcdonalds") { name cuisine } restaurant(name: "Wendy's") {

    name cuisine } } { "data": { "restaurant": { "name": "Mcdonalds", "cuisine": "American" }, "restaurant": { "name": "Wendy's", "cuisine": "American" } } }
  21. { restaurant(name: "Mcdonalds") { name cuisine } restaurant(name: "Wendy's") {

    name cuisine } } { "data": { "restaurant": { "name": "Mcdonalds", "cuisine": "American" }, "restaurant": { "name": "Wendy's", "cuisine": "American" } } }
  22. { "data": { "mcdonalds": { "name": "Mcdonalds", "cuisine": "American" },

    "wendys": { "name": "Wendy's", "cuisine": "American" } } }
  23. { mcdonalds: restaurant(name: "McDonalds") { ...RestaurantInfo } wendys: restaurant(name: "Wendy's")

    { ...RestaurantInfo } } fragment RestaurantInfo on Restaurant { name cuisine }
  24. { restaurant(name: "Cafe Ghia") { name cuisine } } type

    RootQuery { restaurant(name: String): Restaurant } type Restaurant { name: String! cuisine: String }
  25. type RootQuery { restaurant(name: String): Restaurant } module Graph::Types RootQuery

    = GraphQL::ObjectType.define do name 'RootQuery' end end
  26. # The query root. type RootQuery { restaurant(name: String): Restaurant

    } module Graph::Types RootQuery = GraphQL::ObjectType.define do name 'RootQuery' description 'The query root.' end end
  27. module Graph::Types RootQuery = GraphQL::ObjectType.define do name 'RootQuery' field :restaurant

    do argument :name, types.String type Graph::Types::Restaurant resolve -> (object, arguments, context) do ::Restaurant.find_by(name: arguments['name']) end end end end type RootQuery { restaurant(name: String): Restaurant }
  28. module Graph::Types RootQuery = GraphQL::ObjectType.define do name 'RootQuery' field :restaurant

    do argument :name, types.String type Graph::Types::Restaurant resolve -> (object, arguments, context) do ::Restaurant.find_by(name: arguments['name']) end end end end type RootQuery { restaurant(name: String): Restaurant }
  29. module Graph::Types RootQuery = GraphQL::ObjectType.define do name 'RootQuery' field :restaurant

    do argument :name, types.String type Graph::Types::Restaurant resolve -> (object, arguments, context) do ::Restaurant.find_by(name: arguments['name']) end end end end type RootQuery { restaurant(name: String): Restaurant }
  30. module Graph::Types RootQuery = GraphQL::ObjectType.define do name 'RootQuery' field :restaurant

    do argument :name, types.String type Graph::Types::Restaurant resolve -> (object, arguments, context) do ::Restaurant.find_by(name: arguments['name']) end end end end type RootQuery { restaurant(name: String): Restaurant }
  31. type Restaurant { name: String! cuisine: String } module Graph::Types

    Restaurant = GraphQL::ObjectType.define do name 'Restaurant' end end
  32. # A place of business serving food. type Restaurant {

    name: String cuisine: String } module Graph::Types Restaurant = GraphQL::ObjectType.define do name 'Restaurant' description 'A place of business serving food.' end end
  33. type Restaurant { name: String cuisine: String } module Graph::Types

    Restaurant = GraphQL::ObjectType.define do name 'Restaurant' field :cuisine do type types.String resolve -> (restaurant, arguments, context) do restaurant.cuisine end end end end
  34. type Restaurant { name: String cuisine: String } module Graph::Types

    Restaurant = GraphQL::ObjectType.define do name 'Restaurant' field :cuisine do type types.String resolve -> (restaurant, arguments, context) do restaurant.cuisine end end end end
  35. type Restaurant { name: String cuisine: String } module Graph::Types

    Restaurant = GraphQL::ObjectType.define do name 'Restaurant' field :cuisine do type types.String resolve -> (restaurant, arguments, context) do restaurant.cuisine end end end end
  36. v4?