본문 바로가기

etc

[GraphQL+NodeJS] GraphQL으로 영화API만들기_백엔드

해당 포스트는 노마드코더 - GraphQL으로 영화API만들기_백엔드편 인프런 강의를 듣고 정리한 글입니다.

실습 저장소

https://github.com/JisunParkRea/movieql

 

JisunParkRea/movieql

Movie API with Graphql. Contribute to JisunParkRea/movieql development by creating an account on GitHub.

github.com


GraphQL이 해결할 수 있는 REST의 문제

- Over-fetching : 요청한 정보보다 더 많은 것을 받게 되는 것

  예) username이 필요하여 /users/ GET 요청을 하면, 그 외 email, age, 등등의 정보까지 받게 되는 것

 

- Under-fetching : 하나를 완성하려고 많은 소스를 요청하는 것

  예) 인스타그램 첫페이지를 열면 /feed/, /notifications/, /user/1/ 과 같이 여러개의 소스를 요청받아야하는 것

GraphQL 용어

- Schema: 사용자에게 보내거나 사용자로부터 받을 데이터에 대한 설명

  1) Query: DB로부터 정보를 얻는 것

  2) Mutation: 서버/DB/메모리에서 정보를 바꾸는 것

 - Resolvers: query를 resolve(해결)하는 것 (nodejs로 DB 기능을 프로그래밍해야함)


실습1: 간단한 DB를 만들고 query, mutation, resolvers 다뤄보기

schema.graphql

type Movie {
    id: Int!
    name: String!
    score: Int!
}

type Query{
    movies: [Movie]!
    movie(id: Int!): Movie
}

type Mutation{
    addMovie(name: String!, score: Int): Movie!
    deleteMovie(id: Int!): Boolean!
}

db.js

let movies = [
  {
    id: 1,
    name: "Avengers - The Infinity War",
    score: 8
  },
  {
    id: 2,
    name: "The Incredible 2",
    score: 9
  },
  {
    id: 3,
    name: "Mission Impossilbe - Fallout",
    score: 9
  },
  {
    id: 4,
    name: "ILLANG : THE WOLF BRIGADE",
    score: 1
  },
  {
    id: 5,
    name: "Along with the Gods: The Last 49 Days",
    score: 6
  }
]

export const getMovies = () => movies;

export const getById = id => {
  const filteredMovies = movies.filter(movie => movie.id === id);
  return filteredMovies[0];
}

export const deleteMovie = id => {
  const cleanedMovies = movies.filter(movie => movie.id !== id);
  if(movies.length > cleanedMovies.length) {
    movies = cleanedMovies;
    return true;
  } else {
    return false;
  }
}

export const addMovie = (name, score) => {
  const newMovie = {
    id: `${movies.length + 1}`,
    name,
    score
  }
  movies.push(newMovie);
  return newMovie;
}

resolvers.js

import { getById, getMovies, addMovie, deleteMovie } from "./db";

const resolvers = {
    Query: {
        movies: () => getMovies(),
        movie: (_, { id }) => getById(id)
    },
    Mutation: {
        addMovie: (_, {name, score}) => addMovie(name, score),
        deleteMovie: (_, {id}) => deleteMovie(id)
    }
};

export default resolvers;

실습2: 실제 REST API를 GraphQL로 Wrapping하기

YTS YIFY movie list API https://yts.mx/api#list_movies

 

API Documentation - YTS YIFY

Official YTS YIFY API documentation. YTS offers free API - an easy way to access the YIFY movies details.

yts.mx

https://yts.mx/api/v2/list_movies.json?limit=50&minimum_rating=9

  Endpoint                                        쿼리스트링: key name

=> REST에서 이와 같은 방식으로 가져오는 데이터를 graphql로 감싸서 가져와볼 것이다.

schema.graphql

type Movie {
    id: Int!
    title: String!
    rating: Float!
    summary: String!
    language: String!
    medium_cover_image: String!
}

type Query{
    movies(limit: Int, rating: Float): [Movie]!
}

db.js

import fetch from "node-fetch";

const API_URL = "https://yts.mx/api/v2/list_movies.json?"

export const getMovies = (limit, rating) => {
    let REQUEST_URL = API_URL;
    if(limit > 0){
        REQUEST_URL += `limit=${limit}`;
    }
    if(rating > 0){
        REQUEST_URL += `&minimum_rating=${rating}`;
    }
    return fetch(REQUEST_URL)
        .then(res => res.json())
        .then(json => json.data.movies);
}

resolvers.js

import { getMovies } from "./db";

const resolvers = {
    Query: {
        movies: (_, {limit, rating}) => getMovies(limit, rating)
    }
};

export default resolvers;

 

끝!