共用方式為


使用 Azure DocumentDB 的擷取擴增生成 (RAG)

在快速發展的生成式人工智慧領域,GPT 等大型語言模型 (LLM) 改變了自然語言處理。 不過,AI 中的新興趨勢是使用向量存放區,這在增強 AI 應用程式方面發揮著關鍵作用。

本教學將探討如何利用 Azure DocumentDB、LangChain 與 OpenAI 實作檢索增強生成(RAG),以提升 AI 效能,並討論大型語言模型(LLM)及其限制。 我們探索快速採用的 RAG 範例,並簡要討論 LangChain 架構和 Azure OpenAI 模型。 最後,我們會將這些概念整合到真實世界的應用程式。 最後,讀者將對這些概念有紮實的理解。

了解 LLM 及其限制

LLM 是在大量文本數據集上訓練的高級深度神經網絡模型,使它們能夠理解和生成類似人類的文本。 雖然在自然語言處理方面具有革命性,但 LLM 有固有的限制:

  • 幻覺:LLM 有時會產生事實不正確或非前景的資訊,稱為「幻覺」。
  • 過時資料:LLM 在靜態資料集上進行訓練,這些資料集可能不包含最新資訊,從而限制了其當前的相關性。
  • 無法存取使用者的本地資料:LLM 無法直接存取個人或本地化數據,這限制了他們提供個人化回應的能力。
  • 令牌限制:LLM 每次互動都有最大令牌限制,限制了他們一次可以處理的文字量。 例如,OpenAI 的 gpt-3.5-turbo 的代幣限制為 4,096。

使用檢索增強式生成

RAG 是一種旨在克服 LLM 限制的架構。 RAG 會使用向量搜尋,根據輸入查詢擷取相關文件,提供這些文件做為 LLM 的內容,以產生更精確的回應。 RAG 不只依賴預先定型的模式,而是藉由納入最新的相關資訊來增強回應。 此方法有助於:

  • 盡量減少幻覺:將反應建立在事實資訊的基礎上。
  • 確保最新資訊:檢索最新數據以確保回應為最新。
  • 利用外部數據庫: 雖然它不授予對個人數據的直接訪問,但 RAG 允許與外部、用戶特定的知識庫集成。
  • 優化令牌使用:通過專注於最相關的文檔,RAG 使令牌使用更加高效。

本教學示範如何利用 Azure DocumentDB 實作 RAG,打造針對你資料量身打造的問題回答應用程式。

應用程式架構概觀

下列架構圖說明 RAG 實作的關鍵元件:

顯示擷取增強生成實作架構的圖表。

重要元件和架構

我們現在將討論本教學課程中使用的各種架構、模型和元件,強調其角色和細微差別。

Azure DocumentDB

Azure DocumentDB 支援語意相似性搜尋,這對 AI 驅動的應用程式至關重要。 允許以各種格式的資料表示為向量內嵌,可以與源資料和中繼資料一起儲存。 使用近似最近鄰演算法,例如分層可導航小世界 (HNSW),可以查詢這些嵌入以進行快速語意相似性搜尋。

LangChain 架構

LangChain 為常見工作提供鏈結、多個工具整合和端對端鏈結的標準介面,藉此簡化 LLM 應用程式的建立。 它使 AI 開發人員能夠建立使用外部資料來源的 LLM 應用程式。

LangChain 的主要層面:

  • 鏈結:解決特定工作的元件序列。
  • 元件:LLM 包裝函式、向量存放區包裝函式、提示範本、資料載入器、文字分隔器和擷取器等模組。
  • 模組化:簡化開發、偵錯和維護。
  • 熱門:開放原始碼專案可快速獲得採用並不斷演進,以符合使用者需求。

Azure 應用程式服務介面

應用程式服務提供強大的平台,可建置適用於 Gen-AI 應用程式的易用 Web 介面。 本教學課程會使用 Azure 應用程式服務來建立應用程式的互動式 Web 介面。

OpenAI 模型

OpenAI 是 AI 研究的龍頭,提供各種用於語言產生、文字向量化、影像建立和音訊到文字轉換的模型。 在本教學課程中,我們將使用 OpenAI 的內嵌和語言模型,這對於了解和產生以語言為基礎的應用程式至關重要。

