欢迎光临
我们一直在努力

【AI大模型接入SDK】LLMManager架构设计与实现

头像

🎬 个人主页:艾莉丝努力练剑

❄专栏传送门:《C语言》《数据结构与算法》《C/C++干货分享&学习过程记录》 《Linux操作系统编程详解》《笔试/面试常见算法:从基础到进阶》《Python干货分享》

⭐️为天地立心,为生民立命,为往圣继绝学,为万世开太平


🎬 艾莉丝的简介:

在这里插入图片描述


文章目录

  • 1 ~> 项目背景与设计目标
    • 1.1 现有模型接入方案
    • 1.2 现有方案存在的问题
    • 1.3 LLMManager 设计目标
  • 2 ~> 核心抽象与数据结构
    • 2.1 LLMProvider 抽象基类
      • 2.1.1 核心接口契约
      • 2.1.2 子类实现示例(DeepSeekProvider)
    • 2.2 ModelInfo 模型元数据结构体
    • 2.3 LLMManager 核心管理类成员
      • 2.3.1 头文件基础结构
      • 2.3.2 成员变量设计说明
  • 3 ~> LLMManager 公有接口定义
    • 3.1 模型生命周期接口
      • 3.1.1 registerProvider 注册接口
      • 3.1.2 initModel 初始化接口
    • 3.2 模型查询接口
      • 3.2.1 getAvailableModels 获取可用列表
      • 3.2.2 isModelAvailable 可用性检查
    • 3.3 消息交互接口
      • 3.3.1 sendMessage 同步调用
      • 3.3.2 sendMessageStream 流式调用
  • 4 ~> 核心方法实现细节
    • 4.1 注册与初始化逻辑
      • 4.1.1 registerProvider 实现
      • 4.1.2 initModel 实现
    • 4.2 查询逻辑实现
      • 4.2.1 getAvailableModels 实现
      • 4.2.2 isModelAvailable 实现
    • 4.3 消息转发机制
  • 5 ~> 扩展机制与架构价值
    • 5.1 模型扩展流程
    • 5.2 架构设计优势
    • 5.3 当前已接入模型清单
  • 结尾

在这里插入图片描述


1 ~> 项目背景与设计目标

1.1 现有模型接入方案

  • 云端模型接入:通过 HTTP API 调用方式接入三类主流云端大语言模型,包括 ChatGPT 系列、Gemini 系列、DeepSeek 系列
  • 本地模型接入:基于 Ollama 第三方推理工具,实现本地大模型的部署、加载与调用管理
  • 基础扩展逻辑:新增模型接入仅需新建对应实现类,重写抽象基类的纯虚方法即可完成适配,无需修改核心框架

1.2 现有方案存在的问题

  • 代码冗余度高:不同云端模型除 API 密钥、服务端点不同外,请求封装、响应解析、流式处理等核心逻辑高度重合;每接入新模型都需重复实现完整逻辑,代码复用率低、可读性差
  • 业务耦合度高:模型数量增多后,上层业务需直接感知具体模型实现类,调用时需实例化对应 Provider,维护与切换成本高
  • 缺乏统一管控:模型状态、配置、生命周期分散在各个实现类中,无法进行统一的状态监控与调度管理

1.3 LLMManager 设计目标

基于面向对象多态机制构建统一模型管理层,实现三大核心目标:

  • 屏蔽底层不同模型的实现差异,对外提供一致的调用接口
  • 集中管理所有模型的注册、初始化、状态校验与消息转发
  • 上层业务无需依赖具体模型实现类,仅通过 LLMManager 即可完成全部模型交互,符合开闭原则

2 ~> 核心抽象与数据结构

2.1 LLMProvider 抽象基类

LLMProvider 是所有模型提供者的抽象基类,定义了统一的接口契约,是多态机制的核心基础。所有具体模型必须继承该类并实现全部纯虚函数。

2.1.1 核心接口契约

