FoodLens · CaloAI REST API

FoodLens API 문서

FoodLens(CaloAI) REST API는 음식 사진 한 장을 받아, 사진 속 음식마다 이름, 위치, 1회 제공량, 재료, 칼로리와 36종 영양소를 JSON으로 돌려주는 음식 이미지 인식 API입니다. 이 문서는 기능과 응답 구조를 소개합니다.

이 문서는 공개용 개요입니다. 서버 주소, 인증 방식, 요청 파라미터는 계약 후 제공하는 전체 명세서에서 안내합니다. 문의: sales@doinglab.com

개요

멀티 인식한 장의 사진에서 여러 음식을 각각 구분하고, 음식마다 사진 속 위치를 돌려줍니다.
36종 영양소 + 식품군칼로리, 탄단지부터 비타민·무기질, 아미노산, 지방산, 식품교환단위까지.
재료 정보음식을 이루는 재료와 무게를 함께 제공합니다.
전세계 음식분류체계와 재료를 함께 인식해 데이터셋에 없는 음식도 재료 기반으로 계산합니다.
다국어 결과CaloAI는 한국어·영어·일본어, FoodLens는 한국어·영어 결과를 지원합니다.
SDK와 RESTAndroid·iOS SDK(Sample UI 포함)와 REST API 중에서 고를 수 있습니다.

CaloAI는 FoodLens 2.0 엔진입니다. 응답 형식은 FoodLens와 같고, 일부 필드(식품군 등)는 CaloAI에서만 채워집니다.

기능과 엔드포인트

경로는 서버 주소를 뺀 상대 경로입니다.

POST/caloai

음식 인식 — 음식 사진(multipart/form-data)을 보내면 인식된 음식 목록을 돌려줍니다. 응답 보기

/caloai/foodinfo/{id}

음식 정보 조회 — 음식 ID로 그 음식의 제공량과 영양 정보를 돌려줍니다. 응답 형식은 음식 인식 결과와 같습니다. 응답 보기

음식 검색

음식 검색 — 음식 이름으로 영양 DB(28만 개 이상)를 찾아, 간단 목록(ID·이름) 또는 상세 목록(제공량·칼로리 포함)을 돌려줍니다. 경로는 전체 명세서에서 안내합니다. 응답 보기

Android·iOS SDK

앱에 바로 붙이려면 REST API 대신 SDK를 쓸 수 있습니다. 카메라·결과·음식 검색 화면이 들어 있는 UI SDK와, 화면을 직접 만드는 Core SDK를 제공합니다. SDK 응답도 이 문서의 응답 형식과 같습니다.

Android SDKminSdkVersion 26 이상, Gradle로 설치합니다. UI SDK는 AGP 8.1 이상이 필요합니다.
iOS SDKiOS 14.0 이상, Swift Package Manager로 설치합니다.
GitHub설치 방법, 예제 코드, 샘플 앱, V2→V3 마이그레이션 가이드를 볼 수 있습니다.

공통 응답 형식

모든 응답은 application/json이며 아래 구조로 감싸져 있습니다.

필드형식설명
successBoolean처리 결과. 성공하면 true, 실패하면 false
codeString처리에 문제가 있을 때의 오류 코드. 예: server.error(서버 내부 오류). 성공하면 빈 문자열
bodyArray결과 목록. 음식 인식·정보 조회는 음식 객체, 검색은 검색 결과 객체
pathString처리 경로 정보. 보통 빈 문자열

음식 인식 응답

사진 속 음식마다 body에 음식 객체가 하나씩 들어갑니다. 아래 예시는 새우 오일 파스타 한 접시를 인식한 결과입니다(값은 예시).

음식 객체

필드형식설명
nameString기본 음식 이름. 예: Oil Pasta
fullNameString음식과 재료를 합친 이름. 예: Prawn Oil Pasta
positionObject사진 속 음식 위치(픽셀). xmin, xmax, ymin, ymax
candidatesArray음식 후보 목록. FoodLens는 5개, CaloAI는 1개를 돌려줍니다(옵션으로 여러 후보 요청 가능)
ingredientsArray재료 목록. name(재료 이름), gram(1회 제공량 기준 무게)

후보(candidates) 객체

필드형식설명
idNumber음식 ID. CaloAI는 -1
manufacturerString제조사(가공식품·프랜차이즈)
foodNameString기본 음식 이름
fullFoodNameString음식과 재료를 합친 이름
foodTypeString음식 종류(주류 등)
servingSizeNumber1회 제공량
totalServingSizeNumber총 내용량(값이 있을 때)
unitString제공량 단위(g, ml)
countsString제공 단위 이름. 예: plate(L)
countsDetailArray단위 상세. countType은 serving(1회 제공량)과, 총 내용량이 다를 때 함께 오는 total. 각 항목에 servingSize, countsValue, counts, 보조 단위 subCountsValue·subCounts
ingredientsArray이 후보의 재료 목록
energy …Number칼로리와 영양소. 영양소 필드 참고

