알라딘 OpenAPI 의 초상 - Part 2
지난 포스트에서는 API 가 제공하는 데이터를 살펴보았습니다. 오늘은 API 를 사용하는 과정에서 만난 기술적인 문제들을 다룹니다.
JSON 과 JSONP 를 분명히 구분할 필요가 있지 않을까요?
제가 사용한 API 의 엔드포인트는 http://www.aladin.co.kr/ttb/api/ItemLookUp.aspx 이고, 알라딘에서는 “상품API” 라고 부릅니다. API 에 대한 설명은 상품API안내 에서 제공됩니다. API 는 결과를 XML, RSS, JSON 중에서 사용자가 선택한 형식으로 제공합니다. 저는 이 중 JSON 을 선호하고, 이번에 사용한 것이기도 합니다. Output 파라미터를 JS 라고 지정하면 JSON 을 제공합니다. 그런데 CallBack 이라는 파라미터로 “호출 후 불려질 javascript function의 이름을 지정” 할 수 있다고 설명하고 있습니다. JSONP 처럼 들립니다. 실제로 CallBack=callme 라고 주면 callme(true, {…}); 형태의 결과가 옵니다. 문서에서는 찾아볼 수 없지만, 첫 번째 인자는 오류여부를 표시하는데 사용되는 것으로 확인되었습니다. JSONP 를 제공하는 것은 브라우저에서 API 를 직접 호출하는 경우 CSRF 차단을 피하려는 의도겠지요. 그런데 API 를 브라우저 자바스크립트로만 사용하라는 것은 아닐 터이니, CallBack 파라미터를 주지 않으면, 그냥 JSON 을 돌려주는 것이 사용자들이 기대하는 행동일 것입니다. 그런데 이 경우 {…}; 를 돌려줍니다. 함수명과 괄호는 제거했지만 마지막 세미콜론은 남겨두었네요. 이번에 사용한 파이썬의 경우 JSON 해석기는 에러를 일으킵니다. 마지막 세미콜론을 제거한 후 해석기로 넘겨야 했습니다.
결과 값으로 JSON 이나 JSONP 중 어느 것이 전달되는지 분명히 문서화하고, JSON 의 경우는 규격을 정획히 지켜주었으면 하는 바램입니다.
에러도 JSON 으로 주시면 고맙지요
상품API 를 사용하다 보면 종종 에러가 발생합니다. 늘 8번 에러가 발생하는데, 이 에러는 그런 책이 없다는 뜻입니다. 왜 그런지는 신만이 아시겠지만 굉장히 자주 발생하고, 즉시 재시도하면 대부분 성공합니다. 지금 성공했지만 같은 책에 대한 요청이 나중에 실패할 수도 있습니다. 두 번 만에 항상 성공한다는 보장은 없습니다. 재시도 전에 지연을 줘도 차이는 없습니다. 빈도를 조사하고 약간의 계산을 해보면 뒤에 숨은 기작을 추정해볼 수 있을지 모르겠습니다만, 그건 천기를 누설하는 일이 될지도 몰라, 그냥 세 번만 재시도 하기로 합니다. 그런데 이 에러메시지가 문제입니다. 항상 { 'errorCode':8, 'errorMessage':'키에 해당하는 상품이 존재하지 않습니다.' } 가 옵니다. 이번에는 끝에 세미콜론을 제거했네요. 그런데 JSON 은 이중따옴표만을 사용합니다. 전달된 문자열은 자바스크립트 코드일 뿐 JSON 이 아닙니다. 역시 JSONP 만 고려하고 있네요.
오류 보고도 동일한 해석기에 의해 처리될 수 있어야 한다는 원칙을 지켜주면 좋겠습니다. 오류 역시 문서화 대상임은 아무리 강조해도 지나치지 않습니다.
응답은 분명하게 정의되어야 합니다
ItemId 파라미터로 조회할 상품의 코드 값을 지정합니다. 사용 가능한 코드 값은 세 가지인데 알라딘 고유의 상품 코드 외에 두 가지 종류의 ISBN 을 사용 가능합니다. ItemId 로 전달한 코드가 어떤 종류인지는 ItemIdType 파라미터를 통해 알려줍니다. 알라딘 고유의 상품 코드는 웹 페이지에 사람이 읽을 수 있는 형태로 나타나지 않기 때문에, ISBN 을 사용하는 편이 사용 성 측면에서 좋습니다. ISBN 은 원래 10자리였는데, 더 이상 나눠줄 영역이 없어서 2007년 13자리로 늘려 ISBN13으로 변경했습니다. 기존의 ISBN 은 이와 구분해서 ISBN10 이라고 부릅니다. ISBN10 의 모든 코드를 ISBN13으로 변환할 수 있기 때문에 지금 만드는 시스템이라면 ISBN13을 쓰는 것이 당연해 보입니다. 그렇지만 알라딘 OpenAPI 의 경우에는 그렇지 않습니다. ISBN13 9788987931357 를 사용하여 API 를 호출하면 다음과 같은 결과를 얻습니다. 앞서 말씀 드린 JSON 의 문제점들은 손본 상태입니다.
{
"version": "20070901",
"title": "알라딘 상품정보 - 숨겨진 맛, 북한전통음식",
"link": "http://www.aladin.co.kr/shop/wproduct.aspx?ISBN=E898793135",
"pubDate": "Tue, 27 Aug 2013 08:17:27 GMT",
"imageUrl": "http://www.aladin.co.kr/ucl_editor/img_secur/header/2010/logo.jpg",
"totalResults": 1,
"startIndex": 1,
"itemsPerPage": 1,
"query": "isbn13=9788987931357",
"searchCategoryId": 0,
"searchCategoryName": "",
"item": [
{
"title": "숨겨진 맛, 북한전통음식",
"link": "http://www.aladin.co.kr/shop/wproduct.aspx?ISBN=E898793135",
"author": "한식재단 지음",
"pubDate": "2013-08-31",
"description": "",
"creator": "aladin",
"isbn": "E898793135",
"isbn13": "9788987931357",
"itemId": 30599363,
"priceSales": 7000,
"priceStandard": 7000,
"stockStatus": "",
"mileage": 210,
"cover": "http://image.aladin.co.kr/product/3059/93/cover/e898793135_1.jpg",
"categoryId": 56827,
"categoryName": "eBook>가정/요리/뷰티>음식 이야기",
"publisher": "한국외식정보",
"customerReviewRank": 0,
"ebookinfo": {
"paperBookList": [
{
"itemId": 30579573,
"isbn": "8987931358",
"priceSales": 8550,
"link": "http://www.aladin.co.kr/shop/wproduct.aspx?ISBN=8987931358"
}
],
"fileFormatList": [
{
"fileType": "PDF",
"fileSize": 8949336
}
]
}
}
]
}
link, cover, isbn 항목들을 잘 보시면 E898793135 라는 코드가 등장합니다. E 로 시작하는 ISBN 은 존재하지 않고, 이 코드는 알라딘 내부에서 전자 책을 지정하는데 사용하는 내부 코드일 뿐입니다. 즉 이 결과는 전자 책 버전에 관한 내용이고, 종이 책에 대한 내용은 paperBookList 라는 항목에 부록처럼 등장합니다. 반면에 ISBN10 8987931358으로 요청하면 종이 책에 관한 정보가 나옵니다. 그러면 ISBN13 은 전자 책을 더 선호하는 것일까요? 그렇지도 않습니다. 정유정씨의 신작 “28” 의 경우는 종이 책을 줍니다. 결론을 내리자면 ISBN13으로 요청할 경우 전자 책이 올지 종이 책이 올지는 알 수 없습니다. 둘 중 하나를 지정하거나, 둘 모두를 달라고 할 수 있는 파라미터도 없습니다. ISBN10을 사용하는 것이 현재로서는 가장 손쉬워 보이는 선택입니다.
요청의 결과가 어떻게 될지 문서만으로 추측할 수 있다면 많은 시간을 절약할 수 있을 겁니다.
데이터는 API 에 우선한다
이런 몇 가지 불편함에도 불구하고 “알라딘 OpenAPI” 는 계속 사용하게 될 것 같습니다. API 에 약간의 결함이 있어도 우회 책이 있는 경우 여전히 데이터의 힘이 우선한다는 증거이기도 합니다. 하지만 데이터의 신뢰도는 다른 소스의 데이터와 교차 대조하는 방법을 통해서만 개선될 수 있습니다. 이 때문에 “이 한 권의 책” 도 언젠가는 다른 서점과도 연결해야 할 것 같습니다. 당연한 이야기지만 앞서 기록한 내용은 2013년 8월 23일 기준입니다. API 나 데이터가 그 이후에 어찌 바뀔지는 알 수 없지요. 알라딘의 건승을 기원합니다.