class LLMProvider {
public:
virtual ~LLMProvider() = default;

// 模型初始化:加载配置、校验密钥、建立连接
virtual bool initModel(const std::map<std::string, std::string>& modelConfig) = 0;

// 检查模型当前是否可用
virtual bool isAvailable() const = 0;

// 获取模型元数据信息
virtual ModelInfo getModelInfo() const = 0;

// 同步发送消息,返回完整回复
virtual std::string sendMessage(
const std::vector<Message>& messages,
const std::map<std::string, std::string>& requestParam
) = 0;

// 流式发送消息,通过回调逐块返回数据
virtual std::string sendMessageStream(
const std::vector<Message>& messages,
const std::map<std::string, std::string>& requestParam,
std::function<void(const std::string& chunk, bool last)> chunkCallback
) = 0;
};

2.1.2 子类实现示例(DeepSeekProvider)

bool DeepSeekProvider::initModel(const std::map<std::string, std::string>& modelConfig) {
// 读取并校验API密钥
auto it = modelConfig.find("api_key");
if (it == modelConfig.end()) {
ERR("DeepSeekProvider initModel api_key not found");
return false;
}
_apiKey = it->second;

// 读取并校验服务端点
it = modelConfig.find("endpoint");
if (it == modelConfig.end()) {
ERR("DeepSeekProvider initModel endpoint not found");
return false;
}
_endpoint = it->second;

_isAvailable = true;
INFO("DeepSeekProvider initModel success, endpoint: {}", _endpoint);
return true;
}

bool DeepSeekProvider::isAvailable() const {
return _isAvailable;
}

std::string DeepSeekProvider::getModelName() const {
return "deepseek-chat";
}

2.2 ModelInfo 模型元数据结构体

定义于common.h头文件,用于存储模型的静态描述信息,实现模型元数据与业务实现的分离,支撑对外信息展示。

struct ModelInfo {
std::string modelName; // 模型唯一标识名称
std::string modelDesc; // 模型功能与定位描述
std::string provider; // 模型提供厂商
std::string endpoint; // 模型API服务根地址
bool isAvailable = false; // 模型实时可用性状态

// 带默认参数的构造函数
ModelInfo(
const std::string& modelName = "",
const std::string& modelDesc = "",
const std::string& provider = "",
const std::string& endpoint = ""
) : modelName(modelName), modelDesc(modelDesc), provider(provider), endpoint(endpoint) {}
};

2.3 LLMManager 核心管理类成员

LLMManager 通过双映射容器实现模型实例与元数据的统一管理,是整个 SDK 的核心调度中枢。

2.3.1 头文件基础结构

#pragma once
#include <map>
#include <memory>
#include <vector>
#include <string>
#include <stdexcept>
#include <functional>
#include "LLMProvider.h"
#include "common.h"

namespace ai_chat_sdk {

class LLMManager {
public:
// 公有业务接口(后续章节详细定义)

private:
// 模型提供者映射表:key=模型名称, value=模型提供者基类智能指针
std::map<std::string, std::shared_ptr<LLMProvider>> providers;

// 模型信息映射表:key=模型名称, value=模型元数据对象
std::map<std::string, ModelInfo> modelInfos;
};

} // namespace ai_chat_sdk

2.3.2 成员变量设计说明

  • providers:存储所有已注册的模型提供者实例,通过基类指针指向子类对象,利用 C++ 多态特性实现统一调用
  • modelInfos:存储所有模型的元数据信息,与providers通过模型名称一一对应;对外仅暴露该层数据,避免泄露内部实现对象

3 ~> LLMManager 公有接口定义

3.1 模型生命周期接口

3.1.1 registerProvider 注册接口

void registerProvider(const std::string& modelName, std::shared_ptr<LLMProvider> provider);

  • 功能:将具体模型的实现类实例注册到管理容器,是模型纳入统一管理的入口
  • 参数:
    • modelName:模型唯一标识名称,作为后续调用的索引键
    • provider:模型提供者实例的智能指针,必须是 LLMProvider 子类的实例
  • 约束:重复注册同一名称的模型会覆盖原有实例

3.1.2 initModel 初始化接口