값이 없으면 숫자는 -1, 문자열은 빈 문자열로 옵니다.

응답 예시

{
  "body": [
    {
      "name": "Oil Pasta",
      "fullName": "Prawn Oil Pasta",
      "position": { "xmin": 27, "xmax": 712, "ymin": 43, "ymax": 508 },
      "candidates": [
        {
          "id": -1,
          "manufacturer": "",
          "foodName": "Oil Pasta",
          "fullFoodName": "Prawn Oil Pasta",
          "foodType": "",
          "servingSize": 388.0,
          "totalServingSize": 388.0,
          "unit": "g",
          "counts": "plate(L)",
          "countsDetail": [
            { "countType": "serving", "servingSize": 388.0, "countsValue": 1.0, "counts": "plate(L)", "subCountsValue": -1.0, "subCounts": "" }
          ],
          "ingredients": [
            { "name": "Noodles", "gram": 250.0 },
            { "name": "Prawn", "gram": 80.0 },
            { "name": "Oil", "gram": 50.0 },
            { "name": "Parmesan", "gram": 5.0 },
            { "name": "Salt", "gram": 2.5 },
            { "name": "Black pepper", "gram": 0.5 }
          ],
          "energy": 872.21,
          "carbohydrate": 68.36,
          "protein": 25.46,
          "fat": 51.9,
          "totalSugars": 0.0,
          "totalDietaryFiber": 0.0,
          "calcium": 117.31,
          "iron": 2.96,
          "magnesium": 2.55,
          "phosphorus": 220.11,
          "potassium": 363.71,
          "sodium": 1043.66,
          "zinc": 0.21,
          "selenium": 1.78,
          "retinol": 12.75,
          "betaCarotene": 5.54,
          "vitaminA": 13.21,
          "thiamin": 0.15,
          "riboflavin": 0.1,
          "niacin": 4.27,
          "vitaminB6": 0.0,
          "biotin": 0.05,
          "totalFolate": 0.38,
          "vitaminC": 0.8,
          "vitaminD": 0.03,
          "vitaminE": 40.68,
          "vitaminK": 86.14,
          "isoleucine": 74.42,
          "leucine": 141.49,
          "valine": 95.69,
          "bcaa": 5.21,
          "cholesterol": 5.3,
          "saturatedFattyAcid": 6.26,
          "epa": 0.0,
          "dha": 0.0,
          "omega3FattyAcid": 3.41,
          "omega6FattyAcid": 17.07,
          "transFattyAcid": 0.04,
          "grainGroup": -1.0,
          "proteinGroup": -1.0,
          "vegetableGroup": -1.0,
          "fruitGroup": -1.0,
          "oilGroup": -1.0,
          "sugarGroup": -1.0,
          "dairyGroup": -1.0
        }
      ],
      "ingredients": [
        { "name": "Noodles", "gram": 250.0 },
        { "name": "Prawn", "gram": 80.0 },
        { "name": "Oil", "gram": 50.0 },
        { "name": "Parmesan", "gram": 5.0 },
        { "name": "Salt", "gram": 2.5 },
        { "name": "Black pepper", "gram": 0.5 }
      ]
    }
  ],
  "path": "",
  "success": true,
  "code": ""
}

영양소 필드

모든 영양소 값은 1회 제공량(servingSize) 기준입니다. 값이 없으면 -1이 옵니다.

필드영양소단위
energy열량kcal
carbohydrate탄수화물g
protein단백질g
fat지방g
totalSugars당류g
totalDietaryFiber식이섬유g
saturatedFattyAcid포화지방g
transFattyAcid트랜스지방g
cholesterol콜레스테롤mg
sodium나트륨mg
calcium칼슘mg
iron철mg
magnesium마그네슘mg
phosphorus인mg
potassium칼륨mg
zinc아연mg
selenium셀레늄μg
vitaminA비타민Aμg
retinol레티놀μg
betaCarotene베타카로틴μg
thiamin티아민(비타민B1)mg
riboflavin리보플라빈(비타민B2)mg
niacin나이아신mg
vitaminB6비타민B6mg
biotin비오틴μg
totalFolate엽산μg
vitaminC비타민Cmg
vitaminD비타민Dμg
vitaminE비타민Emg
vitaminK비타민Kμg
isoleucine이소류신mg
leucine류신mg
valine발린mg
bcaaBCAA(분지사슬아미노산)mg
epaEPAmg
dhaDHAmg
omega3FattyAcid오메가3 지방산g
omega6FattyAcid오메가6 지방산g
grainGroup … dairyGroup식품교환단위(곡류군·어육류군·채소군·과일군·지방군·당류군·우유군)단위. CaloAI만 제공

