본문 바로가기

IT와 과학/API

구글 시트·엑셀 API 자동화 완전 가이드 | 인증·쿼터·오류 대처 + 10분 템플릿 (2025.10월 최신)

728x90
반응형

구글 시트·엑셀 API 자동화 완전 가이드 | 인증·쿼터·오류 대처 + 10분 템플릿 (2025 최신)

🆕 업데이트 (2025-10-04): Quick Start 스크립트 개선, 429 재시도 로직 추가, 엑셀 Power Query 헤더 예시 보강.

안녕하세요! 오늘은 **비개발자도 10분이면 따라 할 수 있는 '스프레드시트 × API 자동화'**를 소개해드릴게요.

매일 환율 정보를 복사-붙여넣기 하고 계신가요? 날씨 데이터를 일일이 검색해서 입력하시나요? 주가 정보를 수동으로 업데이트하고 계신가요? 이런 반복 작업들을 API 자동화로 해결할 수 있어요. 한 번만 설정해두면 웹 API 데이터를 시트로 자동 수집하고, 필요하다면 매시간 또는 매일 자동 갱신과 메일 발송까지 가능합니다.

핵심 요약

  • 두 가지 빠른 방법: A) 구글 시트 + Apps Script, B) 엑셀 + Power Query
  • 운영 체크리스트: 인증키 보관, 쿼터/429 처리, 캐싱/스케줄링, 로그/보안
  • 템플릿 코드 제공: 그대로 붙여넣고 필요한 값만 바꾸면 바로 동작합니다

왜 스프레드시트로 API 자동화를 해야 할까?

"굳이 스프레드시트로?" 하고 생각하실 수도 있어요. 하지만 스프레드시트를 활용한 API 자동화에는 몇 가지 큰 장점이 있습니다.

진입 장벽이 정말 낮아요

프로그래밍을 전혀 모르는 분들도 따라 할 수 있어요. 별도로 개발 환경을 설치할 필요 없이 웹 브라우저만 있으면 바로 시작할 수 있죠. 게다가 팀원들과 파일 하나만 공유하면 되니까 협업도 쉽습니다.

비용 효율이 정말 높아요

대부분의 무료 API나 저비용 API와 찰떡궁합이에요. 매일 반복되는 데이터 수집 작업을 자동화하면 하루 1시간씩 절약된다고 생각해보세요. 한 달이면 20시간, 1년이면 240시간이나 되죠. 이게 바로 업무 자동화의 진짜 가치입니다.

확장성이 뛰어나요

처음엔 간단한 데이터 수집으로 시작하지만, 나중엔 슬랙 알림, 메일 발송, 실시간 대시보드, 심지어 간단한 데이터 파이프라인(ETL)까지 만들 수 있어요. 작게 시작해서 점점 키워나갈 수 있다는 게 큰 장점이죠.


Quick Start A) 구글 시트 + Apps Script (10분)

구글 시트로 API 자동화를 시작하는 가장 빠른 방법입니다. 단계별로 천천히 따라오세요!

1단계: 시트 준비하기

구글 드라이브에서 새 스프레드시트를 만들어주세요. 그리고 기본으로 만들어진 시트의 이름을 DATA로 바꿔주세요. (시트 하단의 탭을 더블클릭하면 이름을 바꿀 수 있어요)

2단계: Apps Script 에디터 열기

상단 메뉴에서 확장 프로그램 → Apps Script를 선택합니다. 그러면 새 창이 열리면서 코드 에디터가 나타날 거예요. 처음 보시면 좀 낯설 수 있지만 걱정 마세요!

3단계: API 키 안전하게 보관하기

API 키를 코드에 직접 넣으면 보안에 취약해요. 그래서 구글이 제공하는 안전한 저장소를 사용할 거예요.

Apps Script 에디터 화면에서:

  1. 왼쪽 사이드바에 있는 톱니바퀴 아이콘(프로젝트 설정) 클릭
  2. 아래로 스크롤해서 스크립트 속성 섹션 찾기
  3. 스크립트 속성 추가 버튼 클릭
  4. 속성 이름에 API_KEY, 값에 실제 API 키 입력
  5. 스크립트 속성 저장 클릭

이렇게 하면 코드에는 키가 노출되지 않으면서도 안전하게 사용할 수 있어요!

4단계: 코드 붙여넣기

이제 실제로 API를 호출하고 데이터를 시트에 넣는 코드를 작성할 차례예요. 걱정 마세요, 복사-붙여넣기만 하면 됩니다!