bool initModel(const std::string& modelName, const std::map<std::string, std::string>& modelParam);

  • 功能:根据模型名称查找对应实例,完成配置加载与可用性校验
  • 参数:
    • modelName:目标模型的注册名称
    • modelParam:模型初始化参数字典,通常包含api_key、endpoint等配置项
  • 返回值:初始化成功返回 true,失败返回 false
  • 异常:模型未注册时抛出std::runtime_error异常

3.2 模型查询接口

3.2.1 getAvailableModels 获取可用列表

std::vector<ModelInfo> getAvailableModels() const;

  • 功能:返回所有已注册且状态为可用的模型元数据集合
  • 应用场景:客户端新建会话时的模型选择界面展示
  • 返回值:仅包含isAvailable = true的模型信息

3.2.2 isModelAvailable 可用性检查

bool isModelAvailable(const std::string& modelName) const;

  • 功能:校验指定名称的模型是否存在且处于可用状态
  • 返回值:模型不存在或不可用均返回 false,可用返回 true
  • 作用:消息发送前的前置校验,避免无效调用

3.3 消息交互接口

3.3.1 sendMessage 同步调用

std::string sendMessage(
const std::string& modelName,
const std::vector<Message>& messages,
const std::map<std::string, std::string>& requestParam
);

  • 功能:向指定模型同步发送对话消息,等待并返回完整回复文本
  • 参数:
    • modelName:目标模型名称
    • messages:对话历史消息列表,包含角色与内容
    • requestParam:请求超参数,如temperature、max_tokens等

3.3.2 sendMessageStream 流式调用

std::string sendMessageStream(
const std::string& modelName,
const std::vector<Message>& messages,
const std::map<std::string, std::string>& requestParam,
std::function<void(const std::string& chunk, bool last)> chunkCallback
);

  • 功能:向指定模型发送流式请求,通过回调函数逐块返回生成的文本
  • 回调参数:
    • chunk:当前返回的文本片段
    • last:是否为最后一块数据,为 true 时表示响应结束
  • 返回值:最终拼接完成的完整回复文本
  • 流式回调使用示例:
    • auto writeChunk = [](const std::string& chunk, bool last) { INFO("chunk: {}", chunk); if (last) { INFO("[DONE]"); } }; std::string fullData = manager.sendMessageStream("deepseek-chat", messages, requestParam, writeChunk);

4 ~> 核心方法实现细节

4.1 注册与初始化逻辑

4.1.1 registerProvider 实现

void LLMManager::registerProvider(const std::string& modelName, std::shared_ptr<LLMProvider> provider) {
providers[modelName] = provider;
// 同步写入模型基础信息,保证双映射表数据一致
modelInfos[modelName] = provider->getModelInfo();
}

  • 实现要点:注册阶段同时维护providers与modelInfos两个容器,保证数据一致性;注册仅存储实例,不执行初始化

4.1.2 initModel 实现

bool LLMManager::initModel(const std::string& modelName, const std::map<std::string, std::string>& modelParam) {
auto it = providers.find(modelName);
if (it == providers.end()) {
throw std::runtime_error("Model provider not found: " + modelName);
}

// 多态调用:基类指针调用子类重写的初始化方法
bool success = it->second->initModel(modelParam);
// 更新元数据中的可用性状态
modelInfos[modelName].isAvailable = success;
return success;
}

  • 多态原理:基类指针根据指向对象的实际类型,调用对应子类重写的虚函数,实现 “一个接口,多种实现”
  • 状态同步:初始化结果同步更新到modelInfos,确保查询接口返回最新状态

4.2 查询逻辑实现

4.2.1 getAvailableModels 实现

std::vector<ModelInfo> LLMManager::getAvailableModels() const {
std::vector<ModelInfo> models;
for (const auto& pair : modelInfos) {
if (pair.second.isAvailable) {
models.push_back(pair.second);
}
}
return models;
}

  • 实现逻辑:遍历元数据映射表,过滤出可用状态的模型并返回;不直接操作providers容器,符合信息隐藏原则

4.2.2 isModelAvailable 实现

