You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在LangServe API及Playground中实现图片+文本聊天功能

实现LangServe图片+文本双向聊天API方案

1. 扩展输入结构支持图片与文本

先定义支持双输入类型的数据模型,替代原纯文本输入,适配LangServe的Pydantic校验机制:

from langchain_core.messages import HumanMessage
from pydantic import BaseModel, Field
from typing import Optional, Union
import base64

class ChatInput(BaseModel):
    text: Optional[str] = Field(default=None, description="用户输入文本")
    image_base64: Optional[str] = Field(default=None, description="上传图片的Base64编码")

class ChatResponse(BaseModel):
    reply: str = Field(description="LLM回复内容")

2. 实现图片OCR解析逻辑

封装easyocr的图片识别函数,全局初始化模型避免重复加载:

import easyocr
import io
from PIL import Image
from fastapi import UploadFile

# 全局初始化OCR模型(按需选择语言)
ocr_reader = easyocr.Reader(['ch_sim', 'en'])

def process_image(image_source: Union[UploadFile, io.BytesIO]) -> str:
    if isinstance(image_source, UploadFile):
        image = Image.open(io.BytesIO(image_source.file.read()))
    else:
        image = Image.open(image_source)
    # 执行OCR识别并拼接文本
    ocr_result = ocr_reader.readtext(image)
    return "\n".join([text for (_, text, _) in ocr_result])

3. 改造聊天链支持混合输入

将纯文本聊天链扩展为可处理图片+文本的混合输入:

from langchain.chat_models import ChatOpenAI
from langchain.chains import ConversationChain
from langchain.memory import ConversationBufferMemory

# 初始化LLM与会话内存
llm = ChatOpenAI(temperature=0)
memory = ConversationBufferMemory()
conversation_chain = ConversationChain(llm=llm, memory=memory, verbose=True)

async def chat_handler(input_data: Union[str, ChatInput]) -> str:
    # 处理纯文本输入
    if isinstance(input_data, str):
        return conversation_chain.predict(input=input_data)
    
    # 处理图片+文本混合输入
    user_text = input_data.text or ""
    extracted_text = ""
    if input_data.image_base64:
        # 解码Base64图片并执行OCR
        image_bytes = base64.b64decode(input_data.image_base64)
        extracted_text = process_image(io.BytesIO(image_bytes))
    
    # 拼接输入内容传递给LLM
    full_input = f"{user_text}\n\n图片识别内容:\n{extracted_text}" if extracted_text else user_text
    return conversation_chain.predict(input=full_input)

4. 配置LangServe路由与Playground适配

挂载聊天API路由

from fastapi import FastAPI, UploadFile, File
from langserve import add_routes

app = FastAPI(title="支持图片的LLM聊天API")

# 添加支持混合输入的聊天路由
add_routes(
    app,
    chat_handler,
    input_type=Union[str, ChatInput],
    output_type=str,
    playground_type="chat",
)

# 可选:单独提供图片上传测试端点
@app.post("/upload-image")
async def direct_image_upload(file: UploadFile = File(...), text: Optional[str] = None):
    extracted_text = process_image(file)
    full_input = f"{text}\n\n图片识别内容:\n{extracted_text}" if text else extracted_text
    return {"reply": conversation_chain.predict(input=full_input)}

给Playground添加图片上传功能

原生LangServe Playground不支持图片上传,可通过两种方式适配:

  • 快速方案:基于上述/upload-image端点,编写简单前端页面(含文件上传框+文本输入框),提交时调用接口。
  • 定制方案:替换LangServe默认Playground模板,在页面中添加图片上传组件,将图片转为Base64后调用聊天接口。可通过FastAPI挂载静态文件实现:
    from fastapi.staticfiles import StaticFiles
    app.mount("/static", StaticFiles(directory="static"), name="static")
    
    在static/playground.html中添加文件上传逻辑,将图片编码为Base64后传入ChatInput模型。

5. 关键优化点

  • 全局初始化easyocr模型,避免每次请求重复加载模型,提升性能。
  • 添加异常捕获:处理图片解码失败、OCR识别出错等场景,返回友好提示。
  • 会话内存管理:确保图片识别的内容被纳入上下文,支持多轮连贯聊天。
  • 图片格式校验:限制上传文件为JPG/PNG等常见格式,避免无效输入。

内容的提问来源于stack exchange,提问作者DevPy

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.26 22:26:15