GraphQL Endpoint
모든 VPMS 서비스는 Apollo Federation을 통해 통합된 단일 GraphQL endpoint를 제공합니다.
POST https://development.vpms.io/graphql
개발 환경 endpoint입니다. 프로덕션 환경에서는 다른 URL을 사용합니다.
모든 GraphQL 요청에는 다음 헤더가 필요합니다.
Content-Type
Content-Type: application/json
GraphQL 요청은 JSON 형식으로 전송됩니다.
Authorization (선택적)
인증이 필요한 API의 경우 JWT 토큰을 포함해야 합니다.
Authorization: Bearer YOUR_JWT_TOKEN
Bearer 방식의 JWT 토큰
- 형식:
Bearer {token}
- SMS 인증을 통해 획득한 authHash 사용
- 일부 공개 API는 토큰 없이 호출 가능
전체 헤더 예제
POST /graphql HTTP/1.1
Host: development.vpms.io
Content-Type: application/json
Authorization: Bearer 01HQKS9V8X2N3P4Q5R6S7T8U9V
요청 형식
GraphQL 요청은 JSON 객체로 구성되며, 다음 필드를 포함합니다.
Query/Mutation
{
"query": "query GetReservations($id: ID!) { ... }",
"variables": {
"id": "01HQKS9V8X"
},
"operationName": "GetReservations"
}
실행할 작업 이름 (여러 작업이 있을 때 사용)
응답 형식
성공 응답
{
"data": {
"getReservations": [
{
"id": "01HQKS9V8X",
"status": "CONFIRMED"
}
]
}
}
에러 응답
{
"errors": [
{
"message": "인증 토큰이 유효하지 않습니다",
"locations": [{"line": 2, "column": 3}],
"path": ["getReservations"],
"extensions": {
"code": "UNAUTHENTICATED",
"errorCode": "AUTH_TOKEN_INVALID"
}
}
],
"data": null
}
클라이언트 설정 예제
TypeScript (Apollo Client)
import { ApolloClient, InMemoryCache, createHttpLink } from '@apollo/client';
import { setContext } from '@apollo/client/link/context';
// HTTP 링크 설정
const httpLink = createHttpLink({
uri: 'https://development.vpms.io/graphql',
});
// 인증 헤더 설정
const authLink = setContext((_, { headers }) => {
// 로컬 스토리지에서 토큰 가져오기
const token = localStorage.getItem('authToken');
return {
headers: {
...headers,
'Content-Type': 'application/json',
...(token && { authorization: `Bearer ${token}` }),
}
};
});
// Apollo Client 생성
const client = new ApolloClient({
link: authLink.concat(httpLink),
cache: new InMemoryCache(),
});
export default client;
JavaScript (Fetch API)
async function graphqlRequest(query, variables = {}) {
const token = localStorage.getItem('authToken');
const response = await fetch('https://development.vpms.io/graphql', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
...(token && { 'Authorization': `Bearer ${token}` }),
},
body: JSON.stringify({
query,
variables,
}),
});
const { data, errors } = await response.json();
if (errors) {
throw new Error(errors[0].message);
}
return data;
}
// 사용 예제
const data = await graphqlRequest(`
query GetReservations($accommodationId: ID!) {
getReservations(accommodationId: $accommodationId) {
id
status
}
}
`, {
accommodationId: '01HQKS9V8X'
});
cURL
curl -X POST https://development.vpms.io/graphql \
-H "Content-Type: application/json" \
-H "Authorization: Bearer YOUR_TOKEN" \
-d '{
"query": "query GetReservations($id: ID!) { getReservations(accommodationId: $id) { id status } }",
"variables": { "id": "01HQKS9V8X" }
}'
Rate Limiting
API 요청에는 다음과 같은 제한이 적용됩니다.
- 제한: 분당 60회
- 초과 시: 429 Too Many Requests
- SMS 발송: 10분당 5회 (번호당)
- 인증 확인: 1분당 10회 (번호당)
GraphQL Playground
개발 환경에서는 GraphQL Playground를 통해 API를 탐색할 수 있습니다.
https://development.vpms.io/graphql
브라우저에서 접속하면 인터랙티브한 쿼리 도구를 사용할 수 있습니다.
Playground에서 우측 상단의 “HTTP HEADERS” 탭에서 Authorization 헤더를 설정할 수 있습니다.
에러 코드
VPMS API에서 사용하는 공통 에러 코드입니다.
| 코드 | 설명 | HTTP Status |
|---|
UNAUTHENTICATED | 인증되지 않은 요청 | 401 |
FORBIDDEN | 권한 없음 | 403 |
NOT_FOUND | 리소스를 찾을 수 없음 | 404 |
BAD_REQUEST | 잘못된 요청 | 400 |
INTERNAL_SERVER_ERROR | 서버 오류 | 500 |
RATE_LIMITED | 요청 제한 초과 | 429 |
Federation & Subgraphs
VPMS는 Apollo Federation을 사용하여 여러 서비스를 하나의 GraphQL 스키마로 통합합니다.
서비스 구성
- Core Service: 예약, 객실, 인증, 요금 관리
- Booking Service: 공개 구매, 결제 처리
- User Service: 사용자, 인증, 검색
- Subscription Service: 구독, 알림
모든 서비스는 단일 endpoint를 통해 접근 가능하며, Federation이 자동으로 쿼리를 적절한 서비스로 라우팅합니다.
크로스 서비스 쿼리
Federation을 통해 여러 서비스의 데이터를 한 번의 쿼리로 가져올 수 있습니다.
query GetReservationWithUser {
# Core Service에서 예약 조회
getReservation(id: "01HQKS9V8X") {
id
status
# User Service로 확장하여 사용자 정보 조회
user {
id
name
email
}
}
}
관련 문서
GraphQL API 관련 문의사항은 [email protected]로 연락주세요.