본문 바로가기

TIL (Today I Learned)

graphQL vs REST API

한동안 덮어두었던 (= 막힐땐 이렇게 ㅎㅎ) 책을 다시 꺼내들어 이해가 안되던 부분을 다시한번 체크해봤습니다.

 

I. GraphQL 이란?

https://graphql.com/

 

GraphQL: APIs for humans

GraphQL: APIs for humans GraphQL is the developer-friendly query language for the modern web. It transforms how apps fetch data from an API, enabling you to get exactly what you need with a single query—instead of wrangling responses from a patchwork of

graphql.com

 

평소엔 REST API로 충분히? 기본적인 요청과 응답을 처리하면서 필요한 데이터를 처리했던거같은데..왜 GraphQL이 필요할까? 

 

개발자 친화적인 쿼리 언어이고, 서버 요청 수와 응답의 복잡성을 줄여 클라이언트가 정확히 필요한 데이터를 제공하기 위한것이라고 소개하고 있다.

Introducing GraphQL

...중략..

GraphQL is a query language for APIs—meaning that it excels at fetching data from a variety of data sources, bundling it all together, and handing it back to us.

[GraphQL은 API를 위한 쿼리 언어로, 다양한 데이터 소스에서 데이터를 가져오고, 이를 모두 묶어서 우리에게 돌려주는 데 탁월합니다.]

...중략...

 

II. GraphQL 구성요소

세부사항을 건너뛰고? 요약하자면,..

 

GraphQL = typeDefs + Resolver (Query, Mutation)

 

1) 스키마(Schema) : 요청에 대한 청사진(blueprint)이라고도 하는데, 그냥 데이터의 구조를 생각하면 쉽다. 흔히 데이터의 상호작용을 글로 표현한거라고 하는데, 이것은 API에 대해 엄격한 계획을 강제하기 위한 것으로 해석된다.

GraphQL 스키마는 기본 구성요소는 객체이다. 그리고, 객체의 자료형으로는 5가지의 스칼라 자료형이 제공된다.

① String : 문자열 (utf-8)

② Boolean : true, false

③ Int : 32비트 정수형

④ Float : 부동 소수점

⑤ ID : 고유한 식별자

 

아래 예시는 제목(title)과 저자(author)로 표현해본 책(Book)이라는 스키마를 정의해본것이다. 여기서 필수(Mendatory)적인 값은 느낌표(!)를 사용해 나타내야 한다.

const typeDefs = `#graphql
	type Book {
    	title: String,
        author: String
    }
`;

 

2) 스키마(Schema) : 요청에 대한 청사진(blueprint)이라고도 하는데, 그냥 데이터의 구조를 생각하면 쉽다.

III. GraphQL 사용법

이전에 내가 사용했던 v3 에서 최근(이라고 하기엔...) v4로 버전업이 되었더라, 뭐...v3 에서 v4로 버전업되는 중간쯤에 잠깐 GraphQL이 뭔가 하고 써봤던거같은데..암튼, Over Fetching, Under Fetching을 커버하고 정확한 데이터 Fetching을 위해서는 GraphQL이 REST API보다 메리트가 있어보여서 한번 정리해보고자 한다.

 


1) 버전 변경 (v3 에서 v4)

2) GraphQL Playground가 사라지고 GraphQL Sandbox로 변경

3) ApplyMiddleware 함수가 expressMiddleware 함수로 변경 (express.js + @apollo/server)

4) 그밖에...

이 글은, Apollo-Server v4.10.4 버전을 기준으로 작성했습니다.

 

1) Express.js와 @apollo/server를 함께 사용하기 - 미들웨어로 등록

https://www.apollographql.com/docs/apollo-server/api/express-middleware

 

API Reference: expressMiddleware

app.use('/graphql', cors<cors.CorsRequest>(), express.json(), expressMiddleware(server));

www.apollographql.com

 

보통은 로컬에서 개발을 할때 Express.js로 API를 만들고, 여기에 미들웨어로 @apollo/server를 등록해서 쓰는 경우이다. 이전에 학습하다가 멈추기를 반복해서 기존에 메모해두었던 부분을 다시한번 체크해보니, 변경사항이 좀 있어서 ..오류에 적잖이 당황했지만,..이 부분은 앞으로는 Express.js 없이 독립적인 아폴로 서버를 사용해서 GraphQL을 작성하는 습관을 가질려고 한다. 북마크를 참조하시라!

 

2) @apollo/server만으로 사용하기

https://www.apollographql.com/docs/apollo-server/migration

 

Migrating to Apollo Server 4

Apollo Server 4 focuses on improving Apollo Server's extensibility and making it simpler to use, maintain, and document. To learn more about the inspiration behind this release, see the Apollo Server Roadmap. We recommend that all users of previous version

www.apollographql.com

 

당분간 GraphQL을 위한 아폴로 서버를 사용하고자 한다. 까먹지 않기위해서~

import { ApolloServer } from '@apollo/server';
import { startStandaloneServer } from '@apollo/server/standalone';

// GraphQL schema
const typeDefs = `#graphql
  type Book {
    id: ID!,
    title: String!,
    author: String
  }
  type User {
    id: String,
    name: String
  }
  type Query {
    books: [Book],
    users: [User],
    user(id: String!): User
  }
`;

// mockup data
const books = [
  {
    title: 'The Awakeening',
    content: 'Hello World!',
    author: 'Kate Chopin',
  },
  {
    title: 'The sunset',
    content: 'Hello World!',
    author: 'Kate Chopin',
  },
];
const users = [
  {
    id: '1',
    name: 'Elizabeth Bennet',
  },
  {
    id: '2',
    name: 'Fitzwilliam Darcy',
  },
];

// Graphql resolvers
const resolvers = {
  Query: {
    books: () => books,
    users: () => users,
    user: (parent, args) => {
      return users.find((user) => user.id === args.id);
    },
  },
};

const server = new ApolloServer({
  typeDefs,
  resolvers,
});

const { url } = await startStandaloneServer(server, {
  listen: { port: 4000, path: '/api' },
});

console.log(`server ready at http://localhost:4000/api`);

 

< GraphQL SandBox >

 

REST API 보다는 좀더 데이터 자체에 집중하고자 한다면 GraphQL이 뭔가 개연성?이 더 높은걸로 이해되지만 그래도 익숙한건 REST API니까...서두르지 않고 익숙해질때까지 GraphQL을 사용해보기로 한다.

 

+추가

 

최종적으로 기존에 REST API로 만들어본 Todos App을 GraphQL로 변경해서 만들어보기로 함..대략 스키마는 완성해본거고..요청도 잘 되는걸 확인했다.

Todos 전체 목록 요청한 결과
특정 Todo만 요청한 결과

 

이제, 리졸버가 남았네...뮤테이션(Mutation)..보통은 Todo를 등록하고, 수정하고, 삭제하는 게 필요할테고...이건 일단 만들어서 완성된걸로 업데이트 해야겠다.

'TIL (Today I Learned)' 카테고리의 다른 글

Node.js + Express.js + GraphQL + @ApolloServer  (2) 2024.06.04
Ngrok  (1) 2024.04.26
JS-EVERYWHRE | chapter 1~3  (2) 2023.06.01