Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

✨ feat: Support Doubao Models #3055

Closed
wants to merge 24 commits into from
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
28 changes: 28 additions & 0 deletions src/app/(main)/settings/llm/ProviderList/Doubao/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
'use client';

import { DoubaoProviderCard } from '@/config/modelProviders';
import { ModelProvider } from '@/libs/agent-runtime';
import { useUserStore } from '@/store/user';
import { modelProviderSelectors } from '@/store/user/selectors';

import { ProviderItem } from '../../type';

const providerKey = ModelProvider.Doubao;

export const useDoubaoProvider = (): ProviderItem => {

// Get the first model card's deployment name as the check model
const checkModel = useUserStore((s) => {
const chatModelCards = modelProviderSelectors.getModelCardsById(providerKey)(s);

if (chatModelCards.length > 0) {
return chatModelCards[0].deploymentName;
}

return 'Doubao-lite-4k';
});
return {
...DoubaoProviderCard,
checkModel,
};
};
6 changes: 5 additions & 1 deletion src/app/(main)/settings/llm/ProviderList/providers.tsx
Original file line number Diff line number Diff line change
@@ -30,6 +30,7 @@ import {
import { ProviderItem } from '../type';
import { useAzureProvider } from './Azure';
import { useBedrockProvider } from './Bedrock';
import { useDoubaoProvider } from './Doubao';
import { useGithubProvider } from './Github';
import { useHuggingFaceProvider } from './HuggingFace';
import { useOllamaProvider } from './Ollama';
@@ -46,6 +47,7 @@ export const useProviderList = (): ProviderItem[] => {
const HuggingFaceProvider = useHuggingFaceProvider();
const WenxinProvider = useWenxinProvider();
const SenseNovaProvider = useSenseNovaProvider();
const DoubaoProvider = useDoubaoProvider();

return useMemo(
() => [
@@ -81,6 +83,7 @@ export const useProviderList = (): ProviderItem[] => {
Ai360ProviderCard,
TaichuProviderCard,
SiliconCloudProviderCard,
DoubaoProvider,
],
[
AzureProvider,
@@ -91,6 +94,7 @@ export const useProviderList = (): ProviderItem[] => {
WenxinProvider,
HuggingFaceProvider,
SenseNovaProvider,
DoubaoProvider,
],
);
};
};
8 changes: 8 additions & 0 deletions src/config/llm.ts
Original file line number Diff line number Diff line change
@@ -149,6 +149,10 @@ export const getLLMConfig = () => {
SENSENOVA_ACCESS_KEY_ID: z.string().optional(),
SENSENOVA_ACCESS_KEY_SECRET: z.string().optional(),
SENSENOVA_MODEL_LIST: z.string().optional(),

ENABLED_DOUBAO: z.boolean(),
DOUBAO_API_KEY: z.string().optional(),
DOUBAO_MODEL_LIST: z.string().optional(),
},
runtimeEnv: {
API_KEY_SELECT_MODE: process.env.API_KEY_SELECT_MODE,
@@ -295,6 +299,10 @@ export const getLLMConfig = () => {
SENSENOVA_ACCESS_KEY_ID: process.env.SENSENOVA_ACCESS_KEY_ID,
SENSENOVA_ACCESS_KEY_SECRET: process.env.SENSENOVA_ACCESS_KEY_SECRET,
SENSENOVA_MODEL_LIST: process.env.SENSENOVA_MODEL_LIST,

ENABLED_DOUBAO: !!(process.env.DOUBAO_API_KEY && process.env.DOUBAO_MODEL_LIST),
DOUBAO_API_KEY: process.env.DOUBAO_API_KEY,
DOUBAO_MODEL_LIST: process.env.DOUBAO_MODEL_LIST,
},
});
};
69 changes: 69 additions & 0 deletions src/config/modelProviders/doubao.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
import { ModelProviderCard } from '@/types/llm';