코드가 길어서 모바일로 보시는 분들을 위해 기능별로 나눠서 설명드릴게요.


① 기본 설정 부분

const CFG = {
  API_URL: 'https://api.example.com/v1/data',
  SHEET: 'DATA'
};

이 부분은 뭐하는 코드인가요?

  • API_URL: 데이터를 가져올 API 주소예요. https://api.example.com/v1/data 부분을 실제 사용할 API 주소로 바꿔주세요.
  • SHEET: 데이터를 넣을 시트 이름이에요. 1단계에서 만든 DATA 시트를 사용합니다.

② 메인 함수 - API를 호출하고 시트에 저장하기

function fetchToSheet() {
  // 시트 찾기 (없으면 새로 만들기)
  const sh = SpreadsheetApp.getActive()
    .getSheetByName(CFG.SHEET) || 
    SpreadsheetApp.getActive()
    .insertSheet(CFG.SHEET);
  
  // API에 전달할 파라미터 설정
  const params = { 
    q: 'seoul',  // 검색어 (예: 서울)
    page: 1      // 페이지 번호
  };
  
  // URL 만들기
  const url = CFG.API_URL + '?' + 
    Object.entries(params)
    .map(([k,v])=>
      `${encodeURIComponent(k)}=` +
      `${encodeURIComponent(v)}`
    ).join('&');
  
  // 저장된 API 키 가져오기
  const apiKey = PropertiesService
    .getScriptProperties()
    .getProperty('API_KEY');
  
  // API 호출하기
  const resp = UrlFetchApp.fetch(url, { 
    headers: { 
      'Authorization': `Bearer ${apiKey}` 
    }, 
    muteHttpExceptions: true, 
    contentType: 'application/json' 
  });
  
  // 응답 코드 확인 (200이 정상)
  const code = resp.getResponseCode();
  if (code !== 200) {
    throw new Error(
      'API 오류: ' + code + ' ' + 
      resp.getContentText()
    );
  }
  
  // JSON 데이터를 파싱하기
  const json = JSON.parse(
    resp.getContentText()
  );
  
  // 필요한 데이터만 뽑아서 배열로 만들기
  const rows = json.items?.map(obj => [
    obj.id,         // ID
    obj.name,       // 이름
    obj.value,      // 값
    obj.updated_at  // 업데이트 시간
  ]) || [];
  
  // 시트 내용 전체 지우기
  sh.clear();
  
  // 헤더(첫 번째 줄) 넣기
  sh.getRange(1, 1, 1, 4)
    .setValues([[
      "id", "name", "value", "updated_at"
    ]]);
  
  // 데이터가 있으면 시트에 넣기
  if (rows.length) {
    sh.getRange(2, 1, rows.length, 4)
      .setValues(rows);
  }
}

이 부분은 뭐하는 코드인가요? 이 함수가 실제로 일하는 핵심 부분이에요. 하나씩 설명드릴게요:

  1. 시트 찾기: DATA라는 이름의 시트를 찾아요. 없으면 새로 만들어줍니다.
  2. 파라미터 설정: API에 전달할 검색 조건을 설정해요. 예시에서는 q=seoul(서울 검색), page=1(1페이지)를 보내고 있어요.
  3. URL 만들기: API 주소에 파라미터를 붙여서 완전한 URL을 만들어요.
  4. API 키 가져오기: 3단계에서 안전하게 저장한 API 키를 불러와요.
  5. API 호출: 실제로 웹 API를 호출해서 데이터를 받아와요.
  6. 에러 체크: 응답 코드가 200(정상)이 아니면 에러를 띄워요.
  7. 데이터 파싱: JSON 형태로 받은 데이터를 우리가 쓸 수 있게 변환해요.
  8. 배열 만들기: 각 항목에서 필요한 정보(id, name, value, updated_at)만 뽑아내요.
  9. 시트 초기화: 기존 데이터를 지워요.
  10. 헤더 넣기: 첫 번째 줄에 컬럼 이름을 넣어요.
  11. 데이터 넣기: 실제 데이터를 시트에 쓰기 시작해요.

💡 중요!: obj.id, obj.name 등은 실제 API 응답 구조에 맞게 바꿔야 해요. API 문서를 확인해서 어떤 필드명을 사용하는지 체크하세요!


③ 재시도 로직 - 429 에러 대비하기

function withRetry(fn, tries=3, baseMs=1000){
  for (let i=0; i<tries; i++){
    try { 
      return fn(); 
    } catch(e){ 
      if (i === tries-1) throw e; 
      Utilities.sleep(
        baseMs * Math.pow(2, i)
      ); 
    }
  }
}

