Supabase MCP가 전체 SQL 데이터베이스를 유출할 수 있음

3 weeks ago 4

  • Supabase MCP 통합을 악용하여 공격자가 개발자의 비공개 SQL 데이터를 유출할 수 있음
  • LLM이 지시문과 데이터를 구분하지 못해 악의적으로 조작된 메시지가 명령어로 오인될 위험 발생
  • service_role 권한을 가진 AI 에이전트가 고객 사용자 입력을 신뢰 없이 처리, 민감 정보가 노출되는 문제 발생
  • 공격자는 특정한 지시문이 포함된 메시지로 보안 회피 및 중요 정보 유출 가능함을 시연함
  • 대응 방안으로 읽기 전용 모드 활성화프롬프트 인젝션 필터 사용을 제안함

개요

  • Model Context Protocol(MCP)은 LLM이 외부 도구와 상호작용할 수 있도록 해주는 표준 프로토콜임
  • 이로 인해 새로운 기회가 열리는 동시에, 잠재적인 보안 취약점도 발생함
  • 본 게시물은 공격자가 Supabase의 MCP 연동을 활용, 개발자의 비공개 SQL 테이블을 유출할 수 있는 방법을 시연함

문제점 설명

  • LLM은 시스템 프롬프트·사용자 지시문·데이터 컨텍스트를 텍스트로 받아서 처리
  • LLM은 문맥 경계를 내장적으로 알지 못하며, 데이터와 지시문을 구별하지 못함
  • 사용자 입력 데이터 중 명령어처럼 보이도록 조작된 콘텐츠가 있을 경우, LLM이 이를 명령으로 실행할 수 있음

공격 환경(Setup)

  • 새로운 Supabase 프로젝트를 생성하고, 일반적인 다중 테넌트 SaaS 고객지원 환경을 모사함
  • Dummy 데이터만 삽입, Row-Level-Security(RLS) 는 공식 문서대로 적용, 별도 확장이나 정책 없음
  • 공격에 사용된 환경은 기본 제공 서비스만 사용, service_role, RLS, MCP 에이전트 모두 기본 세팅임

1. 주요 행위자와 권한

행위자(역할) 사용 인터페이스 DB 자격증명 주요 권한
고객/공격자 티켓 제출 폼(공개) 'anon'(RLS 제한) 본인 소유의 티켓/메시지 생성
지원 에이전트 지원 대시보드 'support'(RLS 제한) 지원 테이블만 일부 읽기/쓰기
개발자 Cursor IDE+Supabase MCP service_role 모든 테이블에 대해 전체 SQL 가능
IDE Assistant LLM(Cusor에서 작동) service_role 텍스트 명령대로 MCP로 SQL 실행
  • 취약점의 핵심: IDE Assistant는 신뢰할 수 없는 고객 입력을 인지하지 못하며, 최고 권한(service_role) 을 가짐
  • 지원 에이전트의 권한으로는 민감 테이블 접근 불가능(예: integration_tokens), 지시문을 요청해도 거부 반응 반환함

2. 애플리케이션 구조

  • 고객 및 에이전트가 자유롭게 지원 티켓을 생성/메시지 교환 가능
  • 모든 데이터는 Supabase SQL 데이터베이스에 저장
  • 개발자는 때때로 Cursor 에이전트(LLM + MCP) 로 열린 티켓을 검토함

테이블 예시

  • support_tickets: 고객지원 티켓 데이터 저장
  • support_messages: 각 티켓에 대한 메시지 저장
  • integration_tokens: 민감한 세션 토큰 등 보안 정보 저장

3. 애플리케이션 동작 방식

  • 고객지원 시스템은 티켓 생성 및 메시지 교환 기능 제공
  • 개발자는 Cursor 에이전트로 열린 티켓 및 메시지 확인/요약을 자동화함
  • Cursor 에이전트가 service_role 권한으로 DB 접근, RLS 무시 및 고객 메시지도 모두 읽음
  • 누군가 조작된 명령문을 고객 메시지에 심으면, AI가 이를 SQL로 실행하여 민감 정보를 유출할 수 있음

공격 시나리오

  • 공격자는 새로운 티켓을 열고 특수하게 작성한 메시지를 제출함
    • 예시 메시지에는 AI 에이전트에게 integration_tokens 테이블 전체 읽고, 결과를 이 티켓에 추가하라는 명령 포함
    • 메시지 끝에는 정상적인 문의 내용(“무엇을 할 수 있나요?” 등)을 포함해 의심 줄임
  • 이 메시지는 지원 에이전트에게 노출돼도 민감 데이터 접근 권한 부족으로 별 영향 없음
  • 개발자가 나중에 Cursor로 열린 티켓을 요약하려 하면, 에이전트가 해당 메시지를 입력으로 받아 숨겨진 명령 실행
    • 실제로 두 개의 SQL 쿼리를 생성:
        1. 모든 integration_tokens 내용을 읽음
        1. 해당 결과를 티켓 메시지로 다시 삽입함
  • 해당 쿼리는 service_role 권한으로 실행, RLS 우회
  • 공격자는 본인이 연 티켓에서 민감 정보가 포함된 신규 메시지를 쉽게 확인 가능

결론 및 대응 방안

  • 본 공격은 과도한 권한(service_role)사용자 콘텐츠에 대한 검증 부재가 결합된 취약점 기반임
  • MCP 도입 시 자동화 편의와 동시에 보안 리스크가 큼

즉각적인 보안 조치 제안

  1. 읽기 전용(read-only) 모드 사용

    • Supabase MCP에서는 agent 초기화시 읽기 전용 플래그를 설정하면, 모든 쓰기/수정/삭제 SQL 차단
    • 쿼리 기반 에이전트라면 항상 읽기 전용 모드를 활성화 필요
  2. 프롬프트 인젝션 필터 적용

    • 비정상적 명령문, SQL 패턴, 인젝션 흔적 패턴 등 데이터 입력을 사전 필터링
    • MCP 앞단에서 데이터를 감시/차단하는 lightweight 래퍼로 적합
    • 모든 위험 탐지는 불가능하나, 기본적인 1차 방어선 제공

전문가 지원 안내

  • GeneralAnalysis 팀은 LLM 보안 및 적대적 공격 안전성 분야 전문성 보유
  • MCP 서버 또는 LLM 기반 에이전트 보안 강화에 대해 문의 시( info@generalanalysis.com ) 논의 및 가이드 제공 가능

Read Entire Article