diff --git a/src/app/api/chat/[provider]/route.ts b/src/app/api/chat/[provider]/route.ts index 3f0fe7bd3499..7a2e72cc7cef 100644 --- a/src/app/api/chat/[provider]/route.ts +++ b/src/app/api/chat/[provider]/route.ts @@ -1,4 +1,3 @@ -import { getPreferredRegion } from '@/app/api/config'; import { createErrorResponse } from '@/app/api/errorResponse'; import { AgentRuntime, ChatCompletionErrorPayload } from '@/libs/agent-runtime'; import { ChatErrorType } from '@/types/fetch'; @@ -10,8 +9,6 @@ import { createTraceOptions, initAgentRuntimeWithUserPayload } from '../agentRun export const runtime = 'edge'; -export const preferredRegion = getPreferredRegion(); - export const POST = checkAuth(async (req: Request, { params, jwtPayload, createRuntime }) => { const { provider } = params; diff --git a/src/app/api/chat/models/[provider]/route.ts b/src/app/api/chat/models/[provider]/route.ts index 9b292238d4b1..6dc845a535d5 100644 --- a/src/app/api/chat/models/[provider]/route.ts +++ b/src/app/api/chat/models/[provider]/route.ts @@ -1,6 +1,5 @@ import { NextResponse } from 'next/server'; -import { getPreferredRegion } from '@/app/api/config'; import { createErrorResponse } from '@/app/api/errorResponse'; import { ChatCompletionErrorPayload, ModelProvider } from '@/libs/agent-runtime'; import { ChatErrorType } from '@/types/fetch'; @@ -10,8 +9,6 @@ import { initAgentRuntimeWithUserPayload } from '../../agentRuntime'; export const runtime = 'edge'; -export const preferredRegion = getPreferredRegion(); - const noNeedAPIKey = (provider: string) => [ModelProvider.OpenRouter, ModelProvider.TogetherAI].includes(provider as any); diff --git a/src/app/api/chat/openai/route.test.ts b/src/app/api/chat/openai/route.test.ts new file mode 100644 index 000000000000..7e8e9b956270 --- /dev/null +++ b/src/app/api/chat/openai/route.test.ts @@ -0,0 +1,28 @@ +// @vitest-environment edge-runtime +import { describe, expect, it, vi } from 'vitest'; + +import { POST as UniverseRoute } from '../[provider]/route'; +import { POST, preferredRegion, runtime } from './route'; + +// 模拟 '../[provider]/route' +vi.mock('../[provider]/route', () => ({ + POST: vi.fn().mockResolvedValue('mocked response'), +})); + +describe('Configuration tests', () => { + it('should have runtime set to "edge"', () => { + expect(runtime).toBe('edge'); + }); + + it('should contain specific regions in preferredRegion', () => { + expect(preferredRegion).not.contain(['hkg1']); + }); +}); + +describe('OpenAI POST function tests', () => { + it('should call UniverseRoute with correct parameters', async () => { + const mockRequest = new Request('https://example.com', { method: 'POST' }); + await POST(mockRequest); + expect(UniverseRoute).toHaveBeenCalledWith(mockRequest, { params: { provider: 'openai' } }); + }); +}); diff --git a/src/app/api/chat/openai/route.ts b/src/app/api/chat/openai/route.ts new file mode 100644 index 000000000000..489bac2ce858 --- /dev/null +++ b/src/app/api/chat/openai/route.ts @@ -0,0 +1,25 @@ +import { POST as UniverseRoute } from '../[provider]/route'; + +export const runtime = 'edge'; + +export const preferredRegion = [ + 'arn1', + 'bom1', + 'cdg1', + 'cle1', + 'cpt1', + 'dub1', + 'fra1', + 'gru1', + 'hnd1', + 'iad1', + 'icn1', + 'kix1', + 'lhr1', + 'pdx1', + 'sfo1', + 'sin1', + 'syd1', +]; + +export const POST = async (req: Request) => UniverseRoute(req, { params: { provider: 'openai' } }); diff --git a/src/app/api/config.test.ts b/src/app/api/config.test.ts deleted file mode 100644 index 54723bd86988..000000000000 --- a/src/app/api/config.test.ts +++ /dev/null @@ -1,43 +0,0 @@ -// @vitest-environment node -import { describe, expect, it, vi } from 'vitest'; - -import { getPreferredRegion } from './config'; - -// Stub the global process object to safely mock environment variables -vi.stubGlobal('process', { - ...process, // Preserve the original process object - env: { ...process.env }, // Clone the environment variables object for modification -}); - -describe('getPreferredRegion', () => { - beforeEach(() => { - // Reset environment variables before each test case - vi.restoreAllMocks(); - }); - - it('returns default value when get config error', () => { - const originalProcess = global.process; - const originalError = console.error; - // @ts-ignore - global.process = undefined; - console.error = () => {}; - - const preferredRegion = getPreferredRegion(); - expect(preferredRegion).toBe('auto'); - - global.process = originalProcess; - console.error = originalError; - }); - - it('return default value when preferredRegion is empty', () => { - process.env.OPENAI_FUNCTION_REGIONS = ''; - const preferredRegion = getPreferredRegion(); - expect(preferredRegion).toBe('auto'); - }); - - it('return correct list values when preferredRegion is correctly passed', () => { - process.env.OPENAI_FUNCTION_REGIONS = 'ida1,sfo1'; - const preferredRegion = getPreferredRegion(); - expect(preferredRegion).toStrictEqual(['ida1', 'sfo1']); - }); -}); diff --git a/src/app/api/config.ts b/src/app/api/config.ts deleted file mode 100644 index e49583048131..000000000000 --- a/src/app/api/config.ts +++ /dev/null @@ -1,14 +0,0 @@ -import { getLLMConfig } from '@/config/llm'; - -export const getPreferredRegion = (region: string | string[] = 'auto') => { - try { - if (getLLMConfig().OPENAI_FUNCTION_REGIONS.length <= 0) { - return region; - } - - return getLLMConfig().OPENAI_FUNCTION_REGIONS; - } catch (error) { - console.error('get server config failed, error:', error); - return region; - } -}; diff --git a/src/app/api/openai/stt/route.ts b/src/app/api/openai/stt/route.ts index 95cd32afc39a..10af58df37a3 100644 --- a/src/app/api/openai/stt/route.ts +++ b/src/app/api/openai/stt/route.ts @@ -1,11 +1,29 @@ import { OpenAISTTPayload } from '@lobehub/tts'; import { createOpenaiAudioTranscriptions } from '@lobehub/tts/server'; -import { getPreferredRegion } from '../../config'; -import { createBizOpenAI } from '../createBizOpenAI'; +import { createBizOpenAI } from '@/app/api/openai/createBizOpenAI'; export const runtime = 'edge'; -export const preferredRegion = getPreferredRegion(); + +export const preferredRegion = [ + 'arn1', + 'bom1', + 'cdg1', + 'cle1', + 'cpt1', + 'dub1', + 'fra1', + 'gru1', + 'hnd1', + 'iad1', + 'icn1', + 'kix1', + 'lhr1', + 'pdx1', + 'sfo1', + 'sin1', + 'syd1', +]; export const POST = async (req: Request) => { const formData = await req.formData(); diff --git a/src/app/api/openai/tts/route.ts b/src/app/api/openai/tts/route.ts index 04a88d2cb6b5..f263c8c65d2d 100644 --- a/src/app/api/openai/tts/route.ts +++ b/src/app/api/openai/tts/route.ts @@ -1,11 +1,29 @@ import { OpenAITTSPayload } from '@lobehub/tts'; import { createOpenaiAudioSpeech } from '@lobehub/tts/server'; -import { getPreferredRegion } from '../../config'; -import { createBizOpenAI } from '../createBizOpenAI'; +import { createBizOpenAI } from '@/app/api/openai/createBizOpenAI'; export const runtime = 'edge'; -export const preferredRegion = getPreferredRegion(); + +export const preferredRegion = [ + 'arn1', + 'bom1', + 'cdg1', + 'cle1', + 'cpt1', + 'dub1', + 'fra1', + 'gru1', + 'hnd1', + 'iad1', + 'icn1', + 'kix1', + 'lhr1', + 'pdx1', + 'sfo1', + 'sin1', + 'syd1', +]; export const POST = async (req: Request) => { const payload = (await req.json()) as OpenAITTSPayload; diff --git a/src/app/api/text-to-image/[provider]/route.ts b/src/app/api/text-to-image/[provider]/route.ts index 12749c9de182..5106731e8775 100644 --- a/src/app/api/text-to-image/[provider]/route.ts +++ b/src/app/api/text-to-image/[provider]/route.ts @@ -1,17 +1,33 @@ import { NextResponse } from 'next/server'; -import { getPreferredRegion } from '@/app/api/config'; +import { initAgentRuntimeWithUserPayload } from '@/app/api/chat/agentRuntime'; import { createErrorResponse } from '@/app/api/errorResponse'; +import { checkAuth } from '@/app/api/middleware/auth'; import { ChatCompletionErrorPayload } from '@/libs/agent-runtime'; import { TextToImagePayload } from '@/libs/agent-runtime/types'; import { ChatErrorType } from '@/types/fetch'; -import { initAgentRuntimeWithUserPayload } from '../../chat/agentRuntime'; -import { checkAuth } from '../../middleware/auth'; - export const runtime = 'edge'; -export const preferredRegion = getPreferredRegion(); +export const preferredRegion = [ + 'arn1', + 'bom1', + 'cdg1', + 'cle1', + 'cpt1', + 'dub1', + 'fra1', + 'gru1', + 'hnd1', + 'iad1', + 'icn1', + 'kix1', + 'lhr1', + 'pdx1', + 'sfo1', + 'sin1', + 'syd1', +]; // return NextResponse.json( // { diff --git a/src/config/llm.ts b/src/config/llm.ts index 1cbc948b766b..0a226be16777 100644 --- a/src/config/llm.ts +++ b/src/config/llm.ts @@ -3,12 +3,6 @@ import { createEnv } from '@t3-oss/env-nextjs'; import { z } from 'zod'; export const getLLMConfig = () => { - // region format: iad1,sfo1 - let regions: string[] = []; - if (process.env.OPENAI_FUNCTION_REGIONS) { - regions = process.env.OPENAI_FUNCTION_REGIONS.split(','); - } - return createEnv({ server: { API_KEY_SELECT_MODE: z.string().optional(), @@ -17,7 +11,6 @@ export const getLLMConfig = () => { OPENAI_API_KEY: z.string().optional(), OPENAI_PROXY_URL: z.string().optional(), OPENAI_MODEL_LIST: z.string().optional(), - OPENAI_FUNCTION_REGIONS: z.array(z.string()), ENABLED_AZURE_OPENAI: z.boolean(), AZURE_API_KEY: z.string().optional(), @@ -99,7 +92,6 @@ export const getLLMConfig = () => { OPENAI_API_KEY: process.env.OPENAI_API_KEY, OPENAI_PROXY_URL: process.env.OPENAI_PROXY_URL, OPENAI_MODEL_LIST: process.env.OPENAI_MODEL_LIST, - OPENAI_FUNCTION_REGIONS: regions as any, ENABLED_AZURE_OPENAI: !!process.env.AZURE_API_KEY, AZURE_API_KEY: process.env.AZURE_API_KEY, diff --git a/src/features/Conversation/Messages/Tool/Inspector/style.ts b/src/features/Conversation/Messages/Tool/Inspector/style.ts index 9fccf9c8dcb6..e6ea71da1da6 100644 --- a/src/features/Conversation/Messages/Tool/Inspector/style.ts +++ b/src/features/Conversation/Messages/Tool/Inspector/style.ts @@ -5,10 +5,11 @@ export const useStyles = createStyles(({ css, token }) => ({ overflow: hidden; display: -webkit-box; -webkit-box-orient: vertical; - -webkit-line-clamp: 1; font-size: 12px; text-overflow: ellipsis; + + -webkit-line-clamp: 1; `, container: css` cursor: pointer;