bool LLMManager::isModelAvailable(const std::string& modelName) const {
auto it = modelInfos.find(modelName);
if (it == modelInfos.end()) {
return false;
}
return it->second.isAvailable;
}

  • 容错处理:模型不存在时直接返回 false,不抛出异常,保证接口调用的安全性

4.3 消息转发机制

LLMManager 本身不处理具体的 HTTP 请求、协议封装与响应解析,所有消息交互均采用路由转发模式:

std::string LLMManager::sendMessage(
const std::string& modelName,
const std::vector<Message>& messages,
const std::map<std::string, std::string>& requestParam
) {
auto it = providers.find(modelName);
if (it == providers.end()) {
throw std::runtime_error("Model provider not found: " + modelName);
}
if (!it->second->isAvailable()) {
throw std::runtime_error("Model is not available: " + modelName);
}
// 转发给具体模型提供者执行
return it->second->sendMessage(messages, requestParam);
}

  • 职责边界:LLMManager 仅负责路由寻址、前置校验与结果转发,业务逻辑完全下沉到各 Provider 子类
  • 流式接口实现逻辑与同步接口一致,仅增加回调函数透传

5 ~> 扩展机制与架构价值

5.1 模型扩展流程

新增模型接入严格遵循开闭原则,无需修改 LLMManager 核心代码,标准流程如下:

  • 新建模型 Provider 类,公开继承 LLMProvider 抽象基类
  • 重写所有纯虚函数:initModel、isAvailable、getModelInfo、sendMessage、sendMessageStream
  • 上层业务实例化新模型 Provider,调用registerProvider注册到 LLMManager
  • 传入配置参数调用initModel,完成初始化后即可通过统一接口调用
  • 5.2 架构设计优势

    • 业务解耦:上层业务仅依赖 LLMManager 与通用数据结构,与具体模型实现完全隔离,模型切换无需修改业务代码
    • 统一规范:所有模型遵循相同的接口契约,保证调用方式、参数结构、错误处理的一致性
    • 可维护性:各模型实现逻辑内聚于独立的 Provider 类,故障定位、功能迭代、性能优化互不影响
    • 可测试性:可基于 LLMProvider 接口注入 Mock 实现,在无真实 API 的环境下完成单元测试

    5.3 当前已接入模型清单

    模型名称接入方式定位说明
    deepseek-r1:70b 本地 Ollama DeepSeek 旗舰级开源大模型,128K 上下文,主打深度理解与推理
    gemini-2.0-flash 云端 API Google 极速响应模型,面向大规模部署与快速交互场景
    gpt-4o-mini 云端 API OpenAI 轻量级高性价比模型,核心能力接近 GPT-4 Turbo
    deepseek-chat 云端 API 中文优化通用对话模型,适用于日常问答与创意创作场景

    结尾

    uu们,本文的内容到这里就全部结束了,艾莉丝在这里再次感谢您的阅读!

    艾莉丝努力练剑

    C/C++ & Linux 底层探索者 | 一个正在努力练剑的技术博主


    👀
    【关注】 跟随我一起深耕技术领域,见证每一次成长。

    ❤️
    【点赞】 让优质内容被更多人看见,让知识传递更有力量。


    【收藏】 把核心知识点存好,在需要时随时查、随时用。

    💬
    【评论】 分享你的经验或疑问,评论区一起交流避坑!

    不要忘记给博主“一键四连”哦!

    “今日练剑达成!”

    “技术之路难免有困惑,但同行的人会让前进更有方向。”

    结语:希望对学习Linux相关内容的uu有所帮助,不要忘记给博主“一键四连”哦!

    往期回顾:

    【AI大模型接入SDK】Ollama API 流式增量响应

    🗡博主在这里放了一只小狗,大家看完了摸摸小狗放松一下吧!🗡

    ૮₍ ˶ ˊ ᴥ ˋ˶₎ა

    在这里插入图片描述

    赞(0)
    未经允许不得转载:171主机测评 » 【AI大模型接入SDK】LLMManager架构设计与实现
    分享到: 更多 (0)

    评论 抢沙发

    • 昵称 (必填)
    • 邮箱 (必填)
    • 网址