음식 정보 조회 응답

음식 ID로 조회하면 해당 음식 하나의 정보가 음식 인식과 같은 형식으로 옵니다. 사진이 없으므로 position은 모두 0, ingredients는 빈 목록입니다.

{
  "body": [
    {
      "name": "Oil Pasta",
      "fullName": "Prawn Oil Pasta",
      "position": { "xmin": 0, "xmax": 0, "ymin": 0, "ymax": 0 },
      "candidates": [
        {
          "id": -1,
          "manufacturer": "",
          "foodName": "Oil Pasta",
          "fullFoodName": "Prawn Oil Pasta",
          "foodType": "",
          "servingSize": 388.0,
          "totalServingSize": 0.0,
          "unit": "g",
          "counts": "plate(L)",
          "countsDetail": [
            { "countType": "serving", "servingSize": 388.0, "countsValue": 1.0, "counts": "plate(L)", "subCountsValue": -1.0, "subCounts": "" }
          ],
          "energy": 872.21,
          "carbohydrate": 68.36,
          "protein": 25.46,
          "fat": 51.9,
          "totalSugars": 0.0,
          "totalDietaryFiber": 0.0,
          "sodium": 1043.66,
          "cholesterol": 5.3,
          "saturatedFattyAcid": 6.26,
          "transFattyAcid": 0.04,
          "grainGroup": -1.0,
          "proteinGroup": -1.0,
          "vegetableGroup": -1.0,
          "fruitGroup": -1.0,
          "oilGroup": -1.0,
          "sugarGroup": -1.0,
          "dairyGroup": -1.0
        }
      ],
      "ingredients": []
    }
  ],
  "path": "",
  "success": true,
  "code": ""
}

예시에서는 지면상 일부 영양소만 보였습니다. 실제 응답에는 영양소 필드의 모든 항목이 옵니다.

아래 결과의 음식 이름, ID, 값은 형식을 보여 주기 위한 예시입니다.

간단 목록

음식 ID와 이름, 제조사만 돌려줍니다. 고른 음식의 상세 정보는 음식 정보 조회로 가져옵니다.

{
  "body": [
    { "id": 6699, "foodName": "Steamed Steak", "manufacturer": "" },
    { "id": 6702, "foodName": "Grilled Sirloin Steak", "manufacturer": "" },
    { "id": 789, "foodName": "Pork Chop Steak", "manufacturer": "" }
  ],
  "success": true,
  "code": ""
}

상세 목록

제공량과 칼로리, 제공 단위까지 함께 돌려줍니다. 숫자 값도 문자열로 옵니다.

{
  "body": [
    { "id": 360021, "foodName": "연어", "manufacturer": "부경수산", "weight": "100g", "energy": "261.0", "countsValue": "1", "counts": "총 내용량", "subCountsValue": "", "subCounts": "" },
    { "id": 94911, "foodName": "연어초밥", "manufacturer": "", "weight": "180g", "energy": "287.5", "countsValue": "1", "counts": "인분", "subCountsValue": "6", "subCounts": "개" },
    { "id": 94912, "foodName": "연어감자조림", "manufacturer": "", "weight": "125g", "energy": "140.24", "countsValue": "1", "counts": "접시(중)", "subCountsValue": "", "subCounts": "" }
  ],
  "success": true,
  "code": ""
}

오류 응답

HTTP 상태의미
401 Unauthorized인증 정보가 없거나 맞지 않음
402 Payment Required호출 한도를 넘었거나 결제가 필요함
403 Forbidden계약에 포함되지 않은 기능을 호출함
404 Not Found없는 주소이거나 지원하지 않는 주소
406 Not Acceptable등록된 앱 정보와 맞지 않음
5xx Server Error예상하지 못한 서버 오류. 본문 code는 server.error

값 계산 방법

도입 절차

  1. 이메일 sales@doinglab.com 또는 전화 02-6959-5657로 도입을 문의합니다.
  2. 계약 후 API 키, 서버 주소, 요청 파라미터가 담긴 전체 명세서를 받습니다.
  3. 3개월 무료 테스트 기간(FoodLens 최대 3,000회 호출) 동안 개발과 검증을 진행합니다.
  4. 앱에 바로 붙이려면 Sample UI가 포함된 Android·iOS SDK를 쓸 수 있습니다. 설명서: Android · iOS

요금은 FoodLens 요금에서 볼 수 있습니다. 가입 없이 먼저 써 보려면 다이어트카메라 앱이나 푸드렌즈 카카오톡 채널에 음식 사진을 올려 보세요.

FoodLens API 도입 문의

서비스에 맞는 요금제와 전체 API 명세서를 안내해 드립니다. 모든 플랜에 3개월 무료 테스트가 포함됩니다.