이 부분은 뭐하는 코드인가요? API를 호출하다 보면 가끔 실패할 수 있어요. 특히 429 에러(너무 많이 요청해서 일시적으로 차단)가 자주 발생하죠.

이 함수는 실패하면 자동으로 재시도해주는 기능이에요:

  • 1차 시도 실패: 1초(1000ms) 기다린 후 재시도
  • 2차 시도 실패: 2초 기다린 후 재시도
  • 3차 시도 실패: 4초 기다린 후 재시도
  • 4차 시도 실패: 진짜 에러로 처리

기다리는 시간이 점점 길어지는 걸 **지수 백오프(Exponential Backoff)**라고 해요. 서버에 부담을 주지 않으면서 재시도할 수 있는 똑똑한 방법이죠!


④ 실행 및 자동화 함수

function run() { 
  withRetry(fetchToSheet, 4, 1200); 
}

function scheduleHourly(){ 
  ScriptApp.newTrigger('run')
    .timeBased()
    .everyHours(1)
    .create(); 
}

이 부분은 뭐하는 코드인가요?

run() 함수:

  • fetchToSheet 함수를 재시도 로직과 함께 실행해요
  • 최대 4번까지 재시도하고, 첫 대기 시간은 1.2초(1200ms)로 설정했어요

scheduleHourly() 함수:

  • 매시간 자동으로 run() 함수를 실행하도록 예약해주는 기능이에요
  • 한 번만 실행하면 되고, 그 다음부턴 알아서 매시간 돌아가요

5단계: 실행하기

이제 코드를 실행할 차례예요!

  1. 위의 모든 코드를 Apps Script 에디터에 붙여넣으세요
  2. 상단에 있는 함수 선택 드롭다운에서 run 선택
  3. ▶ 실행 버튼 클릭
  4. 처음 실행하면 권한 승인 창이 뜰 거예요:
    • "이 앱은 Google에서 확인하지 않았습니다" 경고가 나와도 괜찮아요
    • 고급 클릭 → [프로젝트명]으로 이동(안전하지 않음) 클릭
    • 허용 버튼 클릭
  5. 실행이 끝나면 DATA 시트를 확인해보세요. 데이터가 들어와 있을 거예요!

6단계: 자동화 설정하기

매번 수동으로 실행하기 귀찮죠? 자동화를 설정해봅시다!

  1. 함수 선택 드롭다운에서 scheduleHourly 선택
  2. ▶ 실행 버튼 클릭
  3. 이제 매시간마다 자동으로 데이터가 업데이트돼요!

왼쪽 사이드바의 **시계 아이콘(트리거)**을 클릭하면 설정된 자동화를 확인하고 관리할 수 있어요.

💡 Tip: 공공데이터포털 같은 일부 API는 Authorization 헤더 대신 URL에 직접 키를 넣어요 (?serviceKey=YOUR_KEY 형태). 그런 경우엔 params 객체에 serviceKey: apiKey를 추가하고, headers에서 Authorization 부분을 삭제하세요!


Quick Start B) 엑셀 + Power Query (10분)

엑셀을 사용하시는 분들을 위한 방법이에요. 구글 시트만큼 강력하지만 접근 방식이 조금 다릅니다.

1단계: 데이터 가져오기 시작

엑셀을 열고:

  1. 데이터 탭 클릭
  2. 데이터 가져오기기타 원본 선택
  3. 대화상자가 뜨면 고급 버튼 클릭

2단계: Power Query M 코드 입력

고급 모드로 전환되면 아래 코드를 붙여넣으세요.

let
  // API 호출 설정
  Source = Json.Document(
    Web.Contents(
      "https://api.example.com/v1/data",
      [ 
        // 쿼리 파라미터
        Query = [ 
          q = "seoul",     // 검색어
          page = "1"       // 페이지 번호
        ],
        // HTTP 헤더
        Headers = [ 
          Authorization = 
            "Bearer YOUR_API_KEY"  // ← 실제 API 키로 교체
        ] 
      ]
    )
  ),
  
  // 받아온 데이터에서 items 배열 추출
  Items = Source[items],
  
  // 배열을 테이블로 변환
  Table = Table.FromList(
    Items, 
    Splitter.SplitByNothing(), 
    null, 
    null, 
    ExtraValues.Error
  ),
  
  // 각 행의 레코드를 컬럼으로 펼치기
  Expand = Table.ExpandRecordColumn(
    Table, 
    "Column1", 
    {"id", "name", "value", "updated_at"}
  )
