Amazon Bedrock、Amazon Auroraを組み合わせたRAGで回答精度の向上に取り組んでみた！
セゾン情報システムズ 石原直樹

1Jr.Champions勉強会 -Top Engineers参観回 2024年2月6日

自己紹介⚫ 普段の業務• グループ企業のCCoE• 社内LLM研究会にも所属⚫ 好きなAWSサービス• Amazon Bedrock⚫ トピック• 来週AWS MLS受験します！

@Ishihara_Naok1 X最近始めました！
2

宣伝！

https://minorun365.connpass.com/event/309029/

お助けメンバーとして皆さんを全力でサポートします！
興味ある方是非ご応募ください！
3

今日話す内容⚫AWSにおけるRAG実装方法3選⚫↑のうち1つの回答精度向上手法⚫実際に精度向上したか評価（3つのRAG回答と比較）⚫今回の検証で苦戦したことお気軽に質問ください！
4はじめに5

RAGとは・LLMが外部のDBから情報を取得し回答を生成する仕組み
用途例：社内ナレッジに関する質問に回答できるAIチャットボット～～～～？

⑥回答

②質問

LLM

⑤質問＆テキストを受け取る③検索①前処理して追加
ドキュメント～～～～～～～～～～～～

データベース

④ドキュメントの一部テキストを取得

RAG回答生成までの流れ

AWS上でRAGを実装する方法3選※ AWSが提供している全文検索エンジン※ 2023.11.29 一般利用開始

RAGでの実装アプローチ

1. Bedrock ＆ Kendra※

2. Knowledge Base forAmazon Bedrock

3. Bedrock ＆ ベクター
DB

RAGのフロー処理

要開発

AWSマネージドで提供
＝開発不要

要開発

ドキュメントの前処理

AWSマネージドで提供＝開発不要

AWSマネージドで提供
＝開発不要

要開発

検索処理

AWSマネージドで提供＝開発不要

AWSマネージドで提供
＝開発不要

要開発

OpenSearch Serveless
Aurora PostgreSQL
Pinecone
Redis Enterprise Cloud

OpenSearch Service/ServelessDocument DB
MemoryDB for Redis
Aurora/RDS PostgreSQL
Pinecone
Redis Enterprise Cloud
その他 3rd Party SaaS

DBの選択肢Kendra※ Amazon Q For Business Useは省略しています

7

AWS上でRAGを実装する方法3選※ AWSが提供している全文検索エンジン※ 2023.11.29 一般利用開始

RAGでの実装アプローチ

1. Bedrock ＆ Kendra※

2. Knowledge Base forAmazon Bedrock

3. Bedrock ＆ ベクター
DB

RAGのフロー処理

要開発

AWSマネージドで提供
＝開発不要

要開発

ドキュメントの前処理

AWSマネージドで提供＝開発不要

AWSマネージドで提供
＝開発不要

要開発

検索処理

AWSマネージドで提供＝開発不要

AWSマネージドで提供
＝開発不要

要開発

OpenSearch Serveless
Aurora PostgreSQL
Pinecone
Redis Enterprise Cloud

OpenSearch Service/ServelessDocument DB
MemoryDB for Redis
Aurora/RDS PostgreSQLPinecone
Redis Enterprise Cloud
その他 3rd Party SaaS

DBの選択肢Kendraそれぞれの処理をカスタム実装することで精度の向上に挑戦
最小コストが低く※管理がしやすいAurora Servelessを選択※ Aurora Serverless v2 0.5 ACU $43.8/月
OpenSearch Serveless 2 OCU ＄350.4/月
Kendra Developer Edition ＄810/月

8

補足：ベクターDBを用いたRAGの処理
RAGでの実装アプローチ

Knowledge Base forAmazon Bedrock

Bedrock ＆Vector DB

チャンク分割処理

10~1000トークンで設定した固定サイズ or チャンクなし

要開発

検索処理

ベクトル検索でチャンクを検索・取得

