로컬 LLM vs 클라우드 API 보안 비교 — 민감한 코드 안전하게 다루는 법

요즘 개발할 때 LLM을 안 쓰는 사람이 드물다. 코드 리뷰, 리팩토링, 디버깅, 문서 작성까지 — Claude나 GPT에 코드를 붙여넣고 “이거 고쳐줘”라고 하는 게 일상이 됐다. 그런데 한 번쯤 생각해봐야 할 게 있다. 내가 보낸 그 코드, 대체 어디로 가는 걸까?

회사에서 내부 API 키가 박힌 설정 파일을 Claude에 붙여넣은 적이 있다. .env 파일 내용을 통째로 복사해서 “이 환경변수 설정 맞는지 확인해줘”라고 물어봤다. 그 순간, AWS 시크릿 키와 데이터베이스 비밀번호가 Anthropic 서버로 전송된 거다. 돌이킬 수 없는 일이었다. 그때부터 로컬 LLM을 진지하게 알아보기 시작했고, 지금은 작업 성격에 따라 로컬과 클라우드를 나눠 쓰고 있다.

이 글에서는 MacBook M1 32GB 환경 기준으로, 로컬 LLM(주로 Ollama)과 클라우드 API(Claude, OpenAI)의 보안 차이를 실전 관점에서 비교한다. 단순히 “로컬이 안전하다”가 아니라, 각 방식의 데이터 흐름을 구체적으로 추적하고, 상황별로 어떤 전략이 맞는지 정리했다.

왜 보안이 중요한가 — API 키, 소스코드, 내부 문서 유출 위험

LLM에 보내는 데이터의 종류를 한번 나열해보면, 생각보다 심각한 것들이 많다. 관련 내용은 Mac Ollama 로컬 LLM 가이드에서도 다루고 있다.

  • API 키와 시크릿: .env 파일, 설정 파일에 들어있는 AWS_SECRET_ACCESS_KEY, DATABASE_URL, STRIPE_SECRET_KEY 같은 값들. 이건 유출되면 금전적 피해로 직결된다.
  • 소스코드: 회사의 핵심 비즈니스 로직, 인증 처리 코드, 결제 로직. 경쟁사가 보면 안 되는 것들.
  • 내부 문서: 아키텍처 다이어그램, 인프라 구성도, 보안 감사 보고서. “이 문서 요약해줘”라고 할 때 통째로 전송된다.
  • 고객 데이터: 버그 재현을 위해 붙여넣는 로그에 사용자 이메일, IP, 세션 토큰이 포함되어 있는 경우가 많다.

Samsung 반도체 부서에서 ChatGPT에 내부 소스코드를 입력한 사건이 2023년에 보도됐고, 이후 많은 기업이 사내 LLM 사용 가이드라인을 만들었다. 하지만 현실적으로 개발자 개인이 매번 “이 코드 보내도 되나?”를 판단하기는 어렵다. 그래서 시스템 차원의 대응이 필요하다.

클라우드 API 데이터 흐름 분석

로컬 LLM — 설정 및 실행 결과 화면

Claude API든 OpenAI API든, 클라우드 LLM을 쓸 때 데이터가 거치는 경로는 기본적으로 동일하다.

요청에서 응답까지의 전체 경로

내가 코드를 붙여넣고 질문을 보내면, 다음 단계를 거친다.

  1. 클라이언트 → TLS 암호화 → 인터넷: HTTPS 연결이므로 전송 중 암호화는 된다. 중간에서 스니핑당할 가능성은 낮다.
  2. API 게이트웨이 도착: 요청이 서비스 제공자의 로드밸런서와 API 게이트웨이를 거친다. 여기서 인증 토큰 검증, rate limit 체크가 일어난다.
  3. 추론 서버 처리: GPU 클러스터에서 모델이 응답을 생성한다. 이 과정에서 프롬프트 전체가 메모리에 올라간다.
  4. 응답 반환 + 로그 저장: 응답이 돌아오고, 요청/응답 쌍이 로그에 저장될 수 있다. 이 부분이 핵심이다.