in
  Expand

코드 설명:

  • Source: API를 호출하고 JSON 데이터를 받아와요
  • Query: URL 파라미터를 설정해요 (예: ?q=seoul&page=1)
  • Headers: HTTP 헤더를 설정해요 (인증 키가 여기 들어가요)
  • Items: 받은 데이터에서 items 배열만 뽑아내요
  • Table: 배열을 엑셀 테이블 형태로 변환해요
  • Expand: 각 항목의 속성들을 컬럼으로 펼쳐요

⚠️ 주의: "Bearer YOUR_API_KEY" 부분을 실제 API 키로 바꿔야 해요!

📌 다른 인증 방식 사용하기:

  • 쿼리 파라미터 방식 (공공데이터포털 등): Query에 serviceKey = "YOUR_KEY" 추가
  • Basic Auth: Headers에 Authorization = "Basic " & Binary.ToText(Text.ToBinary("username:password"), BinaryEncoding.Base64)

3단계: 데이터 변환 및 로드

  1. 확인 버튼을 클릭하면 Power Query 에디터가 열려요
  2. 오른쪽 쿼리 설정 패널에서 각 단계를 확인할 수 있어요
  3. 데이터가 제대로 들어왔는지 미리보기로 확인하세요
  4. 모든 게 정상이면 닫기 및 로드 클릭
  5. 새로운 시트에 데이터가 테이블 형태로 만들어져요!

4단계: 새로 고침 설정

수동 새로 고침

데이터를 업데이트하고 싶을 때:

  • 테이블 아무 곳이나 클릭 → 데이터 탭 → 모두 새로 고침 클릭

자동 새로 고침

  1. 테이블에서 마우스 오른쪽 클릭
  2. 쿼리편집 선택
  3. Power Query 에디터 상단에서 쿼리 속성
  4. 원하는 옵션 선택:
    • 파일을 열 때 자동으로 새로 고침: 엑셀 파일을 열 때마다 업데이트
    • 주기적으로 새로 고침: 원하는 시간(분) 간격 설정

5단계: Windows 작업 스케줄러로 완전 자동화 (선택)

매일 아침 자동으로 데이터를 업데이트하고 메일까지 보내고 싶다면:

  1. Windows 작업 스케줄러 실행 (시작 메뉴에서 검색)
  2. 기본 작업 만들기 클릭
  3. 이름: "엑셀 API 자동 갱신"
  4. 트리거: "매일" 또는 "매주" 선택하고 시간 설정
  5. 작업: "프로그램 시작"
  6. 프로그램/스크립트에 아래 내용 입력:
excel.exe
  1. 인수 추가:
"C:\경로\내파일.xlsm" /e /x

⚠️ 회사 정책 확인: 일부 회사에서는 보안상 스크립트나 매크로, 작업 스케줄러 사용이 제한될 수 있어요. 반드시 IT 보안팀 가이드를 확인하고 승인받아 사용하세요!

📱 모바일 팁: 엑셀 코드는 PC에서 설정하는 게 훨씬 편해요. 설정 후 OneDrive나 SharePoint로 파일을 공유하면 모바일에서도 확인할 수 있어요!


운영 체크리스트 (실무에서 꼭 확인하세요!)

API 자동화를 실제 업무에 활용할 때는 이런 점들을 꼭 체크해주세요.

1. 인증키는 안전하게 보관

  • 구글 시트: Script Properties에 저장 (절대 코드에 직접 입력 ✗)
  • 엑셀: 환경변수, 암호화된 설정 파일, 또는 Azure Key Vault 같은 보안 저장소 사용
  • 절대 금지: 코드에 하드코딩, Git에 커밋, 이메일로 전송

2. 쿼터 및 429 에러 관리

429 에러는 "Too Many Requests", 즉 너무 많이 요청해서 일시 차단된 상태예요.

대처 방법:

  • 지수 백오프: 1.2초 → 2.4초 → 4.8초 → 9.6초... 이렇게 대기 시간을 늘려가며 재시도
  • 캐싱 적용: 같은 데이터를 반복 요청하지 말고, 이전 결과를 저장해두고 재사용
  • 요청 분산: 모든 데이터를 한 번에 받지 말고, 시간대를 나눠서 받기
  • 쿼터 모니터링: API 대시보드에서 사용량 확인

3. 캐싱 전략

매번 전체 데이터를 받아올 필요가 없어요. 변경된 부분만 받아오면 훨씬 효율적이죠.