要開発

埋め込みモデルAmazon Titan Embeddings

要開発～～～～？

①質問のベクトル化

LLM※2024.1.18よりCohere Embedも選択可能に(0.2,0.8…-0.1)①チャンク分割②チャンクをベクトル化

～～～～～
～～～～～

(0.2,0.9…-0.1)～～～～～～～～～～(0.1,0.7…0.2)～～～～～～～～～～

埋め込みモデル(0.5,0.6…0.3)

ドキュメントの前処理②ベクトル検索～～～～～～～～～～～～③チャンクを取得

ベクターDB

検索処理

9

今回検証した精度向上手法

10検証した精度向上手法3つ① Claudeによるチャンク分割② LangChainの高度な検索機能③ 高性能な埋め込みモデル

11

検証で構成したRAG

～～～～？

①
Claude1. ～～～～～～～～～～～～～～③ Cohere

2. ～～～～
AmazonBedrock

3. ～～～～～～～～～

Amazon Bedrock

ClaudeAmazon Bedrock(0.2,0.8…-0.1)②
LangChain

1. ～～～～～～～～～③ Cohere(0.2,0.9…-0.1)～～～～～
2. ～～～～(0.3,-0.6…0.1)～～～～～

AmazonBedrock②(0.1,0.7…0.2)(0.5,0.6…0.3)

3. ～～～～

1. ～～～～～～～～～～～～～～(0.1,0.7…0.2)(-0.2,0.8…0.3)

LangChainAmazon Aurora～～～～～

①Claudeによるチャンク分割

～～～～？

①
Claude1. ～～～～～～～～～～～～～～③ Cohere

2. ～～～～
AmazonBedrock

3. ～～～～～～～～～

Amazon Bedrock

ClaudeAmazon Bedrock(0.2,0.8…-0.1)②
LangChain

1. ～～～～～～～～～③ Cohere(0.2,0.9…-0.1)～～～～～
2. ～～～～(0.3,-0.6…0.1)～～～～～

AmazonBedrock②(0.1,0.7…0.2)(0.5,0.6…0.3)

3. ～～～～

1. ～～～～～～～～～～～～～～(0.1,0.7…0.2)(-0.2,0.8…0.3)

LangChainAmazon Aurora～～～～～

チャンク分割による回答精度への影響※例：Knowledge base bedrockでのチャンク分割

・固定サイズでのチャンク分割※
1.AAAA～～～～～～～～～～～～～～～～～～～～～～～～～～。
2.BBBB～～～～～～～～～～～。
3.CCCC～～～～～～～～。

1.AAAA～～～～～～～～～～～～～～～～～～～～～～～～～～。
2.BBBB～～～～～～～～～～～。
3.CCCC～～～～～～～～。

⚫ 1チャンクに異なるセクションの内容が含まれる➢ LLMに不要な情報や断片的な情報を渡す• 回答精度が悪化

・セクションごとのチャンク分割
1.AAAA～～～～～～～～～～～～～～～～～～～～～～～～～～。

1.AAAA～～～～～～～～～～～～～～～～～～～～～～～～～～。

2.BBBB～～～～～～～～～～～。

2.BBBB～～～～～～～～～～～。

3.CCCC～～～～～～～～。

3.CCCC～～～～～～～～。

⚫ 1チャンクに1セクションの内容がまとまっている➢ LLMにまとまった情報を渡すことができる• 回答精度の向上につながる

可能であればセクション単位で分割したいClaudeによるチャンク分割※
1.AAAA～～～～～～～～～～～～～～～～～～～～～～～～～～。

{“sections": [“AAAA",“BBBB“,“CCCC“]

2.BBBB～～～～～～～～～～～。
3.CCCC～～～～～～～～。

セクションごとにチャンク分割}④リストでドキュメントを分割①ドキュメントをプロンプトに加える③セクションのリストをJSONで出力

