GraphQL Subscriptions를 활용한 자바스크립트 실시간 위치 추적 기능 개발하기

개요

이번 포스트에서는 GraphQL Subscriptions를 사용하여 자바스크립트로 실시간 위치 추적 기능을 개발하는 방법에 대해 소개하겠습니다. 실시간 위치 추적 기능은 사용자의 위치가 변경될 때마다 실시간으로 업데이트되는 기능으로, 실시간 위치 추적 기능을 구현하기 위해 GraphQL Subscriptions를 이용할 것입니다.

Prerequisites

이 포스트를 따라하기 위해선 다음의 사항들이 필요합니다:

위치 추적 기능 설계

먼저, 위치 추적 기능의 구조를 설계해 보겠습니다. 우리는 사용자의 위치 정보를 추적하기 위해 GraphQL Subscription을 사용할 것입니다. 사용자는 위치 정보를 업로드하고, 다른 사용자는 해당 위치 정보를 실시간으로 구독하여 업데이트를 받을 수 있습니다.

다음은 위치 추적을 위한 GraphQL Schema의 예시입니다:

type Location {
  id: ID!
  latitude: Float!
  longitude: Float!
  timestamp: String!
}

type Subscription {
  trackingUpdates: Location
}

type Mutation {
  uploadLocation(latitude: Float!, longitude: Float!): Location
}

위의 스키마에서는 Location이라는 타입과 trackingUpdates라는 Subscription, 그리고 uploadLocation이라는 Mutation이 정의되어 있습니다. 사용자는 uploadLocation Mutation을 통해 위치 정보를 업로드하고, trackingUpdates Subscription을 통해 위치 정보를 실시간으로 받을 수 있습니다.

서버 구현하기

위치 추적 기능을 구현하기 위해선 GraphQL Subscriptions를 지원하는 서버를 구현해야 합니다. 이 예시에서는 Apollo Server를 사용하여 서버를 구현하겠습니다. Apollo Server는 GraphQL Subscriptions를 손쉽게 지원해 주기 때문에 우리의 목적에 맞게 사용할 수 있습니다.

먼저, 필요한 패키지들을 설치합니다:

npm install apollo-server apollo-server-express graphql graphql-subscriptions graphql-tools express

다음으로, 서버를 구성하는 코드를 작성해 보겠습니다:

const { ApolloServer, PubSub } = require('apollo-server');
const express = require('express');
const http = require('http');

const typeDefs = ... // 위에서 정의한 GraphQL Schema

const pubsub = new PubSub();
const PORT = process.env.PORT || 4000;

const resolvers = {
  Subscription: {
    trackingUpdates: {
      subscribe: () => pubsub.asyncIterator(['TRACKING_UPDATES']),
    },
  },
  Mutation: {
    uploadLocation: (_, { latitude, longitude }) => {
      const location = {
        id: 1,
        latitude,
        longitude,
        timestamp: new Date().toISOString(),
      };
      pubsub.publish('TRACKING_UPDATES', { trackingUpdates: location });
      return location;
    }
  }
};

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

const app = express();
server.applyMiddleware({ app });

const httpServer = http.createServer(app);
server.installSubscriptionHandlers(httpServer);

httpServer.listen({ port: PORT }, () => {
  console.log(`Server ready at http://localhost:${PORT}${server.graphqlPath}`);
  console.log(`Subscriptions ready at ws://localhost:${PORT}${server.subscriptionsPath}`);
});

위의 코드에서는 Apollo Server의 PubSub을 사용하여 실시간 업데이트를 위한 이벤트를 발행하고, subscribe 함수를 통해 해당 이벤트를 구독합니다. uploadLocation Mutation에서는 위치 정보를 업로드하고, 업로드된 위치 정보를 이벤트로 발행하여 구독자들에게 전송합니다.

클라이언트 구현하기

위치 추적 기능을 사용하는 클라이언트는 GraphQL Subscriptions를 통해 실시간 위치 업데이트를 받을 수 있어야 합니다. 이를 위해 Apollo Client를 사용하여 클라이언트를 구현하겠습니다.

먼저, 필요한 패키지들을 설치합니다:

npm install apollo-boost apollo-client apollo-link-ws react-apollo subscriptions-transport-ws

다음으로, 클라이언트를 구성하는 코드를 작성해 보겠습니다:

import React, { useEffect } from 'react';
import ApolloClient from 'apollo-client';
import { ApolloProvider } from 'react-apollo';
import { WebSocketLink } from 'apollo-link-ws';
import { InMemoryCache } from 'apollo-cache-inmemory';
import { HttpLink } from 'apollo-link-http';
import { split } from 'apollo-link';
import { getMainDefinition } from 'apollo-utilities';
import { SubscriptionClient } from 'subscriptions-transport-ws';

const httpLink = new HttpLink({
  uri: 'http://localhost:4000/graphql',
});

const wsLink = new WebSocketLink(new SubscriptionClient('ws://localhost:4000/graphql', {
  reconnect: true,
}));

const link = split(
  ({ query }) => {
    const { kind, operation } = getMainDefinition(query);
    return kind === 'OperationDefinition' && operation === 'subscription';
  },
  wsLink,
  httpLink,
);

const client = new ApolloClient({
  link,
  cache: new InMemoryCache(),
});

const App = () => {
  useEffect(() => {
    const subscribeToLocationUpdates = () => {
      client.subscribe({
        query: gql`
          subscription {
            trackingUpdates {
              id
              latitude
              longitude
              timestamp
            }
          }
        `,
      }).subscribe({
        next({ data }) {
          console.log('New location update:', data.trackingUpdates);
        },
        error(error) {
          console.error('Error in location update subscription:', error);
        },
      });
    };

    subscribeToLocationUpdates();
  }, []);

  return (
    <ApolloProvider client={client}>
      {/* 앱 컴포넌트 내용 */}
    </ApolloProvider>
  );
};

export default App;

위의 코드에서는 Apollo Client의 WebSocketLink를 사용하여 웹소켓 프로토콜을 이용해 서버의 실시간 업데이트를 구독합니다. ApolloProvider를 사용하여 클라이언트를 설정하고, subscribe 함수를 사용하여 위치 정보 업데이트를 구독합니다. 새로운 위치 정보가 업데이트될 때마다 next 콜백이 호출되고, 에러가 발생하면 error 콜백이 호출됩니다.

결론

이번 포스트에서는 GraphQL Subscriptions를 활용하여 자바스크립트로 실시간 위치 추적 기능을 개발하는 방법에 대해 알아보았습니다. GraphQL Subscriptions는 실시간으로 업데이트되는 기능을 구현하기 위한 강력한 도구이며, Apollo Server와 Apollo Client를 통해 손쉽게 구현할 수 있습니다. 실시간 위치 추적 기능은 위치 기반 애플리케이션과 다양한 IoT 애플리케이션에 활용될 수 있으며, GraphQL Subscriptions를 통해 유연하게 구현할 수 있습니다.


해시태그: #GraphQL #JavaScript