// 마지막 업데이트 시간 이후 데이터만 가져오기
const params = {
  asof: '2025-10-04',  // 특정 날짜 이후
  // 또는
  updated_after: lastUpdateTime  // 마지막 업데이트 이후
};

4. 스케줄링과 로그

  • 적절한 주기 설정:
    • 실시간 필요 없으면 매시간보다는 매일로
    • 서버 부담을 고려해서 새벽 시간대 활용
  • 로그 남기기: 언제, 어떤 데이터를, 얼마나 받았는지 기록
  • 실패 알림: 에러 발생 시 메일이나 슬랙으로 즉시 알림
function logExecution(status, message) {
  const logSheet = SpreadsheetApp.getActive()
    .getSheetByName('LOG');
  const timestamp = new Date();
  logSheet.appendRow([timestamp, status, message]);
  
  // 실패 시 메일 발송
  if (status === 'FAIL') {
    MailApp.sendEmail(
      'admin@company.com',
      'API 자동화 실패',
      message
    );
  }
}

5. 법률 및 약관 준수

  • robots.txt 확인: 웹사이트가 크롤링을 허용하는지 확인
  • API 이용약관: 사용 제한, 상업적 이용 가능 여부, 데이터 저장 기간 등 확인
  • 개인정보 보호: 개인정보가 포함된 데이터라면 GDPR, 개인정보보호법 준수
  • 저작권: 데이터의 저작권이 누구에게 있는지, 2차 가공이 가능한지 확인

6. 성능 최적화

스프레드시트는 데이터베이스가 아니에요. 한계가 있죠.

  • 구글 시트: 약 5~10만 행부터 느려지기 시작
  • 엑셀: 약 100만 행까지 가능하지만 역시 느려짐

해결 방법:

  • 요약 테이블 사용: 전체 데이터 대신 집계된 데이터만 저장
  • 피벗 테이블 활용: 원본은 숨기고 피벗으로만 보기
  • 분할 저장: 월별, 연도별로 시트를 나눠서 저장
  • 오래된 데이터 보관: 3개월 이상 된 데이터는 별도 파일로 이동

자주 묻는 질문(FAQ)

실제로 자주 받는 질문들을 정리했어요.

Q1. 정말 무료로만 운영 가능한가요?

A. 대부분의 경우 초기에는 무료 구간으로 충분해요. 예를 들어:

  • Google Apps Script: 실행 시간 하루 6시간까지 무료
  • 대부분의 공공 API: 하루 1,000~10,000건 무료
  • 구글 시트: 저장 용량 15GB까지 무료

하지만 트래픽이 늘어나면:

  • 유료 API 플랜으로 전환 필요
  • Google Workspace 유료 버전 고려 (더 높은 실행 시간 쿼터)
  • 전문 데이터베이스나 클라우드 서비스 검토

Q2. 401/403/500/429 오류가 계속 떠요. 어떻게 해야 하나요?

A. 각 에러 코드별로 다른 원인과 해결책이 있어요:

401 Unauthorized (인증 실패)

  • API 키가 잘못됨 → 키를 다시 확인하고 복사-붙여넣기
  • 키가 만료됨 → API 대시보드에서 새 키 발급
  • 키를 잘못된 위치에 넣음 → 헤더에 넣어야 하는지, 쿼리 파라미터에 넣어야 하는지 API 문서 확인
  • Bearer 토큰 형식 확인 → Bearer YOUR_KEY인지 YOUR_KEY만 넣어야 하는지 확인

403 Forbidden (권한 없음)

  • IP 주소가 차단됨 → API 대시보드에서 허용된 IP 목록에 추가
  • 도메인이 등록 안 됨 → 일부 API는 사용할 도메인을 미리 등록해야 해요
  • 플랜 제한 → 무료 플랜에서 지원하지 않는 기능일 수 있어요

500 Internal Server Error (서버 오류)

  • API 서버의 일시적 장애 → 몇 분 후 재시도
  • 잘못된 요청 파라미터 → API 문서를 확인하고 파라미터 형식 점검
  • 서버 점검 시간 → API 공지사항이나 상태 페이지 확인

429 Too Many Requests (과다 요청)

  • 요청 간격을 늘리세요 (예: 매 10초마다 → 매 30초마다)
  • 캐싱을 적용해서 불필요한 요청 줄이기
  • 지수 백오프로 재시도 (위에서 설명한 withRetry 함수 사용)
  • 스케줄을 분산 (예: 모든 요청을 9시에 하지 말고 9시, 10시, 11시로 나누기)