內嵌模型與語言生成模型

類別 文字內嵌模型 語言模型
Purpose 將文字轉換為向量內嵌。 理解並生成自然語言。
Function 將文字資料轉換成數位的高維度陣列,擷取文字的語意意義。 根據指定的輸入,理解並產生類似人類文字的文字。
Output 數字陣列 (向量內嵌)。 文字、答案、翻譯、程式碼等。
範例輸出 每個內嵌都以數值形式代表文字的語意意義,而模型所決定的維度。 例如, text-embedding-ada-002 產生具有 1,536 個維度的向量。 根據提供的輸入產生的內容相關且連貫的文字。 例如,gpt-3.5-turbo 可以產生問題響應、翻譯文字、撰寫程式碼等等。
典型使用案例 - 語意搜尋 - 聊天機器人
- 建議系統 - 自動化內容建立
- 文字資料的群集和分類 - 語言翻譯
- 資訊擷取 - 摘要
資料表示法 數值表示法 (內嵌) 自然語言文字
維度性 陣列的長度對應於內嵌空間中的維度數,例如 1,536 個維度。 通常以權杖序列表示,內容會決定長度。

應用程式的主要元件

  • Azure DocumentDB:存儲和查詢向量嵌入。
  • LangChain:建構應用程式的 LLM 工作流程。 使用的工具例如:
    • 文件載入器:用於從目錄載入和處理文件。
    • 向量儲存整合:用於在 Azure DocumentDB 中儲存及查詢向量嵌入。
    • AzureDocumentDBVectorSearch:Azure DocumentDB 向量搜尋的包裝器
  • Azure 應用程式服務:建置 Cosmic Food 應用程式的使用者介面。
  • Azure OpenAI:提供 LLM 和內嵌模型,包括:
    • text-embedding-ada-002:一種文本嵌入模型,可將文本轉換為具有 1,536 個維度的向量嵌入。
    • gpt-3.5-turbo:用於理解和產生自然語言的語言模型。

進行環境設定

要開始使用 Azure DocumentDB 優化 RAG,請遵循以下步驟:

  • 在 Microsoft Azure 上建立下列資源:
    • Azure DocumentDB 叢集:欲了解更多資訊,請參閱 建立叢集
    • Azure OpenAI 資源:
      • 內嵌模型部署 (例如 text-embedding-ada-002)。
      • 聊天模型部署 (例如 gpt-35-turbo)。

範例文件

在本教學課程中,您會使用 文件載入器載入單一文字檔。 該檔案應保存在 src 資料夾中名為 data 的目錄中。 檔案內容如下:

food_items.json

    {
        "category": "Cold Dishes",
        "name": "Hamachi Fig",
        "description": "Hamachi sashimi lightly tossed in a fig sauce with rum raisins, and serrano peppers then topped with fried lotus root.",
        "price": "16.0 USD"
    },

