[LangChain] LangChain Embedding 中可能發生的問題

What is LangChain and how to use it

前提:

之前在 DeepLearning.ai 開放新的課程「LangChain Chat with Your Data」,裡面有許多相當實用的案例分享。這裡要分享一個關於容易誤解的問題。

案例一: 追求過於近似,但是卻忘記重要訊息的搜尋法

image-20230711210300257

這裡有載入四份文件,你有發現他故意重讀檔案一兩次,意圖去讓資料不正確。

image-20230711210431891

想要去查詢「是否有關於 Regression 資料在“第三章”」的時候,由於資料混亂。也會傳回第一章的結果,因為就是有混亂的問題。造成他無法注意“第三章”,而是只注意到 “regression” 這個字。

image-20230711211030414

這時候要使用 “Maximum Marginal Relevance (MMR)” 的方式來尋找資料,而不要找最接近的資料。

vectordb.max_marginal_relevance_search(query,k=2, fetch_k=3)

image-20230711211637196

query = "What is the bitcoin?" query = "What is the bitcoin?" vectordb.similarity_search(query, k=2, filter={"page": 1})

透過 filter 你可以去指定許多參數,從哪一份文件,從哪切割的內容,甚至是內容對照。

參考內容:

[好書分享]我的99個私抽屜-唐鳳的AI時代生存心法

我的99個私抽屜
唐鳳的AI時代生存心法
何もない空間が価値を生む AI時代の哲学
作者: 唐鳳  丘美珍  出版社:網路與書 

買書推薦網址:

前言:

這是 2023 年第六本讀完的書,雖然說唐鳳是近幾年算是很受注目的素人政壇人物之一,他的這些書籍其實都蠻有內容,也很推薦大家來看。

內容摘要:

臺灣數位發展部長唐鳳五歲時閱讀老子《道德經》,其中有云:「埏埴以為器,當其無,有器之用。」她自此深知「價值的產生,在於空間」之道,最終遷徙到網路世界中獨自尋思、與人協作:她與素未謀面之人共筆、共創,打造橫向溝通平台,每日結束時都將所知所得發表上線;更以自身體歷為基底,提出在AI時代生存的多元心理準備。全書以唐鳳第一視角敘事,分為「思考/學習/網路/工作/人生」五大篇章:99個唐鳳的「私抽屜」,每拉開一格,都可發現直透人心的知行祕訣,當下轉念受用!

日本人看唐鳳,就像江戶幕府時代的人,在看明治時代的人!—— 野島剛

在別人提供的知識基礎上,我會加上自己實作的經驗,
作為驗證,加深理解,或進一步擴大影響力。
我稱這樣的過程為「增幅」。

如果我能提供一個空間,甚至自己就變成一個空間、一個通道,
在「無我」的狀態下,讓眾人透過我,
完成他們在意的工作或任務,這就是我的價值。
創造一個讓眾人可以互動的空間,就變成我這輩子持續在做的事。
來拜訪我的人,帶著他們的人生經驗和夢想,提出想讓世界更好的創新思維,
而我的價值,不在於我想要完成什麼,而在於我如何幫他們做想做的事。
—— 唐鳳

心得:

之前他就任的時候,身邊有一些因為主政的政黨取向而懷疑他的能力。但是我只有在思考說:如果你的反對是因為換了一個政黨就不會,那麼你可能受到政黨取向的偏頗。蠻推薦大家可以看這一本數來更了解唐鳳,如果你想要了解他的家庭如何造就她勇敢的決定停止去學校就學,並且可以包容她的各種意見。更可以看看這本,更了解一個良好的家庭教育的想法。

[研討會][LangChain] LangChain 「Chains vs Agents」 Webinar Notes

LangChain "Chains vs Agents" Webinar

Weblink: https://www.crowdcast.io/c/m2ooh0uy9syg

Speak1: Swyx - smol developer

https://docs.google.com/presentation/d/1d5N3YqjSJwhioFT-edmyjxGsPBCMb1uZg0Zs5Ju673k/edit#slide=id.g254e571859c_0_133

image-20230629013808733

image-20230629013651102

Article:

Speaker2: Alex - Agent Eval

https://docs.google.com/presentation/d/1bo5uxaS4JMNt99VmsRdeTFLo9qSIByJiViIVakzF9NQ/edit#slide=id.g22b104eecb9_0_2