문제는 3번과 4번이다. 내 코드가 상대방의 서버 메모리에 올라가는 건 불가피하고, 그 이후에 얼마나 오래 어떤 형태로 보존되는지가 보안의 핵심 쟁점이다.

보통 간과하는 부분: 중간 경유지

API를 직접 호출하더라도, 실제로는 CDN, WAF, 로드밸런서 같은 인프라를 거친다. 각 단계에서 요청 본문이 로깅될 가능성이 있고, 서비스 제공자가 사용하는 하위 인프라(AWS, GCP 등)의 보안 정책도 간접적으로 적용된다. 결국 내 데이터의 보안은 하나의 회사가 아니라 그 회사가 의존하는 전체 인프라 체인의 보안 수준에 달려있다.

Claude API vs OpenAI API 데이터 정책 비교

두 서비스의 데이터 정책은 비슷해 보이지만, 중요한 차이가 있다. 2025년 기준 공식 문서 기반으로 정리했다.

Anthropic (Claude API)

  • 학습 데이터 사용: API를 통해 전송된 데이터는 모델 학습에 사용하지 않는다고 명시. 이건 웹 UI(claude.ai) 무료 플랜과 다른 부분이다.
  • 데이터 보존: 안전 목적(Trust & Safety)으로 최대 30일간 보존 가능. 이상 행동 탐지와 남용 방지 목적이다.
  • SOC 2 Type II 인증: 보유. 엔터프라이즈 고객 대상으로 BAA(Business Associate Agreement)도 체결 가능.
  • Zero Data Retention: 요청 시 가능하지만 별도 계약 필요.

OpenAI (GPT API)

  • 학습 데이터 사용: API 데이터는 모델 학습에 사용하지 않음. 2023년 3월 정책 변경 이후 적용. 다만 ChatGPT 웹/앱에서 입력한 데이터는 opt-out하지 않으면 학습에 쓰일 수 있다.
  • 데이터 보존: API 요청 데이터를 최대 30일간 보존 (남용 탐지 목적). 이후 자동 삭제.
  • SOC 2 Type II 인증: 보유. Enterprise 플랜에서는 추가적인 데이터 격리 옵션 제공.
  • Zero Data Retention: Enterprise 및 특정 플랜에서 가능.

정리하면

둘 다 “API 데이터는 학습에 안 쓴다”고 하지만, 최대 30일간 서버에 보존된다는 건 동일하다. 이 30일 동안 내부 직원이 접근할 수 있는지, 어떤 암호화로 보호되는지는 각 회사의 내부 보안 정책에 달려있다. 결국 “신뢰”의 문제다. 보안 감사를 통과했다는 건 최소 기준을 충족한다는 뜻이지, 절대적 안전을 보장하지는 않는다.

로컬 LLM의 보안 장점 — 데이터가 기기를 떠나지 않음

로컬 LLM의 가장 큰 장점은 단순하다. 데이터가 내 맥북 밖으로 나가지 않는다. 네트워크 연결이 아예 필요 없다. 비행기 안에서도 쓸 수 있고, 회사 VPN이 끊겨도 상관없다.

MacBook M1 32GB에서 Ollama를 설치하면, 다음과 같은 모델들을 로컬에서 돌릴 수 있다.

# Ollama 설치 (macOS)
brew install ollama

# 서버 시작
ollama serve

# 코드 작업에 적합한 모델 다운로드
ollama pull codellama:13b        # 7.4GB, 코드 특화
ollama pull deepseek-coder-v2:16b  # 8.9GB, 코드 + 일반
ollama pull llama3.1:8b          # 4.7GB, 범용

# 모델 실행 확인
ollama list
# NAME                      SIZE
# codellama:13b              7.4 GB
# deepseek-coder-v2:16b      8.9 GB
# llama3.1:8b                4.7 GB

32GB RAM이면 13B 파라미터 모델까지는 쾌적하게 돌아간다. 추론 속도는 초당 약 20~35토큰 정도로, 체감상 타이핑하는 것보다 약간 빠른 수준이다. Claude나 GPT-4o의 응답 속도(초당 60~80토큰)보다는 느리지만, 민감한 코드를 다룰 때는 속도보다 보안이 우선이다.