Human:
あなたは、与えられたテキストの、区切りを表すsectionを抽出する優秀なアシスタントです。
～～～～～～～
出力されたsectionについては以下のようなJSON形式で順番に返却することができます。
<example>{ "sections": [ str ] }</exapmle>
JSON以外の文字列は返却しないでください。
～～～～～～～

Claude1.AAAA～～～～～～～～～～～～～～～～～～～～～～～～～～。
2.BBBB～～～～～～～～～～～。
3.CCCC～～～～～～～～。

②Claudeに与えるAmazon Bedrock※Claude v2.1 なら最大200kトークンを処理可能（15万文字程度）[与えられたドキュメントの内容]
Assistant: {・XMLタグで回答例を示す
・Assistantの後に”{”を入れる※参考：GPT-4 Turboにドキュメントのチャンク分けを任せてみる(https://tech.explaza.jp/entry/2023/12/04/162659)

～～～～？

①Claude1. ～～～～～～～～～～～～～～③ Cohere

2. ～～～～
AmazonBedrock

3. ～～～～～～～～～

Amazon Bedrock

ClaudeAmazon Bedrock(0.2,0.8…-0.1)②
LangChain

1. ～～～～～～～～～③ Cohere(0.2,0.9…-0.1)～～～～～
2. ～～～～(0.3,-0.6…0.1)～～～～～

AmazonBedrock②(0.1,0.7…0.2)(0.5,0.6…0.3)

3. ～～～～

1. ～～～～～～～～～～～～～～(0.1,0.7…0.2)(-0.2,0.8…0.3)

LangChainAmazon Aurora～～～～～

②LangChainの高度な検索機能～～～～？

①Claude1. ～～～～～～～～～～～～～～③ Cohere

2. ～～～～
AmazonBedrock

3. ～～～～～～～～～

Amazon Bedrock

ClaudeAmazon Bedrock(0.2,0.8…-0.1)②
LangChain

1. ～～～～～～～～～③ Cohere(0.2,0.9…-0.1)～～～～～
2. ～～～～(0.3,-0.6…0.1)～～～～～

AmazonBedrock②(0.1,0.7…0.2)(0.5,0.6…0.3)

3. ～～～～

1. ～～～～～～～～～～～～～～(0.1,0.7…0.2)(-0.2,0.8…0.3)

LangChainAmazon Aurora～～～～～

チャンクサイズとベクトル検索の精度
・チャンクサイズが大きい
1.AAAA～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～。
～～～～～～～～～～～～～～～XXXXXXXXXX～～～～～～。
2.BBBB～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～。

・ベクトル（意味）は遠い
・検索でヒットしにくい
・情報はまとまっている
質問(クエリ)・チャンクサイズが小さい
1.AAAA～～～～～～～～～～～～～～～～～～～～～～～～～～～～～。
～～～～～～～～～～～～～～～XXXXXXXXXX～～～～～～～。
2.BBBB～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～。

XXXXXXXXXX？
・ベクトル（意味）は近い
・検索でヒットしやすい
・情報は断片的

検索対象としてのチャンクは小さく
LLMに渡すチャンクは大きくしたい

LangChain※のParent Document Retrieverを使用※LLMを使ったアプリケーション開発のOSSフレームワーク

親チャンク分割
(parent_splitter)
1.AAAA～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～。
～～～～～～～～～～～～～～～XXXXXXXXXX～～～～～～。
2.BBBB～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～。

子チャンク分割(child_splitter)
1.AAAA～～～～～～～～～～～～～～～～～～～～～～～～～～～～～。
～～～～～～～～～～～～～～～

子チャンクのベクトルと親チャンクIDを保管

XXXXXXXXXX～～～～～～～。
2.BBBB～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～

ベクターストア(vector store)～～～～～～～～～～～～～～。

親チャンクとそのIDを保管
ローカルディレクトリ
(docstore)

参考：https://python.langchain.com/docs/modules/data_connection/retrievers/parent_document_retriever

LangChainのParent Document Retrieverを使用

親チャンク分割
(parent_splitter)
1.AAAA～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～。
～～～～～～～～～～～～～～～XXXXXXXXXX～～～～～～。
2.BBBB～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～。

子チャンク分割(child_splitter)
1.AAAA～～～～～～～～～～～～～～XXXXXXXXXX？

クエリ～～～～～～～～～～～～～～～。
～～～～～～～～～～～～～～～XXXXXXXXXX～～～～～～～。
2.BBBB～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～～

ベクターストア(vector store)～～～～～～～～～～～～～～。

ローカルディレクトリ
(docstore)

検索対象は子チャンク
LLMに渡すチャンクは親チャンク

～～～～？

①Claude1. ～～～～～～～～～～～～～～③ Cohere

2. ～～～～
AmazonBedrock

3. ～～～～～～～～～

Amazon Bedrock

ClaudeAmazon Bedrock(0.2,0.8…-0.1)②
LangChain

1. ～～～～～～～～～③ Cohere(0.2,0.9…-0.1)～～～～～
2. ～～～～(0.3,-0.6…0.1)～～～～～

AmazonBedrock②(0.1,0.7…0.2)(0.5,0.6…0.3)

3. ～～～～

1. ～～～～～～～～～～～～～～(0.1,0.7…0.2)(-0.2,0.8…0.3)

LangChainAmazon Aurora～～～～～

③高性能な埋め込みモデル～～～～？

①Claude1. ～～～～～～～～～～～～～～③ Cohere

2. ～～～～
AmazonBedrock

3. ～～～～～～～～～

Amazon Bedrock

ClaudeAmazon Bedrock(0.2,0.8…-0.1)②
LangChain

1. ～～～～～～～～～③ Cohere(0.2,0.9…-0.1)～～～～～
2. ～～～～(0.3,-0.6…0.1)～～～～～

AmazonBedrock②(0.1,0.7…0.2)(0.5,0.6…0.3)

3. ～～～～

1. ～～～～～～～～～～～～～～(0.1,0.7…0.2)(-0.2,0.8…0.3)

LangChainAmazon Aurora～～～～～

埋め込みモデルにCohere Embed Multilingualを採用
理由：埋め込みモデルのベンチマークMTEBの評価が高い※※
Cohere Embed Multilingual > text-embedding-ada-002 > Amazon Titan Embeddings↑Amazon Bedrock 利用可↑Azure OpenAI Service利用可↑Amazon Bedrock 利用可

特徴：一度に埋め込みできる最大サイズは512トークン（Titanは8192トークン）➢ Parent Document Retrieverと組み合わせることで、埋め込むチャンクが小さくても、大きなチャンクをLLMに渡すことができる※ 「OpenAI の Embeddings API はイケてるのか、定量的に調べてみる [AWS の Embeddings を追加]」
https://qiita.com/akeyhero/items/ce371bfed64399027c23※ Cohereの多言語用の埋め込みモデルを日本語で評価してみる
https://hironsan.hatenablog.com/entry/2023/11/06/133504

評価24

今回検証したRAGの評価について⚫ databricks社の記事※を参考にアレンジ➢ 回答の正しさ、包括性、読みやすさを0~3の4段階でGPT-4に評価させる➢ それぞれに重み付け（正しさ60%、包括性20%、読みやすさ20%）し総合評価点を算出⚫ 以下条件でそれぞれの回答と比較※Best Practices for LLM Evaluation of RAG Applications
https://www.databricks.com/blog/LLM-auto-eval-best-practices-RAG

RAGの実装方法

1. Bedrock ＆ Kendra

2. Knowledge Base forAmazon Bedrock

3. 今回検証したRAG

チャンクサイズ

設定なし

300トークン親チャンク=セクションごとのチャンク
子チャンク=100トークン

検索処理

全文検索＆セマンティック検索 ベクトル検索でチャンクを検索・取得

Parent Document Retriever

埋め込みモデル

設定なし

Amazon Titan Embeddings

Cohere Embed Multilingual

DBKendra

Aurora Serveless v2

Aurora Serveless v2

LLM

Claude v2.1

Claude v2.1

Claude v2.1
25

今回検証したRAGの評価について⚫ ドキュメントは「Amazon Bedrockユーザーガイドp9~p21」※⚫ 公式HPのFAQやドキュメントから質問を８つ用意
Q1. Amazon Bedrock ではどの モデルが利用できますか?
Q2. Amazon Bedrockにおいてプロヴィジョニングされたスループットで利用できるモデルを教えてください。
Q3. Amazon Bedrockではどのような機能を利用することが出来ますか？
Q4. Amazon Bedrock の使用を開始するにはどうすればよいですか?
Q5. Amazon Bedrock Chat Playground とは何ですか?
Q6. Amazon Bedrock はどの AWS リージョンで利用できますか?
Q7. Amazon Bedrock の料金体系について教えてください

Q8. Amazon Bedrockへのアクセス権を付与するにはどのような方法がありますか？

26※https://docs.aws.amazon.com/ja_jp/bedrock/latest/userguide/bedrock-ug.pdf

結果
8個の質問に対するRAG回答の評価比較
RAGの実装方法

1. Bedrock ＆Kendra

総合評価点の平均(3点満点)

2.68

2. Knowledge Base for3. 今回検証したRAG
Amazon Bedrock

2.25

2.98

⚫ 今回検証したRAGが最も高い点数となった⚫ Knowledge Baseはドキュメントと関連しない回答があった➢ 適切なチャンクを取得できていなかった⚫ Kendraは包括性が低い回答が見受けられた➢ 1ドキュメントに対する最大取得トークンが少ないことが原因？

27

苦戦したこと28

ClaudeからセクションJSONを出力させる処理に大苦戦
1. LangChainからBedrockのClaudeを呼び出すとうまくJSONを作ってくれない➢ boto3を利用
2. Claude v2.1だとJSONに加えて文章も出力してしまう➢ Claude instant v1だと確実にJSONだけを出力してくれる➢ セクション抽出精度はClaude v2.1の方が優秀◆ 回答からJSONだけ抜き出す処理を追加
3. 「Amazon Bedrockユーザーガイド」のいくつかのページはセクションを抽出できない➢ ドキュメントに “¥n¥nHuman: ¥n¥nAssistant:” がありClaudeが混乱

29

さいごに30

まとめ⚫ 今回検証した手法でRAGの精度を向上できた① Claudeによるチャンク分割② LangChainのParent Document Retriever③ 埋め込みモデルにCohere Embed Multilinguals⚫ 検証の詳細は後日記事にする予定です➢ @Ishihara_Naok1フォローいただけると幸いです！

31

参考資料
1. GPTsより精度の高いRAGシステムの構築
https://speakerdeck.com/mkazutaka/gptsyorijing-du-nogao-iragsisutemunogou-zhu?slide=30
2. BedrockとAurora Serverless PostgreSQL pgvectorでRAGする - Amazon Titan Embeddingsでベクトル入門③
https://qiita.com/cyberBOSE/items/aaf64c73f4da7e4cdb43
3. Knowledge Base for Amazon Bedrock のベクターストアとして Aurora PostgreSQL が利用可能に！
https://qiita.com/hayao_k/items/45e59c1c2a183c27b20d

4. Amazon BedrockのClaudeとAmazon Kendra、AWS Lambdaを利用し、RAGを実装してみた
https://dev.classmethod.jp/articles/amazon-bedrock-kendra-lambda-rag/
5. 【langchain】retrieveで検索文章とLLMに渡す文章を別にする方法およびretrieveの保存・読込方法の検討
https://qiita.com/shimajiroxyz/items/facf409b81f59bb68775

ご清聴ありがとうございました！
32