image-20230629004649563

  • 很難 debug agent failure:
    • failure token
    • CAPCHA

image-20230629005101725

  • 三種 Evaluation 方式

image-20230629005208061

  • 抓下一堆 dataset

image-20230629005331276

image-20230629010716866

Q&A

  1. What is the most affordable (free, local?) LLM for specific Agent Executor / Agent task like decision making, tool selection…?
    • Mpt7b
  2. In my experience, the OpenAI functions work really well in deciding what tool(s) to use even in multi-step scenarios. Do you think that a train-of-thought process is used behind the scenes, like ReACT or MLKR? And how useful are they now?
    1. 可以考慮看看 few shot

其他

Agent Hackathon

image-20230629011637608

https://lablab.ai/event/ai-agents-hackathon

AgentEval (第一名)

最後有 OpenAI CEO 演講

[學習心得][Python] 透過基於 LangChain 將許多好用工具打包起來的套件 - embedchain 來打造簡易版本客服 LINE Bot 機器人

image-20230628221201753

透過這個 EmbedChain 可以抓取許多種資料,這個圖片是測試他去抓取 「2023年LINE官方帳號方案價格調整,重點一次掌握」網頁上的資料來回覆給使用者。

  • 官方帳號在哪一天調整價錢? 官方帳號價格將在 2023 年 9 月 1 日調整。
  • 中用量方案的價格? 中用量方案的價格是每月 800 元。

前提

許多人都想要打造出客服聊天機器人 LINE Bot ,但是透過 NLU 來打造客服 LINE Bot 其實成本很高。這裡會推薦給各位透過 LangChain 加上 EmbedChain 這個套件,可以打造低成本與簡易版本的客服 LINE Bot 。 本篇文章將快速告訴各位,如何透過 EmbedChain 來打造

這裡也列出一系列,我有撰寫關於 LangChain 的學習文章:

EmbedChain 解決了那些問題

先預設本篇文章讀者,已經是懂的使用 LLM (Large Language Model) 來打造客服機器人。之前你需要先建立客服機器人的參考資料庫,(因為大部分 LLM (e.g. OpenAI) ) 不知道如何回覆你的問題。

需要的架構可以這裡參考文章 Enhancing ChatGPT With Infinite External Memory Using Vector Database and ChatGPT Retrieval Plugin

img

如上圖,快速整理架構如下:

  • 需要把客服文件透過切割成一群群的文字區塊
  • 將文字區塊透過 Embedding 技術放入 LLM 的向量空間,暫存在 Vector Database。 (會變成一個很長的數字陣列 e.g.)
  • 客戶詢問問題的時候,也去針對他的問題切割後作成 Embedding 。並且找尋最接近的文件。
  • 將文件區塊給 LLM 整理後回覆給客戶。

即便你使用了 LangChain 來包裝整個架構,你還是會遇到相關問題:

那有方式可以更快速解決這樣的架構問題嗎? 接下來就要跟大家 EmbedChain

如何透過 EmbedChain 打造客服 LINE Bot

這裡列出幾個簡單流程:

  • 準備打造客服 LINE Bot需要的素材
  • 建立 EmbedChain LINE Bot
  • 測試與調整

以下我們將透過 EmbedChain 來打造一個回覆 LINE Biz-Solution 基本資訊的客服機器人。

image-20230628210029311

(資料來源: LINE Biz-Solution)

準備打造客服 LINE Bot需要的素材

這裡列出一些經常被詢問的問題網頁:

image-20230628090828775

建立 EmbedChain LINE Bot

使用上也很簡單:

  1. 安裝 EmbedChain pip install embedchain

  2. 加上相關程式碼

    from embedchain import App
       
    naval_chat_bot = App()
       
    # Embed Online Resources 將 LINEBiz 內容放進去
    naval_chat_bot.add("web_page", "https://tw.linebiz.com/column/LINEOA-2023-Price-Plan/")
    naval_chat_bot.add("web_page", "https://tw.linebiz.com/column/stepmessage/")
    naval_chat_bot.add("web_page", "https://tw.linebiz.com/column/LAP-Maximize-OA-Strategy/")
       
    # Embed Local Resources
    naval_chat_bot.add_local("qna_pair", ("Who is Naval Ravikant?", "Naval Ravikant is an Indian-American entrepreneur and investor."))
       
    naval_chat_bot.query("What unique capacity does Naval argue humans possess when it comes to understanding explanations or concepts?")
    # answer: Naval argues that humans possess the unique capacity to understand explanations or concepts to the maximum extent possible in this physical reality.
    