로컬 LLM의 보안 측면에서 핵심적인 포인트들을 정리하면 이렇다.

  • 네트워크 전송 없음: 프롬프트가 localhost(127.0.0.1)에서만 처리된다. 패킷 캡처를 해봐도 외부 전송이 없다.
  • 로그 통제 가능: 로그를 어디에 저장할지, 얼마나 보존할지 내가 직접 결정한다.
  • 모델 업데이트 제어: 모델 다운로드 시에만 네트워크를 쓰고, 이후 추론은 완전히 오프라인이다.
  • 디스크 암호화 연동: macOS의 FileVault가 켜져 있으면, 모델 파일과 대화 로그가 전부 디스크 수준에서 암호화된다.

Ollama 네트워크 격리 확인 방법

“로컬이니까 안전하겠지”라고 막연히 믿는 건 좋지 않다. 실제로 네트워크 트래픽을 확인해서 정말 외부로 데이터가 나가지 않는지 검증해야 한다. Ollama가 텔레메트리 데이터를 보내는지도 체크해야 한다.

# 1. Ollama 프로세스의 네트워크 연결 확인
lsof -i -n -P | grep ollama
# 정상 출력: ollama  12345  user  5u  IPv4  TCP 127.0.0.1:11434 (LISTEN)
# → localhost에서만 리스닝하고 있으면 OK

# 2. 실시간 네트워크 모니터링 (추론 중에 실행)
sudo nettop -p $(pgrep ollama) -J bytes_in,bytes_out -d
# → 추론 중에 외부 IP로 나가는 트래픽이 없어야 정상

# 3. 방화벽으로 Ollama 외부 접근 원천 차단 (macOS pf)
# /etc/pf.anchors/ollama.rules 파일 생성
echo "block drop out quick proto tcp from any to any port != 11434 user ollama" | sudo tee /etc/pf.anchors/ollama.rules

# 4. 텔레메트리 비활성화 (환경변수)
export OLLAMA_NOPRUNE=1
# .zshrc에 추가하여 영구 적용
echo 'export OLLAMA_NOPRUNE=1' >> ~/.zshrc

# 5. Ollama를 localhost에만 바인딩 (기본값이지만 명시적으로)
export OLLAMA_HOST=127.0.0.1:11434

특히 5번이 중요하다. Ollama의 기본 바인딩은 127.0.0.1이지만, 일부 가이드에서 0.0.0.0으로 바꾸라고 안내하는 경우가 있다. 이렇게 하면 같은 네트워크의 다른 기기에서도 접근할 수 있게 되므로, 반드시 localhost로 유지해야 한다. 회사 와이파이에서 0.0.0.0으로 열어두면 동료가 내 로컬 LLM에 접근할 수 있다는 뜻이다.

로컬 LLM의 현실적 한계

보안만 보면 로컬 LLM이 압도적으로 유리하다. 그런데 현실적으로는 한계가 분명하다.

성능 차이

MacBook M1 32GB에서 돌릴 수 있는 최대 모델 크기는 약 13B~16B 파라미터다. 이 수준의 모델은 Claude 3.5 Sonnet이나 GPT-4o와 비교하면 코드 품질에서 체감할 수 있는 차이가 난다. 특히 아래 작업에서 격차가 크다.

  • 복잡한 리팩토링: 여러 파일에 걸친 의존성을 파악하고 수정하는 작업. 로컬 13B 모델은 컨텍스트를 자주 놓친다.
  • 아키텍처 설계: “이 시스템을 마이크로서비스로 분리하려면?”같은 고수준 질문. 클라우드 모델의 답변이 훨씬 구체적이다.
  • 긴 코드 분석: 컨텍스트 윈도우가 4K~8K 토큰 수준이라 긴 파일을 통째로 넣기 어렵다. Claude는 200K, GPT-4o는 128K까지 넣을 수 있다.

모델 크기와 디스크

13B 모델 하나가 약 7~9GB다. 여러 모델을 설치하면 금방 수십 GB를 차지한다. 512GB SSD 맥북이라면 모델 관리에 신경을 써야 한다.

전력 소비