// ref https://www.volcengine.com/docs/82379/1330310
const Doubao: ModelProviderCard = {
chatModels: [
{
deploymentName: 'Doubao-lite-4k',
description:
'拥有极致的响应速度,更好的性价比,为客户不同场景提供更灵活的选择。支持 4k 上下文窗口的推理和精调。',
displayName: 'Doubao Lite 4k',
enabled: true,
id: 'Doubao-lite-4k',
tokens: 4096,
},
{
deploymentName: 'Doubao-lite-32k',
description:
'拥有极致的响应速度,更好的性价比,为客户不同场景提供更灵活的选择。支持 32k 上下文窗口的推理和精调。',
displayName: 'Doubao Lite 32k',
enabled: true,
id: 'Doubao-lite-32k',
tokens: 32_768,
},
{
deploymentName: 'Doubao-lite-128k',
description:
'拥有极致的响应速度,更好的性价比,为客户不同场景提供更灵活的选择。支持 128k 上下文窗口的推理和精调。',
displayName: 'Doubao Lite 128k',
enabled: true,
id: 'Doubao-lite-128k',
tokens: 128_000,
},
{
deploymentName: 'Doubao-pro-4k',
description:
'效果最好的主力模型,适合处理复杂任务,在参考问答、总结摘要、创作、文本分类、角色扮演等场景都有很好的效果。支持 4k 上下文窗口的推理和精调。',
displayName: 'Doubao Pro 4k',
enabled: true,
id: 'Doubao-pro-4k',
tokens: 4096,
},
{
deploymentName: 'Doubao-pro-32k',
description:
'效果最好的主力模型,适合处理复杂任务,在参考问答、总结摘要、创作、文本分类、角色扮演等场景都有很好的效果。支持 32k 上下文窗口的推理和精调。',
displayName: 'Doubao Pro 32k',
enabled: true,
id: 'Doubao-pro-32k',
tokens: 32_768,
},
{
deploymentName: 'Doubao-pro-128k',
description:
'效果最好的主力模型,适合处理复杂任务,在参考问答、总结摘要、创作、文本分类、角色扮演等场景都有很好的效果。支持 128k 上下文窗口的推理和精调。',
displayName: 'Doubao Pro 128k',
enabled: true,
id: 'Doubao-pro-128k',
tokens: 128_000,
},
],
description: '字节跳动推出的自研大模型。通过字节跳动内部50+业务场景实践验证,每日万亿级tokens大使用量持续打磨,提供多种模态能力,以优质模型效果为企业打造丰富的业务体验。',
disableBrowserRequest: true, // CORS error
id: 'doubao',
modelsUrl: 'https://www.volcengine.com/product/doubao',
name: '豆包',
url: 'https://www.volcengine.com/product/doubao',
};

export default Doubao;
4 changes: 4 additions & 0 deletions src/config/modelProviders/index.ts
Original file line number Diff line number Diff line change
@@ -7,6 +7,7 @@ import AzureProvider from './azure';
import BaichuanProvider from './baichuan';
import BedrockProvider from './bedrock';
import DeepSeekProvider from './deepseek';
import DoubaoProvider from './doubao';
import FireworksAIProvider from './fireworksai';
import GithubProvider from './github';
import GoogleProvider from './google';
@@ -65,6 +66,7 @@ export const LOBE_DEFAULT_MODEL_LIST: ChatModelCard[] = [
HunyuanProvider.chatModels,
WenxinProvider.chatModels,
SenseNovaProvider.chatModels,
DoubaoProvider.chatModels,
].flat();