Q3. 시트가 너무 느려져요. 어떻게 해야 하나요?

A. 스프레드시트는 빅데이터용이 아니에요. 데이터가 많아지면 느려질 수밖에 없죠.

즉시 해결 방법:

  1. 행 수 줄이기
    • 최근 3개월 데이터만 유지
    • 오래된 데이터는 다른 시트나 파일로 이동
  2. 요약 테이블 사용
  3. // 전체 데이터 대신 일별 집계만 저장 const summary = data.reduce((acc, row) => { const date = row.date; if (!acc[date]) acc[date] = {sum: 0, count: 0}; acc[date].sum += row.value; acc[date].count += 1; return acc; }, {});
  4. 피벗 테이블 활용
    • 원본 데이터는 숨긴 시트에 보관
    • 보고용으로는 피벗 테이블만 표시
  5. 불필요한 수식 제거
    • 수식이 많으면 재계산 때문에 느려져요
    • 가능하면 값으로 변환 (복사 → 선택하여 붙여넣기 → 값)
  6. 분할 저장
    • 월별 시트 분리: DATA_2025_01, DATA_2025_02 식으로
    • 연도별 파일 분리: 데이터_2024.xlsx, 데이터_2025.xlsx

장기적 해결책:

  • 데이터가 계속 쌓인다면 구글 빅쿼리나 MySQL 같은 실제 데이터베이스로 전환 고려
  • 또는 구글 시트를 "대시보드"로만 사용하고, 원본 데이터는 DB에 저장

Q4. 여러 API를 한 번에 호출하고 싶어요.

A. 가능해요! 하지만 주의할 점이 있어요.

순차 실행 (안전하지만 느림)

function fetchMultipleAPIs() {
  // API 1 호출
  const data1 = fetchAPI1();
  writeToSheet(data1, 'SHEET1');
  
  // 잠깐 쉬기 (서버 부담 줄이기)
  Utilities.sleep(2000);
  
  // API 2 호출
  const data2 = fetchAPI2();
  writeToSheet(data2, 'SHEET2');
  
  // 또 쉬기
  Utilities.sleep(2000);
  
  // API 3 호출
  const data3 = fetchAPI3();
  writeToSheet(data3, 'SHEET3');
}

병렬 실행 (빠르지만 주의 필요)

function fetchMultipleAPIs() {
  // 모든 URL 준비
  const urls = [
    'https://api1.example.com/data',
    'https://api2.example.com/data',
    'https://api3.example.com/data'
  ];
  
  // 한 번에 요청
  const responses = UrlFetchApp.fetchAll(
    urls.map(url => ({
      url: url,
      headers: {'Authorization': `Bearer ${apiKey}`}
    }))
  );
  
  // 각 응답 처리
  responses.forEach((resp, i) => {
    const data = JSON.parse(resp.getContentText());
    writeToSheet(data, `SHEET${i+1}`);
  });
}

⚠️ 주의: 병렬 실행은 빠르지만 서버에 순간적으로 많은 요청을 보내서 차단될 수 있어요. 꼭 필요한 경우에만 사용하세요!

Q5. API 응답이 너무 복잡해요. 어떻게 파싱하나요?

A. JSON 구조가 복잡할 때는 단계적으로 접근하세요.

예시: 복잡한 JSON

{
  "status": "success",
  "data": {
    "items": [
      {
        "id": 1,
        "info": {
          "name": "상품A",
          "price": {
            "amount": 10000,
            "currency": "KRW"
          }
        },
        "tags": ["전자기기", "인기"]
      }
    ]
  }
}

파싱 코드

function parseComplexJSON(json) {
  // 1단계: 최상위에서 data 추출
  const data = json.data;
  
  // 2단계: items 배열 추출
  const items = data.items;
  
  // 3단계: 각 항목에서 필요한 정보 추출
  const rows = items.map(item => {
    // 중첩된 객체에서 값 꺼내기
    const name = item.info.name;
    const price = item.info.price.amount;
    const currency = item.info.price.currency;
    
    // 배열은 join으로 문자열 변환
    const tags = item.tags.join(', ');
    
    return [item.id, name, price, currency, tags];
  });
  
  return rows;
}

디버깅 팁:

// JSON 구조를 확인하고 싶을 때
Logger.log(JSON.stringify(json, null, 2));
// Apps Script 실행 후 보기 → 로그에서 확인 가능

Q6. 에러가 났을 때 자동으로 알림받을 수 있나요?

