All You Ever Wanted To Know About GraphQL
Tags: graphql, apollo, beginners, tutorial
Published: 2018-11-27 20:54:57

---
title: All You Ever Wanted To Know About GraphQL
published: true
description: Andrew Sprouse, Co-founder of TakeShape, presents on GraphQL to an audience of developers at the JAMstack NYC meetup.
tags: graphql, apollo, beginners, tutorial
cover_image: https://thepracticaldev.s3.amazonaws.com/i/xvc5p1r52sha49m8ry1j.jpg
canonical_url: https://www.takeshape.io/articles/all-you-ever-wanted-to-know-about-graphql/
---

Co-founder of [TakeShape](https://www.takeshape.io/), Andrew Sprouse, presents GraphQL to a JAMstack meetup in New York.

{% youtube FgjHCt_9do4 %}

**Accompanying Github repo: https://github.com/takeshape/jamstack-meetup-graphql-demo**

### What is GraphQL?
Schema Definition + Query language + Resolution framework

### Schema
- Provides a strongly typed description of your data
- Schema Description Language (SDL) is the recommended cross-platform way to specify schema.

```graphql
enum Title {
    ACTOR
    DIRECTOR
}

type Role {
    characterName: String!
    title: Title
    movie: Movie
}

type Person {
    name: String!
    photo: String
    filmography: [Role]
}

type Movie {
    title: String!
    watched: Boolean
    rating: Float
    poster: String
    actors: [Person]!
    director: Person!
    year: String
}
```

GraphQL Schema also specifies how you interact with your data with queries and mutations

```graphql
type Query {
    listMovies: [Movie]
}

type Mutation {
    addMove(title: String): [Movie]
    removeMovie(title: String): [Movie]
}
```

### Query Langauge

Query your data and fetch exactly what you need

```graphql
query {
    getToWatchList {
        watched
        movie {
            title
            year
            director
        }
    }
}
```

```json
{
  "data": {
    "getToWatchList": [
      {
        "watched": true,
        "movie": {
          "title": "Top Gun",
          "year": "1985",
          "director": "Tony Scott"
        }
      },
      {
        "watched": true,
        "movie": {
          "title": "Big Trouble in Little China",
          "year": "1986",
          "director": "John Carpenter"
        }
      },
      {
        "watched": true,
        "movie": {
          "title": "The Princess Bride",
          "year": "1987",
          "director": "Rob Reiner"
        }
      },
      {
        "watched": false,
        "movie": {
          "title": "Taxi Driver",
          "year": "1976",
          "director": "Martin Scorsese"
        }
      }
    ]
  }
}
```

### Mutations
Modify your data

```graphql
mutation {
    addMovieToWatch(title: "Die Hard") {
        watched
        movieTitle
        movie {
            title
            year
            director
        }
    }
}
```

```json
{
  "data": {
    "addMovieToWatch": [
      {
        "watched": false,
        "movie": {
          "title": "Taxi Driver",
          "year": "1976",
          "director": "Martin Scorsese"
        }
      },
      {
        "watched": false,
        "movie": {
          "title": "Die Hard",
          "year": "1988",
          "director": "John McTiernan"
        }
      }
    ]
  }
}
```

### Resolution Framework
- Each GraphQL implementation provides it own query resolution framework
- GraphQL.js is the reference implementation
- Perform query and mutation resolution

#### Schema (SDL)

```graphql
type Query {
    getToWatchList: [ToWatch]
}

type Mutation {
    addMovieToWatch(title: String!): [ToWatch]
    removeMovieToWatch(title: String!): [ToWatch]
    markMovieWatched(title: String! watched: Boolean!): [ToWatch]
}
```

#### Resolvers

```javascript
const resolvers = {
    Query: {
        getToWatchList: () => {
            return WatchList.list();
        }
    },
    
    Mutation: {
        addMovieToWatch(_, {title}) {
            return WatchList.add(title);
        },

        removeMovieToWatch(_, {title}) {
            return WatchList.remove(title);
        },

        markMovieWatched(_, {title, watched}) {
            return WatchList.markWatched(title, watched);
        }
    }
};
```

Resolvers are also able to resolve dynamically computed fields

#### Schema (SDL)

```graphql
type Move {
    title: String
    rating: Float
    poster: String
    actors: String
    director: String 
    year: String
}

type ToWatch {
    movieTitle: String!
    movie: Movie
    watched: Boolean!
}
```

#### Resolvers

```
const resolvers = {
    ToWatch: {
        async movie(toWatch) {
            const info = await fetchMovieInfo(toWatch.movieTitle);
            return info ? {
                title: info.Title,
                rating: info.imdbRating,
                poster: info.Poster,
                year: info.Year,
                actors: info.Actors,
                director: info.Director
            } : null
        }
    }
};
```