From f30c6a4348fb25fead1d1ba4f4ff6717a45496fb Mon Sep 17 00:00:00 2001 From: suruiqiang Date: Fri, 7 Feb 2025 16:14:19 +0800 Subject: [PATCH 1/7] fix doubao and grok not upload image --- app/client/platforms/bytedance.ts | 11 ++++++----- app/client/platforms/xai.ts | 4 ++-- 2 files changed, 8 insertions(+), 7 deletions(-) diff --git a/app/client/platforms/bytedance.ts b/app/client/platforms/bytedance.ts index a2f0660d828..c2f128128fe 100644 --- a/app/client/platforms/bytedance.ts +++ b/app/client/platforms/bytedance.ts @@ -22,7 +22,7 @@ import { } from "@fortaine/fetch-event-source"; import { prettyObject } from "@/app/utils/format"; import { getClientConfig } from "@/app/config/client"; -import { getMessageTextContent } from "@/app/utils"; +import { preProcessImageContent } from "@/app/utils/chat"; import { fetch } from "@/app/utils/stream"; export interface OpenAIListModelResponse { @@ -84,10 +84,11 @@ export class DoubaoApi implements LLMApi { } async chat(options: ChatOptions) { - const messages = options.messages.map((v) => ({ - role: v.role, - content: getMessageTextContent(v), - })); + const messages: ChatOptions["messages"] = []; + for (const v of options.messages) { + const content = await preProcessImageContent(v.content); + messages.push({ role: v.role, content }); + } const modelConfig = { ...useAppConfig.getState().modelConfig, diff --git a/app/client/platforms/xai.ts b/app/client/platforms/xai.ts index 06dbaaa29ff..8c41c2d988f 100644 --- a/app/client/platforms/xai.ts +++ b/app/client/platforms/xai.ts @@ -17,7 +17,7 @@ import { SpeechOptions, } from "../api"; import { getClientConfig } from "@/app/config/client"; -import { getMessageTextContent } from "@/app/utils"; +import { preProcessImageContent } from "@/app/utils/chat"; import { RequestPayload } from "./openai"; import { fetch } from "@/app/utils/stream"; @@ -62,7 +62,7 @@ export class XAIApi implements LLMApi { async chat(options: ChatOptions) { const messages: ChatOptions["messages"] = []; for (const v of options.messages) { - const content = getMessageTextContent(v); + const content = await preProcessImageContent(v.content); messages.push({ role: v.role, content }); } From f156430cc5f9451618b13e6432148d1d0dd35c5c Mon Sep 17 00:00:00 2001 From: suruiqiang Date: Fri, 7 Feb 2025 16:18:15 +0800 Subject: [PATCH 2/7] fix emoji issue for doubao and glm's congview & congvideox --- app/components/emoji.tsx | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/app/components/emoji.tsx b/app/components/emoji.tsx index 6686d87310d..6cefe349757 100644 --- a/app/components/emoji.tsx +++ b/app/components/emoji.tsx @@ -80,9 +80,13 @@ export function Avatar(props: { model?: ModelType; avatar?: string }) { LlmIcon = BotIconGrok; } else if (modelName.startsWith("hunyuan")) { LlmIcon = BotIconHunyuan; - } else if (modelName.startsWith("doubao")) { + } else if (modelName.startsWith("doubao") || modelName.startsWith("ep-")) { LlmIcon = BotIconDoubao; - } else if (modelName.startsWith("glm")) { + } else if ( + modelName.startsWith("glm") || + modelName.startsWith("cogview-") || + modelName.startsWith("cogvideox-") + ) { LlmIcon = BotIconChatglm; } From 3fe55b4f7ff1791cf6e8c5d9da02b69a240e98a8 Mon Sep 17 00:00:00 2001 From: suruiqiang Date: Fri, 7 Feb 2025 16:20:07 +0800 Subject: [PATCH 3/7] fix bug that gemini has multiple candidates part --- app/client/platforms/google.ts | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/app/client/platforms/google.ts b/app/client/platforms/google.ts index 5ca8e1071a7..22c89b13f33 100644 --- a/app/client/platforms/google.ts +++ b/app/client/platforms/google.ts @@ -69,9 +69,16 @@ export class GeminiProApi implements LLMApi { .join("\n\n"); }; + let content = ""; + if (Array.isArray(res)) { + res.map((item) => { + content += getTextFromParts(item?.candidates?.at(0)?.content?.parts); + }); + } + return ( getTextFromParts(res?.candidates?.at(0)?.content?.parts) || - getTextFromParts(res?.at(0)?.candidates?.at(0)?.content?.parts) || + content || //getTextFromParts(res?.at(0)?.candidates?.at(0)?.content?.parts) || res?.error?.message || "" ); From a5a976824591a7e2c228dbb257616b98fd7a53ed Mon Sep 17 00:00:00 2001 From: suruiqiang Date: Fri, 7 Feb 2025 16:34:14 +0800 Subject: [PATCH 4/7] change request timeout for thinking mode --- app/client/platforms/deepseek.ts | 7 ++++++- app/client/platforms/google.ts | 10 ++++++++-- app/client/platforms/openai.ts | 9 +++++++-- app/constant.ts | 1 + 4 files changed, 22 insertions(+), 5 deletions(-) diff --git a/app/client/platforms/deepseek.ts b/app/client/platforms/deepseek.ts index 2bf3b2338ea..c436ae61d01 100644 --- a/app/client/platforms/deepseek.ts +++ b/app/client/platforms/deepseek.ts @@ -5,6 +5,7 @@ import { DEEPSEEK_BASE_URL, DeepSeek, REQUEST_TIMEOUT_MS, + REQUEST_TIMEOUT_MS_FOR_THINKING, } from "@/app/constant"; import { useAccessStore, @@ -117,10 +118,14 @@ export class DeepSeekApi implements LLMApi { // console.log(chatPayload); + const isR1 = + options.config.model.endsWith("-reasoner") || + options.config.model.endsWith("-r1"); + // make a fetch request const requestTimeoutId = setTimeout( () => controller.abort(), - REQUEST_TIMEOUT_MS, + isR1 ? REQUEST_TIMEOUT_MS_FOR_THINKING : REQUEST_TIMEOUT_MS, ); if (shouldStream) { diff --git a/app/client/platforms/google.ts b/app/client/platforms/google.ts index 22c89b13f33..1e593dd4257 100644 --- a/app/client/platforms/google.ts +++ b/app/client/platforms/google.ts @@ -1,4 +1,9 @@ -import { ApiPath, Google, REQUEST_TIMEOUT_MS } from "@/app/constant"; +import { + ApiPath, + Google, + REQUEST_TIMEOUT_MS, + REQUEST_TIMEOUT_MS_FOR_THINKING, +} from "@/app/constant"; import { ChatOptions, getHeaders, @@ -197,10 +202,11 @@ export class GeminiProApi implements LLMApi { headers: getHeaders(), }; + const isThinking = options.config.model.includes("-thinking"); // make a fetch request const requestTimeoutId = setTimeout( () => controller.abort(), - REQUEST_TIMEOUT_MS, + isThinking ? REQUEST_TIMEOUT_MS_FOR_THINKING : REQUEST_TIMEOUT_MS, ); if (shouldStream) { diff --git a/app/client/platforms/openai.ts b/app/client/platforms/openai.ts index 467bb82e0ac..fbe533cadab 100644 --- a/app/client/platforms/openai.ts +++ b/app/client/platforms/openai.ts @@ -8,6 +8,7 @@ import { Azure, REQUEST_TIMEOUT_MS, ServiceProvider, + REQUEST_TIMEOUT_MS_FOR_THINKING, } from "@/app/constant"; import { ChatMessageTool, @@ -195,7 +196,9 @@ export class ChatGPTApi implements LLMApi { let requestPayload: RequestPayload | DalleRequestPayload; const isDalle3 = _isDalle3(options.config.model); - const isO1OrO3 = options.config.model.startsWith("o1") || options.config.model.startsWith("o3"); + const isO1OrO3 = + options.config.model.startsWith("o1") || + options.config.model.startsWith("o3"); if (isDalle3) { const prompt = getMessageTextContent( options.messages.slice(-1)?.pop() as any, @@ -359,7 +362,9 @@ export class ChatGPTApi implements LLMApi { // make a fetch request const requestTimeoutId = setTimeout( () => controller.abort(), - isDalle3 || isO1OrO3 ? REQUEST_TIMEOUT_MS * 4 : REQUEST_TIMEOUT_MS, // dalle3 using b64_json is slow. + isDalle3 || isO1OrO3 + ? REQUEST_TIMEOUT_MS_FOR_THINKING + : REQUEST_TIMEOUT_MS, // dalle3 using b64_json is slow. ); const res = await fetch(chatPath, chatPayload); diff --git a/app/constant.ts b/app/constant.ts index 32e5a22632a..64aa734f4d4 100644 --- a/app/constant.ts +++ b/app/constant.ts @@ -110,6 +110,7 @@ export const UNFINISHED_INPUT = (id: string) => "unfinished-input-" + id; export const STORAGE_KEY = "chatgpt-next-web"; export const REQUEST_TIMEOUT_MS = 60000; +export const REQUEST_TIMEOUT_MS_FOR_THINKING = REQUEST_TIMEOUT_MS * 5; export const EXPORT_MESSAGE_CLASS_NAME = "export-markdown"; From c4e9cb03a92751b37ec0b9615ef5ec056fa20bde Mon Sep 17 00:00:00 2001 From: itsevin <2720269770@qq.com> Date: Fri, 7 Feb 2025 20:29:21 +0800 Subject: [PATCH 5/7] Add Xai model --- app/constant.ts | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/app/constant.ts b/app/constant.ts index 32e5a22632a..e04152d0f85 100644 --- a/app/constant.ts +++ b/app/constant.ts @@ -585,7 +585,16 @@ const iflytekModels = [ const deepseekModels = ["deepseek-chat", "deepseek-coder", "deepseek-reasoner"]; -const xAIModes = ["grok-beta"]; +const xAIModes = [ + "grok-beta", + "grok-2", + "grok-2-1212", + "grok-2-latest", + "grok-vision-beta", + "grok-2-vision-1212", + "grok-2-vision", + "grok-2-vision-latest", +]; const chatglmModels = [ "glm-4-plus", From 1ae5fdbf013349a2c32e6083b41500cbf2c4000d Mon Sep 17 00:00:00 2001 From: suruiqiang Date: Sat, 8 Feb 2025 16:15:10 +0800 Subject: [PATCH 6/7] mini optimizations --- app/client/platforms/siliconflow.ts | 4 ++-- app/components/emoji.tsx | 2 ++ 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/app/client/platforms/siliconflow.ts b/app/client/platforms/siliconflow.ts index fe2f9862b27..d6d51fe9395 100644 --- a/app/client/platforms/siliconflow.ts +++ b/app/client/platforms/siliconflow.ts @@ -4,7 +4,7 @@ import { ApiPath, SILICONFLOW_BASE_URL, SiliconFlow, - REQUEST_TIMEOUT_MS, + REQUEST_TIMEOUT_MS_FOR_THINKING, } from "@/app/constant"; import { useAccessStore, @@ -123,7 +123,7 @@ export class SiliconflowApi implements LLMApi { // make a fetch request const requestTimeoutId = setTimeout( () => controller.abort(), - REQUEST_TIMEOUT_MS, + REQUEST_TIMEOUT_MS_FOR_THINKING, ); if (shouldStream) { diff --git a/app/components/emoji.tsx b/app/components/emoji.tsx index 6cefe349757..ecb1c65819e 100644 --- a/app/components/emoji.tsx +++ b/app/components/emoji.tsx @@ -54,6 +54,8 @@ export function Avatar(props: { model?: ModelType; avatar?: string }) { if ( modelName.startsWith("gpt") || modelName.startsWith("chatgpt") || + modelName.startsWith("dall-e") || + modelName.startsWith("dalle") || modelName.startsWith("o1") || modelName.startsWith("o3") ) { From 2842b264e06b08de9cfdcb84982ee6571fa45881 Mon Sep 17 00:00:00 2001 From: RiverRay Date: Sun, 9 Feb 2025 11:05:32 +0800 Subject: [PATCH 7/7] Update LICENSE --- LICENSE | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/LICENSE b/LICENSE index 047f9431e7d..4864ab00d2c 100644 --- a/LICENSE +++ b/LICENSE @@ -1,6 +1,6 @@ MIT License -Copyright (c) 2023-2024 Zhang Yifei +Copyright (c) 2023-2025 NextChat Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal