본문으로 건너뛰기

© 2026 Molayo

Qiita헤드라인2026. 06. 15. 18:06

【실기 검증】 Amazon S3 Vectors를 순수 API로 파헤치기 ― RAG의 '벡터 저장소'는 정말 저렴한가, 메타데이터 필터는

요약

Amazon S3 Vectors를 사용하여 RAG용 벡터 저장소를 구축하는 실무 가이드를 제공합니다. 순수 API를 통해 버킷 생성, 임베딩 투입, 유사도 검색 및 메타데이터 필터링 과정을 검증하며 비용 효율성을 분석합니다.

핵심 포인트

  • S3 Vectors는 스토리지 기반 과금으로 저빈도 대량 벡터 보관에 매우 경제적임
  • 순수 API를 활용한 인덱스 생성 및 코사인 유사도 검색 실습
  • 최소 권한 설정 시 s3vectors:GetVectors 권한 누락 주의 필요
  • 실시간 고성능 QPS가 필요한 경우 OpenSearch 등 전용 DB가 적합함

면책 사항

본 기사는 필자 개인의 견해이며, 소속 조직의 공식 견해·개발 체제·업무 내용을 나타내는 것이 아닙니다. 기사 내의 기술적 표현은 집필 시점(2026년 6월)의 실기 검증에 기반한 것이며, 특정 제품·서비스의 성능·사양을 보증하지 않습니다. 계정 ID·리소스명은 마스킹(계정 ID는 123456789012로 처리)하였습니다.

안녕하세요! Dirbato의 사내 기술 횡단 지원 조직인 Backbeat에 소속된 시바타입니다!

OpenSearch나 pgvector를 구축할 정도는 아니지만, RAG용 벡터는 보유하고 싶다―― 그런 "상시 가동되는 벡터 DB를 운영하는 것은 비용 측면에서 부담스럽다"라는 문제에 대해, AWS가 **스토리지 과금형 (storage-based billing)**으로 답을 내놓은 것이 바로 Amazon S3 Vectors입니다.

본 기사에서는 매니지드 서비스나 프레임워크(LangChain 등)에 의존하지 않고, 순수 S3 Vectors API만을 사용하여 벡터 버킷 생성 → 임베딩 (embedding) 투입 → 유사도 검색 → 메타데이터 필터링까지 실기로 진행하며, **"결국 어떤 점이 유용한가", "최소 권한 설정 시 빠지기 쉬운 함정은 무엇인가"**를 실측 기반으로 정리합니다.

#검증 내용결과
1버킷/인덱스 생성 (1024차원・cosine・float32)✅ API 호출 몇 번으로 완료. 암호화는 기본적으로 SSE-S3가 활성화됨
...✅ MongoDB 스타일의 연산자가 대부분 올바르게 동작
4최소 권한의 함정🚨 QueryVectors에서 필터/메타데이터를 가져오려면 (없으면 403) s3vectors:GetVectors도 필수
5비용 구조✅ 상시 가동되는 컴퓨팅 자원을 갖지 않음 = 유휴(idle) 시 비용이 거의 스토리지 비용뿐

한 줄 요약: S3 Vectors는 "저빈도 액세스의 대량 벡터를 저렴하게 보관할 수 있는 RAG용 벡터 저장소"입니다. 실시간 고QPS(Queries Per Second) 용도는 계속해서 OpenSearch 등의 역할입니다.

S3 Vectors의 본론으로 들어가기 전에, "벡터 검색"의 토대를 3가지만 짚고 넘어가겠습니다. 이 부분을 이해하면 후반부의 "1024차원", "cosine 거리"를 한결 쉽게 읽을 수 있습니다.

문장이나 이미지를 의미를 나타내는 **수백~수천 개의 숫자 나열(=벡터 (vector))**로 변환하는 것을 **임베딩 (embedding)**이라 하며, 변환하는 AI를 **임베딩 모델 (embedding model)**이라고 부릅니다. 핵심은 **"의미가 가까운 것은 숫자 나열도 가까워진다"**는 점입니다.

"1024차원"이란, 하나의 벡터가 1024개의 숫자로 구성되어 있다는 의미입니다. 차원이 많을수록 의미를 세밀하게 표현할 수 있지만, 용량과 계산량도 늘어납니다. Titan V2는 256 / 512 / 1024 중에서 선택할 수 있으며, 본 기사에서는 1024를 사용합니다. 이 차원은 인덱스 생성 시 고정되며, 나중에 변경할 수 없습니다 (사용할 임베딩 모델과 차원을 처음에 결정해야 합니다).

검색이란 "쿼리(query)의 벡터와 가까운 벡터를 찾는 것"일 뿐입니다. 가까움을 측정하는 방법이 **거리 메트릭 (distance metric)**이며, 문장 의미 검색에서는 **cosine (벡터의 방향 = 각도의 근접성)**이 정석입니다 (S3 Vectors는 cosine / euclidean 중에서 선택 가능).

📏

중요: 거리는 작을수록 유사합니다. 후반부 결과 표에 나오는 lambda (0.684)dynamodb (0.387)는 cosine 거리로, 값이 작을수록 확신을 가지고 일치함을 나타냅니다.

더 쉽게 풀이된 전제 조건(RAG의 전체상·용어집 포함)이 필요한 분들을 위해, 별첨 입문 HTML(s3-vectors-primer.html)도 준비되어 있습니다.

S3에 네이티브하게 추가된 **벡터 스토리지 (vector storage)**로, 다음과 같은 3계층으로 구성됩니다.

포인트는 OpenSearch Serverless와 같은 "상시 가동되는 검색 컴퓨팅 (OCU)"를 갖지 않는다는 점입니다. 과금은 대체로 "저장하고 있는 벡터량 + 요청 수"로 이루어지며, 사용하지 않는 동안의 비용이 매우 저렴합니다.

전형적인 활용 사례는 RAG (Retrieval-Augmented Generation: 검색 증강 생성) 입니다. 생성형 AI (LLM)는 학습하지 않은 최신 정보나 사내 정보를 알지 못합니다. 그래서 **「먼저 관련 문서를 검색하고, 그 내용을 “근거”로 삼아 질문과 함께 LLM에 전달」**함으로써, 생성형 AI가 정확한 답변을 하도록 만듭니다. 이 검색을 담당하는 “벡터 보관소”가 바로 S3 Vectors 입니다 (Amazon Bedrock Knowledge Bases의 벡터 스토어로도 선택 가능).

「생성형 AI가 똑똑하게 답변하는」 이면에서, S3 Vectors는 ②의 검색 부분 (Retrieval)을 뒷받침하는 눈에 띄지 않지만 중요한 부품이라는 관계입니다.

항목
리전 (Region)ap-northeast-1 (도쿄)
임베딩 모델 (Embedding Model)amazon.titan-embed-text-v2:0 (1024차원 · normalize=true)
인덱스 (Index)dataType=float32 / dimension=1024 / distanceMetric=cosine
코퍼스 (Corpus)일본어 AWS 서비스 설명 12건 (메타데이터 category / year / service / text)
# 1) 벡터 버킷 생성
aws s3vectors create-vector-bucket \
--vector-bucket-name s3vectors-poc-123456789012 \
...

get-index로 확인해 보니, 암호화를 지정하지 않아도 SSE-S3 (AES256)가 기본 적용되어 있었습니다.

{
"dataType": "float32",
"dimension": 1024,
...

벡터 데이터는 float32로 전달하는 것이 관례입니다 (고정밀 형식을 전달하면 내부에서 float32로 변환됩니다). data / queryVector{"float32": [...]} 형태의 유니온 타입 (Union type)입니다.

import json, boto3
REGION = "ap-northeast-1"
BUCKET = "s3vectors-poc-123456789012"
...

일본어 구어체 쿼리에 대해, 모든 쿼리에서 top-1이 의도한 서비스로 나타났습니다 (cosine 거리는 작을수록 유사함).

쿼리top-1 (거리)
서버리스로 코드를 실행하고 싶다lambda (0.684)
생성형 AI의 파운데이션 모델을 API로 사용하고 싶다bedrock (0.561)
데이터를 암호화하는 키를 관리하고 싶다kms (0.665)
밀리초 단위로 응답하는 NoSQL 데이터베이스가 필요하다dynamodb (0.387)

레이턴시 (Latency)는 「동일 리전의 EC2/Lambda에서 직접 호출하는 것」이 공정한 측정 조건입니다 (수동으로 사용하는 배스천 호스트(Bastion Host)를 거치면 왕복 시간이 지배적이 되어 서비스 본래의 값을 측정할 수 없습니다). 본 기사에서는 기능 측면 (recall · 필터)을 주요 성과로 삼으며, 레이턴시 측정은 위 코드를 그대로 in-region에서 실행하는 방식을 권장합니다.

S3 Vectors의 filter는 MongoDB와 유사한 조건식입니다. 근접 탐색 (Nearest Neighbor Search)과 필터가 AND 결합되어, 조건에 부합하는 후보만 반환됩니다. 대표적인 연산자를 한 차례 테스트해 보았습니다.

# 예: category가 데이터베이스인 것만 근접 탐색
res = s3v.query_vectors(
vectorBucketName=BUCKET, indexName=INDEX,
...
필터반환된 key판정
{"category": {"$eq": "データベース"}}dynamodb, aurora 만
{"year": {"$gte": 2015}}aurora, ecs, sagemaker, bedrock
{"$and": [{"category": {"$in": ["ストレージ","ネットワーク"]}}, {"year": {"$lte": 2009}}]}s3, ebs, vpc, cloudfront
{"category": {"$ne": "セキュリティ"}}iam/kms 제외

비교($gte / $lte), 집합($in), 부정($ne), 논리 결합($and)까지 충실히 동작합니다. 「벡터 근접 탐색 × 구조화된 속성 필터링」이 1회의 요청(Request)으로 완결된다는 점은 구현 측면에서 매우 편리합니다.

이 부분이 은근히 중요한 함정입니다. QueryVectors에 필요한 권한은 요청 내용에 따라 달라집니다.

수행하려는 작업필요한 IAM 액션
근접한 키와 거리만 취득 (returnMetadata 미지정)s3vectors:QueryVectors만 필요
메타데이터 필터를 사용 / returnMetadata=trues3vectors:QueryVectorss3vectors:GetVectors

즉, "검색은 되는데 필터를 추가하자마자 403 에러가 발생하는" 사고가 일어납니다. 실제로 필터 및 메타데이터 반환을 다용했던 이번 검증에서는, 두 권한을 모두 부여하고 나서야 성공했습니다.

최소 권한 정책(Least Privilege Policy)은 인덱스 단위로 작성할 수 있습니다 (ARN은 bucket/<이름>/index/<이름> 계층). 애플리케이션 용도에 따라 읽기 전용 인덱스와 쓰기 가능 인덱스를 분리할 수 있습니다.

{
"Version": "2012-10-17",
"Statement": [{
...
항목상한
벡터 / 인덱스최대 20억
...

"필터에 사용하는 메타데이터는 2KB까지", "비필터 키는 생성 시 선언(최대 10개)" 정도의 제약은 설계 시 고려해야 하므로, 장문의 원문은 비필터 키(Non-filter key)로 돌리는 것이 정석입니다.

관점S3 VectorsOpenSearch Serverless (Vector)Aurora PostgreSQL + pgvector
과금 모델스토리지 + 요청 (상시 가동 컴퓨팅 없음)OCU (컴퓨팅) 상시 과금 · 최소 용량 하한선 있음DB 인스턴스 상시 과금
유휴(Idle) 시 비용거의 저장량만큼만 발생 = 낮음높음 (최소 OCU가 계속 돌아감)중간 ~ 높음
특화 영역대량 · 저빈도 액세스 벡터를 저렴하게 보관, Bedrock KB 연동실시간 · 고QPS · 전문 검색(Full-text Search) 병용기존 RDB와 결합 · 트랜잭션
스케일20억 벡터/인덱스대규모 · 고처리량(High Throughput)인스턴스 성능에 의존

AWS는 "벡터 업로드 · 스토리지 · 쿼리에 드는 비용을 전용 벡터 DB를 사용할 때와 비교하여 최대 90% 절감할 수 있다"고 설명합니다 (단, 이는 벡터 계층의 비용에 국한된 수치이며, 시스템 총 비용에 대한 이야기가 아니라는 점에 주의하십시오. 출처는 말미에 기재). 요컨대 「속도를 위한 마지막 한 끗」보다는 「보관 비용」을 챙기는 선택지라는 위치를 점하고 있습니다.

각 서비스의 실제 금액은 요금 개정에 따라 달라지므로, 채택 판단 시에는 최신 pricing 페이지에서 산출해 보시기 바랍니다. 본 기사는 어디까지나 "과금 모델의 구조적인 차이"를 정리한 것입니다.

  • S3 Vectors는 순수 API만으로 RAG의 벡터 계층을 완결할 수 있습니다 (버킷 → 인덱스 → put → query).
  • 일본어 코퍼스에서의 재현율(Recall)은 실용적으로 충분합니다 (Titan v2 · 1024차원 · cosine 유사도로 top-1 정답).
  • 메타데이터 필터는 연산자를 한 세트 모두 사용할 수 있으므로, 속성으로 필터링된 근접 탐색을 단 한 번의 호출(Call)로 작성할 수 있습니다.
  • 최소 권한의 함정: 필터/메타데이터 취득에는 GetVectors가 필요합니다.

필요합니다. -
기쁨의 본질은 비용 구조: 상시 가동되는 컴퓨팅 (Compute) 자원을 보유하지 않으므로, 저빈도 액세스 (Low-frequency access) 벡터를 저렴하게 보관할 수 있습니다. 실시간 고QPS (Queries Per Second) 환경은 계속해서 OpenSearch 등을 사용해야 합니다.

"일단 RAG의 벡터를 두는 장소"로서, 우선 S3 Vectors부터 시작하고 레이턴시(Latency)/QPS 요구사항이 엄격해지면 다른 대안을 검토한다――는 식의 접근이 쉬워졌다고 느꼈습니다.

AI 자동 생성 콘텐츠

본 콘텐츠는 Qiita AI의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.

원문 바로가기
0

댓글

0