A. 물론이죠! 메일이나 슬랙으로 알림을 받을 수 있어요.

메일 알림 (구글 시트)

function fetchWithErrorNotification() {
  try {
    withRetry(fetchToSheet, 4, 1200);
    
    // 성공 로그
    logSuccess();
    
  } catch(e) {
    // 실패 시 메일 발송
    const subject = '[API 자동화] 오류 발생';
    const body = `
      오류 시간: ${new Date()}
      오류 내용: ${e.message}
      스택 트레이스: ${e.stack}
    `;
    
    MailApp.sendEmail(
      'your-email@company.com',
      subject,
      body
    );
    
    // 로그에도 기록
    logError(e.message);
  }
}

슬랙 알림 (Webhook 사용)

function sendSlackNotification(message) {
  const webhookUrl = 
    'https://hooks.slack.com/services/YOUR/WEBHOOK/URL';
  
  const payload = {
    text: message,
    channel: '#api-alerts',
    username: 'API Bot',
    icon_emoji: ':robot_face:'
  };
  
  UrlFetchApp.fetch(webhookUrl, {
    method: 'post',
    contentType: 'application/json',
    payload: JSON.stringify(payload)
  });
}

// 사용 예시
try {
  fetchToSheet();
} catch(e) {
  sendSlackNotification(
    `⚠️ API 자동화 실패: ${e.message}`
  );
}

Q7. API 키를 팀원들과 공유해도 되나요?

A. 되도록이면 각자 개인 키를 발급받는 게 좋아요.

개인 키를 써야 하는 이유:

  • 누가 얼마나 사용했는지 추적 가능
  • 문제 발생 시 책임 소재 명확
  • 한 사람이 퇴사해도 다른 사람에게 영향 없음
  • 보안 사고 시 피해 최소화

하지만 꼭 공유해야 한다면:

  1. Script Properties 활용 (구글 시트)
    • 팀원이 코드는 볼 수 있지만, 키는 못 봐요
    • 관리자만 키를 설정/변경 가능
  2. 환경변수 파일 분리 (엑셀)
  3. config.json (Git에 올리지 않음) { "apiKey": "실제키값" }
  4. 접근 권한 관리
    • 파일 편집 권한과 실행 권한을 분리
    • 필요한 사람에게만 최소 권한 부여

FAQ JSON‑LD

{
  "@context": "https://schema.org",
  "@type": "FAQPage",
  "mainEntity": [
    {"@type": "Question","name": "API 키는 어디에 보관하나요?","acceptedAnswer": {"@type": "Answer","text": "구글 시트는 Script Properties, 엑셀은 환경변수/암호화 파일/보안 저장소를 권장합니다."}},
    {"@type": "Question","name": "429 오류가 자주 납니다.","acceptedAnswer": {"@type": "Answer","text": "요청 주기를 늘리고, 결과 캐싱과 지수 백오프로 재시도하세요."}},
    {"@type": "Question","name": "무료로만 운영 가능한가요?","acceptedAnswer": {"@type": "Answer","text": "초기엔 무료 구간으로 충분하지만, 요청량이 늘면 유료 과금이 필요할 수 있습니다."}},
    {"@type": "Question","name": "시트가 느려지면 어떻게 하나요?","acceptedAnswer": {"@type": "Answer","text": "행 수를 줄이고, 요약 테이블로 전환하며, 오래된 데이터는 별도 보관하세요."}},
    {"@type": "Question","name": "여러 API를 동시에 호출할 수 있나요?","acceptedAnswer": {"@type": "Answer","text": "UrlFetchApp.fetchAll()을 사용하면 가능하지만, 서버 부담을 고려해 주의해서 사용하세요."}}
  ]
}

실전 예제: 환율 API 자동화

이론만으로는 감이 안 잡히시죠? 실제로 동작하는 환율 API 예제를 보여드릴게요!

한국수출입은행 환율 API 사용하기

1. API 키 발급받기

2. 전체 코드

const CFG = {
  API_URL: 'https://www.koreaexim.go.kr/site/program/financial/exchangeJSON',
  SHEET: 'EXCHANGE_RATE'
};