測試與調整

目前測試下來發現的問題還不少:

  • 常常跑出英文
  • 容易跑出不知道答案在哪裡

結語

EmbedChain 來打造客服機器人算是可以達成 POC 概念的呈現,但是如果要正式上線的話,建議還是要透過 LangChain 來透過 vector stores 加上 Embedding 來打造(其實也是他裡面的方式)。這邊有更多的資訊,會再慢慢更新上來。

[學習心得][Python] 透過 LangChain 來處理特殊的中央氣象局資料

image-20230622194316256

前提

接下來,我們將介紹如何透過 LangChain 來打造一些實用的 LINE Bot 。第一個我們先透過旅遊小幫手的概念,來幫大家串接關於氣象的 LangChain Function Agent吧。

本篇文章將要帶給各位一些概念:

  • 如何用 LangChain 來串接 中央氣象局的 Open API Data
  • 如何在 LLM 的對話中來處理一些特別數值的輸入。
  • 如何活用 LLM 對話的聰明性,來活用 LangChain Function Agent 。

這裡也列出一系列,我有撰寫關於 LangChain 的學習文章:

直接看如何使用程式碼 https://github.com/kkdai/langchain_tools/blob/master/travel_tool/

如何用 LangChain 來串接 中央氣象局的 Open API Data

要申請中央氣象局 OpenAPI Data ,依照以下流程:

image-20230622195316423