M1 칩의 전력 효율이 좋긴 하지만, 연속으로 추론을 돌리면 배터리가 눈에 띄게 줄어든다. 전원 연결 없이 카페에서 쓰기엔 부담스럽다.

하이브리드 전략 — 민감 작업은 로컬, 일반은 클라우드

결론적으로, 하나만 쓰는 건 비효율적이다. 내가 실제로 쓰는 전략은 간단한 기준 하나로 나눈다. “이 코드가 GitHub public repo에 올라가도 괜찮은가?” 괜찮다면 클라우드, 아니라면 로컬이다.

로컬 LLM으로 처리하는 작업

  • .env 파일이나 시크릿이 포함된 설정 파일 관련 질문
  • 인증/인가 로직 코드 리뷰
  • 내부 API 스펙이나 아키텍처 문서 분석
  • 고객 데이터가 포함된 로그 분석
  • 보안 취약점 분석 (취약점 자체가 민감 정보)

클라우드 API로 처리하는 작업

  • 오픈소스 라이브러리 사용법 질문
  • 일반적인 알고리즘 구현
  • 문서 작성, 번역
  • 민감 정보가 제거된 코드의 리팩토링
  • 디자인 패턴 적용 방법 논의

자동화 스크립트 예시

매번 수동으로 나누기 귀찮으니, 간단한 래퍼 스크립트를 만들어서 쓸 수 있다. 민감한 패턴이 감지되면 자동으로 로컬 모델로 라우팅한다.

#!/bin/bash
# ask-llm.sh — 민감도 기반 LLM 라우팅 스크립트

PROMPT="$1"
LOCAL_URL="http://127.0.0.1:11434/api/generate"
CLOUD_API="https://api.anthropic.com/v1/messages"

# 민감 패턴 체크
SENSITIVE_PATTERNS="(API_KEY|SECRET|PASSWORD|TOKEN|PRIVATE_KEY|aws_secret|database_url|BEGIN RSA)"

if echo "$PROMPT" | grep -qiE "$SENSITIVE_PATTERNS"; then
    echo "[!] 민감 패턴 감지 → 로컬 LLM (codellama:13b) 사용"
    curl -s "$LOCAL_URL" \
        -d "{\"model\": \"codellama:13b\", \"prompt\": \"$PROMPT\", \"stream\": false}" \
        | jq -r '.response'
else
    echo "[i] 일반 요청 → Claude API 사용"
    curl -s "$CLOUD_API" \
        -H "x-api-key: $ANTHROPIC_API_KEY" \
        -H "anthropic-version: 2023-06-01" \
        -H "content-type: application/json" \
        -d "{
            \"model\": \"claude-sonnet-4-20250514\",
            \"max_tokens\": 4096,
            \"messages\": [{\"role\": \"user\", \"content\": \"$PROMPT\"}]
        }" | jq -r '.content[0].text'
fi

이건 단순한 예시이고, 실제로는 정규식으로 잡히지 않는 민감 정보도 많다. 그래도 최소한의 안전장치 역할은 한다. 좀 더 정교하게 만들려면, git-secrets나 detect-secrets 같은 도구의 패턴 목록을 가져다 쓰면 된다.

기업 환경에서의 선택 기준

개인 프로젝트라면 본인 판단으로 결정하면 되지만, 기업 환경에서는 좀 더 체계적인 기준이 필요하다.

규모별 권장 접근법

  • 1~10인 스타트업: Claude API나 OpenAI API의 Team 플랜을 쓰되, 민감 코드는 개인 장비의 로컬 LLM으로 처리. 별도 인프라 구축은 비용 대비 효과가 낮다.
  • 10~100인 중소기업: 사내 GPU 서버에 vLLM이나 Ollama를 올려서 사내 전용 LLM 서버를 운영하는 것이 현실적이다. RTX 4090 한 장(약 200만원)이면 70B 모델도 양자화해서 돌릴 수 있다.
  • 100인 이상: Anthropic이나 OpenAI의 Enterprise 플랜 도입. Zero Data Retention 계약, 전용 인스턴스, SSO 연동, 감사 로그까지 지원된다. 또는 Azure OpenAI Service처럼 자체 클라우드 내에 모델을 배포하는 방식도 가능.