載入文件

  1. 設定 Azure DocumentDB 連線字串、資料庫名稱、集合名稱和索引:

    mongo_client = MongoClient(mongo_connection_string)
    database_name = "Contoso"
    db = mongo_client[database_name]
    collection_name = "ContosoCollection"
    index_name = "ContosoIndex"
    collection = db[collection_name]
    
  2. 初始化內嵌用戶端。

    from langchain_openai import AzureOpenAIEmbeddings
    
    openai_embeddings_model = os.getenv("AZURE_OPENAI_EMBEDDINGS_MODEL_NAME", "text-embedding-ada-002")
    openai_embeddings_deployment = os.getenv("AZURE_OPENAI_EMBEDDINGS_DEPLOYMENT_NAME", "text-embedding")
    
    azure_openai_embeddings: AzureOpenAIEmbeddings = AzureOpenAIEmbeddings(
        model=openai_embeddings_model,
        azure_deployment=openai_embeddings_deployment,
    )
    
  3. 從資料建立嵌入,儲存到資料庫,然後回傳連結到你的向量儲存庫 Azure DocumentDB。

    vector_store: AzureDocumentDBVectorSearch = AzureDocumentDBVectorSearch.from_documents(
        json_data,
        azure_openai_embeddings,
        collection=collection,
        index_name=index_name,
    )
    
  4. 在集合上建立下列 HNSW 向量索引 。 (請注意,索引的名稱相同。

    num_lists = 100
    dimensions = 1536
    similarity_algorithm = DocumentDBSimilarityType.COS
    kind = DocumentDBVectorSearchType.VECTOR_HNSW
    m = 16
    ef_construction = 64
    
    vector_store.create_index(
        num_lists, dimensions, similarity_algorithm, kind, m, ef_construction
    )
    

使用 Azure DocumentDB 執行向量搜尋

  1. 連線到您的向量存放區。

    vector_store: AzureDocumentDBVectorSearch =  AzureDocumentDBVectorSearch.from_connection_string(
        connection_string=mongo_connection_string,
        namespace=f"{database_name}.{collection_name}",
        embedding=azure_openai_embeddings,
    )
    
  2. 定義一個函式,能使用 Azure DocumentDB 向量搜尋對查詢進行語意相似性搜尋。 (請注意,此程式碼片段只是一個測試函數。

    query = "beef dishes"
    docs = vector_store.similarity_search(query)
    print(docs[0].page_content)
    
  3. 初始化聊天用戶端以實作 RAG 函式。

    azure_openai_chat: AzureChatOpenAI = AzureChatOpenAI(
        model=openai_chat_model,
        azure_deployment=openai_chat_deployment,
    )
    
  4. 建立 RAG 函式。

    history_prompt = ChatPromptTemplate.from_messages(
        [
            MessagesPlaceholder(variable_name="chat_history"),
            ("user", "{input}"),
            (
                "user",
                """Given the above conversation,
                generate a search query to look up to get information relevant to the conversation""",
            ),
        ]
    )
    
    context_prompt = ChatPromptTemplate.from_messages(
        [
            ("system", "Answer the user's questions based on the below context:\n\n{context}"),
            MessagesPlaceholder(variable_name="chat_history"),
            ("user", "{input}"),
        ]
    )
    
  5. 將向量儲存轉換為檢索器,可以根據指定的參數搜尋相關文件。

    vector_store_retriever = vector_store.as_retriever(
        search_type=search_type, search_kwargs={"k": limit, "score_threshold": score_threshold}
    )
    
  6. 建立一個了解對話歷史記錄的檢索器鏈,確保使用 azure_openai_chat 模型和 vector_store_retriever進行上下文相關的文件檢索。

    retriever_chain = create_history_aware_retriever(azure_openai_chat, vector_store_retriever, history_prompt)
    
  7. 使用語言模型 (azure_openai_chat) 和指定的提示 (context_prompt),建立鏈結,將擷取的文件結合成一致的回應。

    context_chain = create_stuff_documents_chain(llm=azure_openai_chat, prompt=context_prompt)
    
  8. 建立處理整個擷取程序的鏈結,整合記錄感知擷取器鏈結和文件組合鏈結。 您可以執行此 RAG 鏈結來擷取並產生內容正確的回應。

    rag_chain: Runnable = create_retrieval_chain(
        retriever=retriever_chain,
        combine_docs_chain=context_chain,
    )
    

範例輸出

下列螢幕擷取畫面說明各種問題的輸出。 純粹的語意相似性搜尋會從來源文件傳回原始文字,而使用RAG架構的問答應用程式會藉由結合擷取的文件內容與語言模型來產生精確的個人化答案。

Cosmic Food 應用程式範例輸出的螢幕擷取畫面。

Conclusion

在這套教學中,我們探討如何利用 Azure DocumentDB 作為向量儲存工具,打造一個能與你的私人資料互動的問答應用程式。 藉由搭配 LangChain 和 Azure OpenAI 使用 RAG 架構,我們示範向量存放區對於 LLM 應用程式的重要性。

RAG 是 AI 的顯著進步,特別是在自然語言處理中,結合這些技術可針對各種使用案例建立強大的 AI 驅動應用程式。

後續步驟