接下來來透過 ChatGPT 來協助撰寫相關資料:

  • 透過 Execute 結果中的 CURL `
  curl -X 'GET' \
    'https://opendata.cwb.gov.tw/api/v1/rest/datastore/F-C0032-001?Authorization=你的授權碼' \
    -H 'accept: application/json'
  • 然後去ChatGPT 問說,就可以取得 get_weather_data ,這邊記住我們只有使用地點。原因如下:

    • 雖然會傳回未來三天的氣象資料,但是 LLM 可以幫我們整理,並且篩選。
    • 三天的資料也可以幫助我們來處理更多詢問,不需要再查詢的時候就修改。
    def get_weather_data(location_name=None):
      
        url = 'https://opendata.cwb.gov.tw/api/v1/rest/datastore/F-C0032-001'
      
        headers = {'accept': 'application/json'}
      
        query = {
            'Authorization': cwb_token}
      
        if location_name is not None:
            query['locationName'] = location_name
      
        response = requests.get(url, headers=headers, params=query)
      
        if response.status_code == 200:
            return response.json()
        else:
            return response.status_code
    

轉換成 LangChain Function Agent

參考之前其他的 Tool Agent 的寫法,可以很快速改成以下方式。

cwb_token = os.getenv('CWB_TOKEN', None)

# From CWB API
# https://opendata.cwb.gov.tw/dist/opendata-swagger.html#/%E9%A0%90%E5%A0%B1/get_v1_rest_datastore_F_C0032_001
class WeatherDataInput(BaseModel):
    """Get weather data input parameters."""
    location_name: str = Field(...,
                               description="The cities in Taiwan.")


class WeatherDataTool(BaseTool):
    name = "get_weather_data"
    description = "Get the weather data for Taiwan"

    def _run(self,  location_name: str):
        weather_data_results = get_weather_data(
            location_name)

        return weather_data_results

    def _arun(self, location_name: str):
        raise NotImplementedError("This tool does not support async")

    args_schema: Optional[Type[BaseModel]] = WeatherDataInput

如何在 LLM 的對話中來處理一些特別數值的輸入。

如果你依照以上的方式來寫,你會發現你執行天氣的結果都會失敗。尤其是查詢台北市的天氣。

image-20230702160209686

如果回去看原來的 Open API Spec

image-20230622200638227

誒?! 原來是固定輸入的資料,而且資料名稱用「臺北市」?!那該怎麼辦呢?

你不能要求每次叫使用者輸入「臺北市」,更不要自己去改那些輸入。(那就太不 LLM 了)。那該如何處理呢?

讓 LLM 了解你的輸入範圍,並且知道該如何調整。

既然知道,地址只能輸入一個區間的資料。並且有限定的「用字」(也就是 臺) 。其實可以透過 Function 的敘述來讓 LLM (OpenAI) 來讀懂。

location_name: str = Field(...,
                           description="The cities in Taiwan, it must be one of following 臺北市, 新北市, 臺中市, 臺南市, 雲林縣, 南投縣, 屏東縣, 嘉義市, 嘉義縣")

只要透過對於 Argument 的敘述更加的細膩,LLM(OpenAI) 就會讀懂他的含義來幫你解決。比如說這樣的敘述:

  • 台北市 –> 就會輸入 「臺北市」(同理台中)
  • 墾丁 –> 因為不在裡面,他會猜測墾丁可能在屏東縣附近。就會輸入「屏東縣」。

這樣是不是我們需要的呢?

如何活用 LLM 對話的聰明性,來活用 LangChain Function Agent 。

image-20230622194316256 image-20230622203105421

這邊用以上兩個截圖給各位一些想法,也證實了透過 LLM 是可以很強大的來讓你的聊天機器人更聰明。

  • 明天台北市跟新北市白天哪裡比較容易下雨:
    • 這會呼叫兩次,一次查「臺北市」另外一次查「新北市」的氣象資訊。然後 LLM 會幫你整理相關資訊,並且比較裡面的「降雨機率」。
    • 同理也可以知道哪裡溫度比較高。
  • 告訴我明天靠近墾丁的天氣:
    • 這會去查詢「屏東縣」的資料。
  • 明天台北需要帶傘嗎?:
    • 這就是 LLM 最聰明的事情,以前還需要透過 NLU 的處理方式。現在都不需要了,直接知道你要找氣象局。並且幫你分析究竟需不需要帶傘。

結語

還記得 2018 年,在 iThome 演講的題目裡面就有提到,Intent 跟 Entity 的重要性。也表示不論那時候多麼先進的 NLU 引擎都很難處理許多內容。但是 2022 年的年底,自從 OpenAI 的模型公開後,我們就發現了許多嶄新的應用。更加上許多殺手型的運用(Function Calling) 看來讓許多的開發者可以換了新的腦袋來思考問題。

[學習心得][Python] 透過 LangChain 的 Functions Agent 達成用中文來操控資料夾

image-20230619204550551

前提

以前 Linux 課程上,大家總是對於 ls , mvcp 的指令無法背起來。都忘記有多少次聽到朋友抱怨,難道不能用中文來下指令嗎? 比如說:

  • 幫我移動1.pdf
  • 刪除 2.cpp 這個檔案
  • 列出檔案

現在,其實你可以透過 LangChain 很快來達成。本篇文章將給你範例程式碼,跟相關的原理 LangChain Functions Agent 的用法。

這裡也列出一系列,我有撰寫關於 LangChain 的學習文章:

開源套件參考這個 https://github.com/kkdai/langchain_tools/tree/master/func_filemgr

什麼是 LangChain

透過 LLM (大型語言模型)的開發上,有許多很方便的工具可以幫助你快速地打造出 POC 。 這裡最知名的莫過於 LangChain ,除了支援眾多的大型語言模型之外,更支援許多小工具(類似: Flowise) 。

What is LangChain and how to use it

什麼是 Functions Tool

就像是這篇文章提到的一樣, Functions Tools 是根據 最新的 06/13 公佈的 OpenAI Function Calling 的功能 所打造的功能。也就是你先給予 LLM 一連串可以執行的「工具列表」後。他會根據你的語意,來回答給你說「可能」是屬於哪一個 Function Tool 可以呼叫。 並且讓你來決定,究竟是要呼叫呢? 還是要繼續處理它。

就像是幫你的 LLM 告訴他可以做哪些判斷,由他來幫你判斷使用者的語意「可能」做哪一件事情。

image-20230620112225023

(讓機器人來幫你決定,應該要準備執行哪個 Function Tools)

在 Python LangChain 裡面也相當的簡單,前一篇文章已經有大部分的內容。 這裡做相關的說明:

from stock_tool import StockPriceTool
from stock_tool import get_stock_price

model = ChatOpenAI(model="gpt-3.5-turbo-0613")

# 將工具轉換成可以被解釋的 JSON 格式給 LLM 來處理。(目前只有 OpenAI)
tools = [StockPriceTool()]
functions = [format_tool_to_openai_function(t) for t in tools]

.....

# 透過 OpenAI 的最新模型,來判斷這個使用者的文字應該去執行哪個 Function
# 回傳可能是 get_stock_price 或者甚至可能是空的。
hm = HumanMessage(content=event.message.text)
ai_message = model.predict_messages([hm], functions=functions)

# 處理 OpenAI 幫你抓出的「參數」(arguments)
_args = json.loads(
    ai_message.additional_kwargs['function_call'].get('arguments'))

# (optional) 直接去執行該 function tool
tool_result = tools[0](_args)

這邊如果直接把結果回傳,可能只會達到股價的「數字」而已。甚至那個數字的單位都不會加上去。其實這只是讓 LLM 來告訴你該使用哪個 function 的判斷跟解釋。就很像我們之前使用 NLU 的 Intent detection 一樣。

如何完成 LangChain Functions Agent

image-20230621132804983

如果是 Function Agent 的話,就像是幫你的 LLM 大腦裝上了手臂,開始讓他不只是「說」,更能夠開使「動手做」。

image-20230620110007097

這邊「更加的抽象一點」,除了讓 LLM 知道有哪些工具外。 並且透過將他們定義成 Agent 去抓取資料後再來解釋。也就是會有以下流程:

  • 輸入使用者語詞,判斷呼叫哪個 Agent。並且取出相關的 Arguments 。
  • 呼叫該 Agent ,並且取得結果。
  • 透過結果,再一次詢問 LLM 總結回覆的答案。
# 以下 impot 工具類別中的 file management 工具組
# 這些是真的可以操控檔案的相關 tools
# 分別是: 讀取檔案,複製檔案,刪除檔案,移動檔案,寫入檔案。
from langchain.tools.file_management import (
    ReadFileTool,
    CopyFileTool,
    DeleteFileTool,
    MoveFileTool,
    WriteFileTool,
    ListDirectoryTool,
)

....

# 以下方式透過 OPENAI_FUNCTIONS 的 Agent 格式將剛才所有的工具都加入進去。
# 也就是說我們的 LLM 現在多了檔案操控的能力。

    model = ChatOpenAI(model="gpt-3.5-turbo-0613")
    tools = FileManagementToolkit().get_tools()
    open_ai_agent = initialize_agent(tools,
                                     model,
                                     agent=AgentType.OPENAI_FUNCTIONS,
                                     verbose=True)



# 真的要執行 Agent 的功能只要呼叫這一行就好。
        tool_result = open_ai_agent.run(question)

Langchain Functions Agent 跟 Functions Tool 的比照表

  OpenAI Function Tools OpenAI Function Agent
定義方式 Tools 透過 LangChain Tools 包裝成 Agents (OPENAI_FUNCTIONS)
執行流程 (1)輸入使用者語詞,判斷呼叫哪個 Agent。並且取出相關的 Arguments 。 (2) 開發者自己決定要不要去執行他,或是剩下的動作。 (1)輸入使用者語詞,判斷呼叫哪個 Agent。並且取出相關的 Arguments 。 (2) 呼叫該 Agent ,並且取得結果。 (3) 透過結果,再一次詢問 LLM 總結回覆的答案。
不要回覆定意外問題? 可以,自己決定哪些要回覆 不行!不論什麼都會回覆。

成果

以下的影片可以看到,這樣才幾行的程式碼,卻可以開始操控檔案。

並且,你還不需要完整把指令打對,甚至可以使用中文的指令才「列表」「讀取」「寫入」「刪除」,

最令人不可相信的是,你甚至可以「寫一首詩,然後把內容寫進 1.txt」這種比較複雜的指令都可以完整地被執行。

asciicast

結語

近期完了不少的 LangChain 的相關範例,並且感受了透過 Flowise 來打造相關應用的方式。 覺得 LINE Bot 的開發將會幫助各位更容易貼近使用者。打造出一個「專一」「好用」的聊天機器人,並且讓 LINE 官方帳號來幫助你的生意邁向生成式 AI 的時代吧!!