背景:
為了快速且規范的實現ai應用,可使用LangChain框架,便于后期維護。雖然deepseek異軍突起,在終端用戶占有率很高,但是仔細查閱相關api接口,尤其是自有知識庫需要使用的文本向量化模型方面,openai仍無法被替代。目前國內仍無法付費使用openai接口,需要迂回使用azure版的openai相關模型。
目前,ai類應用處于快速迭代期,很多一年前的教程已經過時,因此記錄下2025年最新的ai應用使用方法。
一、開通azureopenai需要注冊azure.microsoft.com微軟云服務,并綁定visa功能的信用卡。
openai.com不支持國內信用卡:
在azure的主頁左上角下拉菜單,找到“成本管理 + 計費”:
在“成本管理 + 計費”窗口左側導航欄,打開“計費-》付款方式”:
添加visa卡即可。
二、進入Azure AI Foundry,創建ai容器
訪問新版的ai地址:Azure AI Foundryhttps://ai.azure.com/
?
然后通過頂部“+創建項目”按鍵一鍵完成openai容器創建。
注意:我也試過舊版的創建容器方式,也許是訪問地址沒有搞對,使用api訪問總是報404錯誤。
用新版創建容器后,點擊項目名稱,直接進入項目。
點擊操場即可測試當前容器是否運行正常:
?在舊版的azure openai容器沒有找到類似功能。也許有,但是新版更好找。推薦小白初學者用新版
Azure AI Foundryhttps://ai.azure.com/
三、測試python接入azure openai
點擊聊天操場的“查看代碼”功能
?可以看到完整的python運行代碼:
?粘貼到https://colab.research.google.com/或者jupyter notebook中稍加改動(加入api key和endpoint)即可運行:
?api key在 Azure AI Foundry / 224199843-5323 /?概述 頁可以找到
endpoint在示例代碼上方的文本框中能找到:
?注意:在使用langchain_openai框架時,endpoint不填全,api接口無法訪問,會報404錯誤。比如只填域名部分:
https://ai-2241998435710ai347721904316.openai.azure.com/
https://ai-2241998435710ai347721904316.openai.azure.com/
?
被這個問題困惑了一天,最后填寫了正確的url地址才解決。
!pip install -U langchain_openai
from langchain_openai import AzureChatOpenAI
from google.colab import userdatachat = AzureChatOpenAI(azure_endpoint="https://ai-2241998435710ai347721904316.openai.azure.com/openai/deployments/gpt-4o-mini/chat/completions?api-version=2025-01-01-preview",# azure_endpoint="https://ai-2241998435710ai347721904316.openai.azure.com/", 錯誤urlazure_deployment="ai-2241998435710ai347721904316",api_key=userdata.get('AZURE_OPENAI_API_KEY'),api_version="2025-01-01-preview",temperature=0,max_tokens=None,timeout=None,max_retries=2,# organization="...",# model="gpt-35-turbo",# model_version="0125",# other params...
)messages = [("system","You are a helpful translator. Translate the user sentence to French.",),("human", "I love programming."),
]
chat.invoke(messages)
四、學會使用langchain的 提示詞模板(ChatPromptTemplate)和 輸出解析器(JsonOutputParser)
雖然吳恩達的課程已經過時,但是可以結合deepseek的提示和最新的langchain api文檔來學習,我覺得吳恩達的講課思路非常清晰,很適合看了一堆視頻,越看越沒有頭緒的初學者。
(超爽中英!) 2024公認最好的【吳恩達LangChain+RAG】教程!更適合中國寶寶體質,全程干貨無廢話,學完成為AGI大佬!(附課件+代碼)_嗶哩嗶哩_bilibili(超爽中英!) 2024公認最好的【吳恩達LangChain+RAG】教程!更適合中國寶寶體質,全程干貨無廢話,學完成為AGI大佬!(附課件+代碼)共計29條視頻,包括:基于LangChain的大語言模型應用開發1——介紹、基于LangChain的大語言模型應用開發2——模型,提示和輸出解析、基于LangChain的大語言模型應用開發3——記憶等,UP主更多精彩視頻,請關注UP賬號。https://www.bilibili.com/video/BV1TJ4zemETf/
from langchain_openai import AzureChatOpenAI
from google.colab import userdatachat = AzureChatOpenAI(azure_endpoint="https://ai-2241998435710ai347721904316.openai.azure.com/openai/deployments/gpt-4o-mini/chat/completions?api-version=2025-01-01-preview",# azure_endpoint="https://ai-2241998435710ai347721904316.openai.azure.com/",azure_deployment="ai-2241998435710ai347721904316",api_key=userdata.get('AZURE_OPENAI_API_KEY'),api_version="2025-01-01-preview",temperature=0,max_tokens=None,timeout=None,max_retries=2,# organization="...",# model="gpt-35-turbo",# model_version="0125",# other params...
)from langchain_core.prompts import ChatPromptTemplate
from langchain_core.output_parsers import JsonOutputParser
# from langchain_core.pydantic_v1 import BaseModel, Field, HttpUrl
# langchain_core.pydantic_v1 已淘汰,langchain可以直接導入pydantic 2的對象
from pydantic import BaseModel, Field, HttpUrl
from typing import List, Optional, Union
from datetime import date# 1.1 創建含有動態字段的簡歷結構# 動態字段的基類
class DynamicSection(BaseModel):section_name: str = Field(description="模塊名稱")content: Union[str, List[str], dict] = Field(description="模塊內容")# 教育經歷、工作經歷、技能、項目經驗
class Education(BaseModel):"""教育背景條目(所有字段可選)"""sections: List[DynamicSection] = Field(default_factory=list, description="動態項或動態列表")class WorkExperience(BaseModel):"""工作經歷條目(所有字段可選)"""sections: List[DynamicSection] = Field(default_factory=list, description="動態項或動態列表")class Skill(BaseModel):"""技能條目(所有字段可選)"""sections: List[DynamicSection] = Field(default_factory=list, description="動態項或動態列表")class ProjectExperience(BaseModel):sections: List[DynamicSection] = Field(default_factory=list, description="動態項或動態列表")class Resume_dynamic(BaseModel):"""簡歷數據模型(所有字段可選)"""# 基礎信息seq_num: Optional[int] = Field(None, description="序號", gt=0)file_name: Optional[str] = Field(None, description="文件名", max_length=255) # 允許字母數字/下劃線/點/橫線 regex=r"^[\w\-\.]+$"is_resume: Optional[bool] = Field(None, description="該文件是否是簡歷")# 個人信息name: Optional[str] = Field(None, description="姓名", min_length=2, max_length=50)gender: Optional[str] = Field(None, description="性別", examples=["男", "女", "其他"])birthday: Optional[date] = Field(None, description="生日")ethnicity: Optional[str] = Field(None, description="民族")political_affiliation: Optional[str] = Field(None, description="政治面貌")marital_status: Optional[str] = Field(None, description="婚姻狀況")native_place: Optional[str] = Field(None, description="籍貫或戶口所在地")address: Optional[str] = Field(None, description="現住址")id_number: Optional[str] = Field(None, description="身份證號碼", pattern=r"^\d{17}[\dXx]$")phone: Optional[str] = Field(None, description="手機號", pattern=r"^1[3-9]\d{9}$")email: Optional[str] = Field(None, description="郵箱", pattern=r"^[\w\.-]+@[\w\.-]+\.\w{2,4}$")# 教育信息highest_degree: Optional[str] = Field(None, description="最高學歷", examples=["高中", "專科", "本科", "碩士", "博士"])major: Optional[str] = Field(None, description="最高學歷專業", max_length=50)# 求職信息job_target: Optional[str] = Field(None, description="求職意向職業", max_length=100)# 結構化信息education_background: Optional[List[Education]] = Field(None, description="教育背景")work_experience: Optional[List[WorkExperience]] = Field(None, description="工作經歷")skills: Optional[List[Skill]] = Field(None, description="特殊技能或資格證書")project_experience: Optional[List[ProjectExperience]] = Field(None, description="項目經歷")# 2.1 創建簡歷結構json解析器
resume_output_parser = JsonOutputParser(pydantic_object=Resume_dynamic)# 3. 創建簡歷解析提示模板
prompt = ChatPromptTemplate.from_template("解析以下簡歷:{question}\n""請按照指定格式返回:\n""{format_instructions}"
)# 4. 組合成鏈
chain = prompt | chat | resume_output_parserresume_text = '''
應聘人員信息表
姓名 ...
電話 ...
... ...'''# 5. 調用
result = chain.invoke({"question": resume_text,"format_instructions": resume_output_parser.get_format_instructions()
})
result輸出結果:
{'seq_num': None,'file_name': None,'is_resume': None,'name': '','gender': '男','birthday': '1900-00-00','ethnicity': '漢','political_affiliation': '群眾','marital_status': '未婚','native_place': '吉林省長春市','address': '高新技術開發區,保利羅蘭香谷','id_number': '221100000000000000','phone': '15922334455','email': None,'highest_degree': '碩士','major': '建筑與土木工程','job_target': '市政道路、排水設計','education_background': [{'sections': [{'section_name': '教育經歷','content': {'起止年月': '2012.09-2015.07','畢業院校及系名稱': '吉林建筑大學','專業': '建筑與土木工程','學位': '碩士'}},{'section_name': '教育經歷','content': {'起止年月': '2008.09-2012.07','畢業院校及系名稱': '長春工程學院',
...{'section_name': '項目經歷',
注意:langchain_core.pydantic_v1 已淘汰,langchain可以直接導入pydantic 2的對象
例子來自deepseek,在本例中class Resume_dynamic(BaseModel):對象即用于提示詞中對生成格式的要求,又用于將ai生成結果解析為dict對象,一箭雙雕。其余代碼非常直觀,鏈式編程也符合一般人的認知。這樣編寫的代碼即簡潔又高效。