규제 산업의 경우

금융, 의료, 국방 분야라면 클라우드 LLM 사용 자체가 규제로 막힌 경우가 많다. 이런 환경에서는 로컬 또는 온프레미스 LLM이 사실상 유일한 선택지다. HIPAA, PCI-DSS 같은 규정을 준수하려면 데이터가 지정된 물리적 경계를 벗어나면 안 되기 때문이다.

네트워크 모니터링으로 데이터 유출 확인하기

로컬 LLM을 쓰든 클라우드를 쓰든, 실제로 어떤 데이터가 외부로 나가는지 모니터링하는 습관이 중요하다. macOS에서 쓸 수 있는 방법 몇 가지를 정리한다.

# 1. 특정 프로세스의 네트워크 연결 실시간 확인
sudo lsof -i -n -P | grep -E "(ollama|curl|python)"

# 2. tcpdump로 특정 포트의 패킷 캡처
# Ollama 포트(11434)로 오가는 트래픽 확인
sudo tcpdump -i lo0 port 11434 -A -c 20

# 3. 외부로 나가는 DNS 쿼리 모니터링
# LLM 관련 프로세스가 예상치 못한 도메인에 접속하는지 확인
sudo tcpdump -i en0 port 53 -l | grep -E "(anthropic|openai|ollama)"

# 4. Little Snitch 또는 LuLu(무료) 설치
# GUI 기반으로 앱별 네트워크 접근을 제어
brew install --cask lulu

# 5. 특정 시간 동안의 네트워크 사용량 기록
# 추론 중 나가는 바이트 수 확인
nettop -p $(pgrep ollama) -J bytes_in,bytes_out -l 1 -t wifi

특히 LuLu(무료 방화벽)를 추천한다. 앱 단위로 아웃바운드 연결을 허용/차단할 수 있어서, Ollama가 인터넷에 접근하는 걸 원천 차단할 수 있다. 모델 다운로드할 때만 일시적으로 허용하고, 평소에는 차단해두면 완벽에 가까운 네트워크 격리가 된다.

보안 수준별 권장 설정 비교

마지막으로, 보안 요구 수준에 따른 권장 설정을 표로 정리했다. 본인의 상황에 맞는 레벨을 선택하면 된다.

항목 Level 1 (일반) Level 2 (민감) Level 3 (기밀)
LLM 클라우드 API (Claude/GPT) 하이브리드 (로컬+클라우드) 로컬 전용 (Ollama)
네트워크 일반 인터넷 VPN + 방화벽 규칙 에어갭 또는 LuLu 차단
모니터링 없음 nettop 주기적 확인 tcpdump 상시 로깅
데이터 전처리 민감값 수동 마스킹 git-secrets 자동 스캔 전송 자체가 불가
디스크 암호화 FileVault 권장 FileVault 필수 FileVault + 별도 암호화 볼륨
API 플랜 일반 API Team/Pro 플랜 사용 안 함
코드 품질 최상 (GPT-4o/Claude) 상~중 (혼합) 중 (13B 모델 기준)
적합 대상 개인 프로젝트, 오픈소스 일반 기업, SaaS 개발 금융, 의료, 국방

대부분의 개발자에게는 Level 2(하이브리드)가 가장 현실적이다. 민감한 코드는 로컬에서 처리하고, 나머지는 클라우드 API의 성능을 활용하는 것이다. 핵심은 “무엇이 민감한지”에 대한 기준을 미리 정해두는 것이다. 매번 판단하려면 피로해지고, 결국 귀찮아서 전부 클라우드로 보내게 된다.

내 경우에는 간단한 규칙을 세워뒀다. .env, config/, auth/, security/ 디렉토리의 파일은 무조건 로컬 LLM으로만 처리한다. 나머지는 클라우드를 쓴다. 이 규칙만으로도 실수로 시크릿이 외부로 나가는 일은 거의 막을 수 있었다. 완벽한 보안은 없지만, 합리적인 수준의 보안은 생각보다 간단한 습관에서 시작된다. 자세한 내용은 Ollama 공식 사이트를 참고하자.