function fetchExchangeRate() {
  const sh = SpreadsheetApp.getActive()
    .getSheetByName(CFG.SHEET) || 
    SpreadsheetApp.getActive()
    .insertSheet(CFG.SHEET);
  
  // 오늘 날짜 (YYYYMMDD 형식)
  const today = Utilities.formatDate(
    new Date(), 
    'GMT+9', 
    'yyyyMMdd'
  );
  
  // API 키 가져오기
  const apiKey = PropertiesService
    .getScriptProperties()
    .getProperty('API_KEY');
  
  // URL 만들기
  const url = `${CFG.API_URL}?authkey=${apiKey}&searchdate=${today}&data=AP01`;
  
  // API 호출
  const resp = UrlFetchApp.fetch(url);
  const json = JSON.parse(resp.getContentText());
  
  // 데이터 가공
  const rows = json.map(item => [
    item.cur_unit,      // 통화코드 (USD, JPY 등)
    item.cur_nm,        // 국가/통화명
    item.ttb,           // 전신환(송금) 받으실때
    item.tts,           // 전신환(송금) 보내실때
    item.deal_bas_r,    // 매매 기준율
    item.bkpr,          // 장부가격
    today               // 기준일자
  ]);
  
  // 시트에 쓰기
  sh.clear();
  sh.getRange(1, 1, 1, 7).setValues([[
    "통화코드", "통화명", "받을때", 
    "보낼때", "기준율", "장부가격", "날짜"
  ]]);
  
  if (rows.length) {
    sh.getRange(2, 1, rows.length, 7)
      .setValues(rows);
  }
  
  // 숫자 컬럼 서식 지정
  sh.getRange(2, 3, rows.length, 4)
    .setNumberFormat('#,##0.00');
}

// 실행
function run() {
  withRetry(fetchExchangeRate, 3, 1000);
}

// 매일 오전 9시 실행
function scheduleDaily() {
  ScriptApp.newTrigger('run')
    .timeBased()
    .everyDays(1)
    .atHour(9)
    .create();
}

3. 실행 결과 시트에 이렇게 표시돼요:

통화코드 통화명 받을때 보낼때 기준율 장부가격 날짜

USD 미국 달러 1,320.00 1,340.00 1,330.00 1,330.00 20251004
JPY(100) 일본 엔 920.50 935.10 927.80 927.80 20251004

매일 아침 9시마다 자동으로 업데이트됩니다!


이미지 프롬프트(Adobe Firefly)

블로그 포스팅에 사용할 이미지를 생성하고 싶다면 아래 프롬프트를 활용해보세요.

  1. 메인 썸네일: "Google Sheets UI 위에 API → Sheet 데이터 흐름, 청록 그라디언트, 한글 라벨, 4K, 아이소메트릭"
  2. 엑셀 파워쿼리: "Excel Power Query 창 + JSON 데이터 연결 장면, 미니멀 대시보드, 4K"
  3. 자동화 컨셉: "시계/번개/화살표 아이콘이 스프레드시트와 연결된 자동화 포스터, 파랑/초록 계열, 모던"
  4. 프로세스 다이어그램: "API 호출 → 캐싱 → 리포트 생성 흐름 다이어그램, 심플 라인아트, 4K"
  5. 알림 기능: "메일 알림 아이콘과 스프레드시트 썸네일, 밝은 톤, 4K"

내부 링크(추천)

이 글과 함께 보면 좋은 다른 포스팅들이에요.

  • 한국의 주요 증권 관련 API 소개
  • 한국 주식 API 생태계 완전 가이드 (허브)
  • 키움증권 REST API 분봉/주문 튜토리얼
  • Windows 작업 스케줄러 × Outlook 자동 메일 (다음 글)

해시태그

#구글시트, PowerQuery ,공공데이터API ,API자동화 ,스프레드시트 ,오피스자동화 ,429오류 ,캐싱 ,AppsScript ,2025최신


마무리

구글 시트와 엑셀을 활용한 API 자동화, 생각보다 어렵지 않죠?

한 번 세팅해두면 매일 반복되는 데이터 수집 작업에서 완전히 해방될 수 있어요. 환율 정보든, 날씨 데이터든, 주식 시세든 원하는 정보를 자동으로 받아보면서 업무 효율을 크게 높일 수 있습니다.

처음에는 간단한 것부터 시작하세요. 하루 한 번 업데이트되는 데이터 하나만 자동화해도 큰 변화를 느낄 수 있을 거예요. 그리고 점점 더 복잡한 자동화로 확장해나가면 됩니다.

 

궁금한 점이나 잘 안 되는 부분이 있다면 댓글로 남겨주세요. 최대한 자세히 답변드리겠습니다! 😊

P.S. 이 글이 도움이 되셨다면 북마크해두고, 주변 분들과도 공유해주세요. API 자동화로 업무 효율을 높이는 분들이 더 많아졌으면 좋겠어요! 📊✨

728x90
반응형