export const DEFAULT_MODEL_PROVIDER_LIST = [
@@ -88,6 +90,7 @@ export const DEFAULT_MODEL_PROVIDER_LIST = [
UpstageProvider,
QwenProvider,
WenxinProvider,
DoubaoProvider,
HunyuanProvider,
SparkProvider,
ZhiPuProvider,
@@ -118,6 +121,7 @@ export { default as AzureProviderCard } from './azure';
export { default as BaichuanProviderCard } from './baichuan';
export { default as BedrockProviderCard } from './bedrock';
export { default as DeepSeekProviderCard } from './deepseek';
export { default as DoubaoProviderCard } from './doubao';
export { default as FireworksAIProviderCard } from './fireworksai';
export { default as GithubProviderCard } from './github';
export { default as GoogleProviderCard } from './google';
3 changes: 3 additions & 0 deletions src/const/settings/llm.ts
Original file line number Diff line number Diff line change
@@ -63,6 +63,9 @@ export const DEFAULT_LLM_CONFIG: UserModelProviderConfig = {
enabled: false,
enabledModels: filterEnabledModels(DeepSeekProviderCard),
},
doubao: {
enabled: false,
},
fireworksai: {
enabled: false,
enabledModels: filterEnabledModels(FireworksAIProviderCard),
7 changes: 7 additions & 0 deletions src/libs/agent-runtime/AgentRuntime.ts
Original file line number Diff line number Diff line change
@@ -10,6 +10,7 @@ import { LobeAzureOpenAI } from './azureOpenai';
import { LobeBaichuanAI } from './baichuan';
import { LobeBedrockAI, LobeBedrockAIParams } from './bedrock';
import { LobeDeepSeekAI } from './deepseek';
import { LobeDoubaoAI } from './doubao';
import { LobeFireworksAI } from './fireworksai';
import { LobeGithubAI } from './github';
import { LobeGoogleAI } from './google';
@@ -132,6 +133,7 @@ class AgentRuntime {
baichuan: Partial<ClientOptions>;
bedrock: Partial<LobeBedrockAIParams>;
deepseek: Partial<ClientOptions>;
doubao: Partial<ClientOptions>;
fireworksai: Partial<ClientOptions>;
github: Partial<ClientOptions>;
google: { apiKey?: string; baseURL?: string };
@@ -321,6 +323,11 @@ class AgentRuntime {
runtimeModel = await LobeSenseNovaAI.fromAPIKey(params.sensenova);
break;
}

case ModelProvider.Doubao: {
runtimeModel = new LobeDoubaoAI(params.doubao ?? {});
break;
}
}

return new AgentRuntime(runtimeModel);
10 changes: 10 additions & 0 deletions src/libs/agent-runtime/doubao/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
import { ModelProvider } from '../types';
import { LobeOpenAICompatibleFactory } from '../utils/openaiCompatibleFactory';

export const LobeDoubaoAI = LobeOpenAICompatibleFactory({
baseURL: 'https://ark.cn-beijing.volces.com/api/v3',
debug: {
chatCompletion: () => process.env.DEBUG_DOUBAO_CHAT_COMPLETION === '1',
},
provider: ModelProvider.Doubao,
});
1 change: 1 addition & 0 deletions src/libs/agent-runtime/types/type.ts
Original file line number Diff line number Diff line change
@@ -29,6 +29,7 @@ export enum ModelProvider {
Baichuan = 'baichuan',
Bedrock = 'bedrock',
DeepSeek = 'deepseek',
Doubao = 'doubao',
FireworksAI = 'fireworksai',
Github = 'github',
Google = 'google',
11 changes: 11 additions & 0 deletions src/server/globalConfig/index.ts
Original file line number Diff line number Diff line change
@@ -143,6 +143,9 @@ export const getServerGlobalConfig = () => {

ENABLED_HUGGINGFACE,
HUGGINGFACE_MODEL_LIST,

ENABLED_DOUBAO,
DOUBAO_MODEL_LIST,
} = getLLMConfig();

const config: GlobalServerConfig = {
@@ -210,6 +213,14 @@ export const getServerGlobalConfig = () => {
modelString: DEEPSEEK_MODEL_LIST,
}),
},
doubao: { enabled: ENABLED_DOUBAO,
enabledModels: extractEnabledModels(DOUBAO_MODEL_LIST, true),
serverModelCards: transformToChatModelCards({
defaultChatModels: [],
modelString: DOUBAO_MODEL_LIST,
withDeploymentName: true,
}),
},
fireworksai: {
enabled: ENABLED_FIREWORKSAI,
enabledModels: extractEnabledModels(FIREWORKSAI_MODEL_LIST),
7 changes: 7 additions & 0 deletions src/server/modules/AgentRuntime/index.ts
Original file line number Diff line number Diff line change
@@ -271,6 +271,13 @@ const getLlmOptionsFromPayload = (provider: string, payload: JWTPayload) => {

const apiKey = sensenovaAccessKeyID + ':' + sensenovaAccessKeySecret;

return { apiKey };
}
case ModelProvider.Doubao: {
const { DOUBAO_API_KEY } = getLLMConfig();

const apiKey = apiKeyManager.pick(payload?.apiKey || DOUBAO_API_KEY);

return { apiKey };
}
}
1 change: 1 addition & 0 deletions src/types/user/settings/keyVaults.ts
Original file line number Diff line number Diff line change
@@ -34,6 +34,7 @@ export interface UserKeyVaults {
baichuan?: OpenAICompatibleKeyVault;
bedrock?: AWSBedrockKeyVault;
deepseek?: OpenAICompatibleKeyVault;
doubao?: OpenAICompatibleKeyVault;
fireworksai?: OpenAICompatibleKeyVault;
github?: OpenAICompatibleKeyVault;
google?: OpenAICompatibleKeyVault;