no message
This commit is contained in:
parent
07d209d1fe
commit
e57728b1c5
@ -260,12 +260,6 @@ pm2 monit # 监控面板
|
|||||||
yarn dev #端口60000
|
yarn dev #端口60000
|
||||||
```
|
```
|
||||||
|
|
||||||
- 使用 Bun 快速运行开发服务:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
yarn bun:dev #端口60000
|
|
||||||
```
|
|
||||||
|
|
||||||
4. **项目打包**
|
4. **项目打包**
|
||||||
|
|
||||||
- 编译并生成 TypeScript 文件:
|
- 编译并生成 TypeScript 文件:
|
||||||
|
|||||||
@ -22,13 +22,19 @@
|
|||||||
"license": "bun run scripts/license.ts"
|
"license": "bun run scripts/license.ts"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
|
"@ai-sdk/anthropic": "^3.0.35",
|
||||||
|
"@ai-sdk/deepseek": "^2.0.17",
|
||||||
|
"@ai-sdk/google": "^3.0.20",
|
||||||
|
"@ai-sdk/openai": "^3.0.25",
|
||||||
"@aigne/core": "^1.72.0",
|
"@aigne/core": "^1.72.0",
|
||||||
"@aigne/openai": "^0.16.16",
|
"@aigne/openai": "^0.16.16",
|
||||||
"@langchain/core": "^1.1.15",
|
"@langchain/core": "^1.1.15",
|
||||||
"@langchain/openai": "^1.2.1",
|
"@langchain/openai": "^1.2.1",
|
||||||
"@rmp135/sql-ts": "^2.2.0",
|
"@rmp135/sql-ts": "^2.2.0",
|
||||||
|
"ai": "^6.0.67",
|
||||||
"axios": "^1.13.2",
|
"axios": "^1.13.2",
|
||||||
"axios-retry": "^4.5.0",
|
"axios-retry": "^4.5.0",
|
||||||
|
"best-effort-json-parser": "^1.2.1",
|
||||||
"better-sqlite3": "^12.6.2",
|
"better-sqlite3": "^12.6.2",
|
||||||
"cors": "^2.8.5",
|
"cors": "^2.8.5",
|
||||||
"dotenv": "^17.2.3",
|
"dotenv": "^17.2.3",
|
||||||
@ -42,8 +48,10 @@
|
|||||||
"knex": "^3.1.0",
|
"knex": "^3.1.0",
|
||||||
"langchain": "^1.2.10",
|
"langchain": "^1.2.10",
|
||||||
"morgan": "^1.10.1",
|
"morgan": "^1.10.1",
|
||||||
|
"qwen-ai-provider": "^0.1.1",
|
||||||
"sharp": "^0.34.5",
|
"sharp": "^0.34.5",
|
||||||
"sqlite3": "^5.1.7",
|
"sqlite3": "^5.1.7",
|
||||||
|
"zhipu-ai-provider": "^0.2.2",
|
||||||
"zod": "^4.3.5"
|
"zod": "^4.3.5"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
|
|||||||
@ -115,19 +115,91 @@ async function mergeImages(imagePaths: string[]): Promise<Buffer> {
|
|||||||
return compressImage(mergedImage);
|
return compressImage(mergedImage);
|
||||||
}
|
}
|
||||||
|
|
||||||
// 处理图片列表,确保不超过10张且每张不超过3MB
|
// 进一步压缩单张图片到指定大小
|
||||||
|
async function compressToSize(buffer: Buffer, targetSize: number): Promise<Buffer> {
|
||||||
|
if (buffer.length <= targetSize) {
|
||||||
|
return buffer;
|
||||||
|
}
|
||||||
|
|
||||||
|
const metadata = await sharp(buffer).metadata();
|
||||||
|
let quality = 80;
|
||||||
|
let scale = 1.0;
|
||||||
|
let compressedBuffer = buffer;
|
||||||
|
|
||||||
|
// 先尝试降低质量
|
||||||
|
while (compressedBuffer.length > targetSize && quality > 10) {
|
||||||
|
compressedBuffer = await sharp(buffer).jpeg({ quality }).toBuffer();
|
||||||
|
quality -= 10;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 如果还是太大,缩小尺寸
|
||||||
|
while (compressedBuffer.length > targetSize && scale > 0.2) {
|
||||||
|
scale -= 0.1;
|
||||||
|
const newWidth = Math.round((metadata.width || 1000) * scale);
|
||||||
|
const newHeight = Math.round((metadata.height || 1000) * scale);
|
||||||
|
compressedBuffer = await sharp(buffer)
|
||||||
|
.resize(newWidth, newHeight, { fit: "inside" })
|
||||||
|
.jpeg({ quality: Math.max(quality, 20) })
|
||||||
|
.toBuffer();
|
||||||
|
}
|
||||||
|
|
||||||
|
return compressedBuffer;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 确保图片列表总大小不超过指定限制
|
||||||
|
async function ensureTotalSizeLimit(buffers: Buffer[], maxTotalBytes: number = 10 * 1024 * 1024): Promise<Buffer[]> {
|
||||||
|
let totalSize = buffers.reduce((sum, buf) => sum + buf.length, 0);
|
||||||
|
|
||||||
|
if (totalSize <= maxTotalBytes) {
|
||||||
|
return buffers;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 计算每张图片的平均目标大小
|
||||||
|
const avgTargetSize = Math.floor(maxTotalBytes / buffers.length);
|
||||||
|
|
||||||
|
// 按大小降序排列,优先压缩大图片
|
||||||
|
const indexedBuffers = buffers.map((buf, idx) => ({ buf, idx, size: buf.length }));
|
||||||
|
indexedBuffers.sort((a, b) => b.size - a.size);
|
||||||
|
|
||||||
|
const result = [...buffers];
|
||||||
|
|
||||||
|
for (const item of indexedBuffers) {
|
||||||
|
totalSize = result.reduce((sum, buf) => sum + buf.length, 0);
|
||||||
|
if (totalSize <= maxTotalBytes) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 计算这张图片需要压缩到的目标大小
|
||||||
|
const excessSize = totalSize - maxTotalBytes;
|
||||||
|
const targetSize = Math.max(item.buf.length - excessSize, avgTargetSize, 100 * 1024); // 最小100KB
|
||||||
|
|
||||||
|
if (item.buf.length > targetSize) {
|
||||||
|
result[item.idx] = await compressToSize(item.buf, targetSize);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 处理图片列表,确保不超过10张且每张不超过3MB,总大小不超过10MB
|
||||||
async function processImages(images: ImageInfo[]): Promise<Buffer[]> {
|
async function processImages(images: ImageInfo[]): Promise<Buffer[]> {
|
||||||
const maxImages = 10;
|
const maxImages = 10;
|
||||||
|
let processedBuffers: Buffer[];
|
||||||
|
|
||||||
if (images.length <= maxImages) {
|
if (images.length <= maxImages) {
|
||||||
const buffers = await Promise.all(images.map((img) => u.oss.getFile(img.filePath)));
|
const buffers = await Promise.all(images.map((img) => u.oss.getFile(img.filePath)));
|
||||||
return Promise.all(buffers.map((buffer) => compressImage(buffer)));
|
processedBuffers = await Promise.all(buffers.map((buffer) => compressImage(buffer)));
|
||||||
|
} else {
|
||||||
|
const mergeStartIndex = maxImages - 1;
|
||||||
|
const firstBuffers = await Promise.all(images.slice(0, mergeStartIndex).map((img) => u.oss.getFile(img.filePath)));
|
||||||
|
const compressedFirstImages = await Promise.all(firstBuffers.map((buffer) => compressImage(buffer)));
|
||||||
|
const imagesToMergeList = images.slice(mergeStartIndex).map((img) => img.filePath);
|
||||||
|
const mergedImage = await mergeImages(imagesToMergeList);
|
||||||
|
processedBuffers = [...compressedFirstImages, mergedImage];
|
||||||
}
|
}
|
||||||
const mergeStartIndex = maxImages - 1;
|
|
||||||
const firstBuffers = await Promise.all(images.slice(0, mergeStartIndex).map((img) => u.oss.getFile(img.filePath)));
|
// 确保总大小不超过10MB
|
||||||
const compressedFirstImages = await Promise.all(firstBuffers.map((buffer) => compressImage(buffer)));
|
return ensureTotalSizeLimit(processedBuffers);
|
||||||
const imagesToMergeList = images.slice(mergeStartIndex).map((img) => img.filePath);
|
|
||||||
const mergedImage = await mergeImages(imagesToMergeList);
|
|
||||||
return [...compressedFirstImages, mergedImage];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 使用 AI 过滤与分镜相关的资产
|
// 使用 AI 过滤与分镜相关的资产
|
||||||
|
|||||||
@ -1,13 +1,17 @@
|
|||||||
import { Knex } from "knex";
|
import { Knex } from "knex";
|
||||||
|
|
||||||
export default async (knex: Knex): Promise<void> => {
|
export default async (knex: Knex): Promise<void> => {
|
||||||
const hasTime = await knex.schema.hasColumn("t_video", "time");
|
const videoHasTime = await knex.schema.hasColumn("t_video", "time");
|
||||||
if (!hasTime) {
|
if (!videoHasTime) {
|
||||||
await knex.schema.alterTable("t_video", (table) => {
|
await knex.schema.alterTable("t_video", (table) => {
|
||||||
table.integer("time");
|
table.integer("time");
|
||||||
});
|
});
|
||||||
console.log("字段 'time' 已添加到 t_video 表");
|
}
|
||||||
} else {
|
|
||||||
console.log("t_video 表已存在 'time' 字段");
|
const configHasIndex = await knex.schema.hasColumn("t_config", "index");
|
||||||
|
if (configHasIndex) {
|
||||||
|
await knex.schema.alterTable("t_config", (table) => {
|
||||||
|
table.dropColumn("index");
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@ -1,12 +1,14 @@
|
|||||||
import express from "express";
|
import express from "express";
|
||||||
import { success, error } from "@/lib/responseFormat";
|
import { success, error } from "@/lib/responseFormat";
|
||||||
import { createAgent } from "langchain";
|
|
||||||
import { openAI } from "@/agents/models";
|
|
||||||
import { OpenAIChatModel, type OpenAIChatModelOptions } from "@aigne/openai";
|
|
||||||
import { validateFields } from "@/middleware/middleware";
|
import { validateFields } from "@/middleware/middleware";
|
||||||
|
import u from "@/utils";
|
||||||
import { z } from "zod";
|
import { z } from "zod";
|
||||||
|
import { generateText, Output, tool, stepCountIs } from "ai";
|
||||||
const router = express.Router();
|
const router = express.Router();
|
||||||
|
|
||||||
|
import { createOpenAI } from "@ai-sdk/openai";
|
||||||
|
import { createDeepSeek } from "@ai-sdk/deepseek";
|
||||||
|
|
||||||
// 检查语言模型
|
// 检查语言模型
|
||||||
export default router.post(
|
export default router.post(
|
||||||
"/",
|
"/",
|
||||||
@ -17,24 +19,42 @@ export default router.post(
|
|||||||
}),
|
}),
|
||||||
async (req, res) => {
|
async (req, res) => {
|
||||||
const { modelName, apiKey, baseURL } = req.body;
|
const { modelName, apiKey, baseURL } = req.body;
|
||||||
const ai = new OpenAIChatModel({
|
|
||||||
apiKey: apiKey,
|
const getWeatherTool = tool({
|
||||||
baseURL: baseURL,
|
// strict: true,
|
||||||
model: modelName,
|
description: "Get the weather in a location",
|
||||||
modelOptions: { temperature: 0.7 },
|
inputSchema: z.object({
|
||||||
|
location: z.string().describe("The location to get the weather for"),
|
||||||
|
}),
|
||||||
|
execute: async ({ location }) => {
|
||||||
|
return {
|
||||||
|
location,
|
||||||
|
temperature: 72 + Math.floor(Math.random() * 21) - 10,
|
||||||
|
};
|
||||||
|
},
|
||||||
});
|
});
|
||||||
try {
|
try {
|
||||||
const data = await ai.invoke({
|
const { reply } = await u.ai.text.invoke(
|
||||||
messages: [
|
{
|
||||||
{
|
prompt: "请调用工具获取北京的天气,并回答我多少气温",
|
||||||
role: "user",
|
tools: { getWeatherTool },
|
||||||
content: "hello",
|
output: {
|
||||||
|
reply: z.string().describe("回复内容"),
|
||||||
},
|
},
|
||||||
],
|
},
|
||||||
});
|
{
|
||||||
res.status(200).send(success(data));
|
model: modelName,
|
||||||
} catch (err: any) {
|
apiKey,
|
||||||
res.status(500).send(error(err.error.message || "模型调用失败"));
|
baseURL,
|
||||||
|
},
|
||||||
|
);
|
||||||
|
console.log("%c Line:52 🍐 reply", "background:#ffdd4d", reply);
|
||||||
|
res.status(200).send(success(reply));
|
||||||
|
} catch (err) {
|
||||||
|
console.log(err);
|
||||||
|
if (typeof err === "string") return res.status(500).send(error(err));
|
||||||
|
const msg = err instanceof Error ? err.message : (err as any)?.error?.message;
|
||||||
|
return res.status(500).send(error(msg || "未知错误"));
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|||||||
@ -1,9 +1,6 @@
|
|||||||
import express from "express";
|
import express from "express";
|
||||||
import { success, error } from "@/lib/responseFormat";
|
import { success, error } from "@/lib/responseFormat";
|
||||||
import u from "@/utils";
|
import u from "@/utils";
|
||||||
import { createAgent } from "langchain";
|
|
||||||
import { openAI } from "@/agents/models";
|
|
||||||
import { OpenAIChatModel, type OpenAIChatModelOptions } from "@aigne/openai";
|
|
||||||
import { validateFields } from "@/middleware/middleware";
|
import { validateFields } from "@/middleware/middleware";
|
||||||
import { z } from "zod";
|
import { z } from "zod";
|
||||||
const router = express.Router();
|
const router = express.Router();
|
||||||
|
|||||||
@ -15,7 +15,7 @@ export default router.post(
|
|||||||
|
|
||||||
const settingData = await u.db("t_setting").select("*");
|
const settingData = await u.db("t_setting").select("*");
|
||||||
|
|
||||||
const configData = await u.db("t_config").where("userId", userId).select("*").orderBy("index", "asc");
|
const configData = await u.db("t_config").where("userId", userId).select("*") ;
|
||||||
|
|
||||||
const parsedData = settingData.map((item) => ({
|
const parsedData = settingData.map((item) => ({
|
||||||
...item,
|
...item,
|
||||||
|
|||||||
@ -1,16 +1,20 @@
|
|||||||
import db from "@/utils/db";
|
import db from "@/utils/db";
|
||||||
import oss from "@/utils/oss";
|
import oss from "@/utils/oss";
|
||||||
import * as ai from "@/utils/ai";
|
// import * as ai from "@/utils/ai";
|
||||||
import editImage from "@/utils/editImage";
|
import editImage from "@/utils/editImage";
|
||||||
import number2Chinese from "@/utils/number2Chinese";
|
import number2Chinese from "@/utils/number2Chinese";
|
||||||
import deleteOutline from "@/utils/deleteOutline";
|
import deleteOutline from "@/utils/deleteOutline";
|
||||||
import getConfig from "./utils/getConfig";
|
import getConfig from "./utils/getConfig";
|
||||||
import { v4 as uuid } from "uuid";
|
import { v4 as uuid } from "uuid";
|
||||||
|
|
||||||
|
import AIText from "@/utils/ai/text";
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
db,
|
db,
|
||||||
oss,
|
oss,
|
||||||
ai,
|
ai: {
|
||||||
|
text: AIText,
|
||||||
|
},
|
||||||
editImage,
|
editImage,
|
||||||
number2Chinese,
|
number2Chinese,
|
||||||
deleteOutline,
|
deleteOutline,
|
||||||
|
|||||||
414
src/utils/ai/modelList.ts
Normal file
414
src/utils/ai/modelList.ts
Normal file
@ -0,0 +1,414 @@
|
|||||||
|
import { createOpenAI } from "@ai-sdk/openai";
|
||||||
|
import { createDeepSeek } from "@ai-sdk/deepseek";
|
||||||
|
import { createZhipu } from "zhipu-ai-provider";
|
||||||
|
import { createQwen } from "qwen-ai-provider";
|
||||||
|
import { createGoogleGenerativeAI } from "@ai-sdk/google";
|
||||||
|
import { createAnthropic } from "@ai-sdk/anthropic";
|
||||||
|
|
||||||
|
interface Owned {
|
||||||
|
manufacturer: string;
|
||||||
|
model: string;
|
||||||
|
responseFormat: "schema" | "object";
|
||||||
|
image: boolean;
|
||||||
|
think: boolean;
|
||||||
|
tool: boolean;
|
||||||
|
instance:
|
||||||
|
| typeof createOpenAI
|
||||||
|
| typeof createDeepSeek
|
||||||
|
| typeof createZhipu
|
||||||
|
| typeof createQwen
|
||||||
|
| typeof createGoogleGenerativeAI
|
||||||
|
| typeof createAnthropic;
|
||||||
|
}
|
||||||
|
|
||||||
|
const modelList: Owned[] = [
|
||||||
|
// DeepSeek
|
||||||
|
{
|
||||||
|
manufacturer: "deepseek",
|
||||||
|
model: "deepseek-chat",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createDeepSeek,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "deepseek",
|
||||||
|
model: "deepseek-reasoner",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: false,
|
||||||
|
think: true,
|
||||||
|
instance: createDeepSeek,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
|
||||||
|
// 豆包
|
||||||
|
{
|
||||||
|
manufacturer: "doubao",
|
||||||
|
model: "doubao-seed-1-8",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: true,
|
||||||
|
instance: createOpenAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "doubao",
|
||||||
|
model: "doubao-seed-1-6",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: true,
|
||||||
|
instance: createOpenAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "doubao",
|
||||||
|
model: "doubao-seed-1-6-lite",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: true,
|
||||||
|
instance: createOpenAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "doubao",
|
||||||
|
model: "doubao-seed-1-6-flash",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: true,
|
||||||
|
instance: createOpenAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
// GLM
|
||||||
|
{
|
||||||
|
manufacturer: "zhipu",
|
||||||
|
model: "glm-4.7",
|
||||||
|
responseFormat: "object",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createZhipu,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "zhipu",
|
||||||
|
model: "glm-4.7-flashx",
|
||||||
|
responseFormat: "object",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createZhipu,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "zhipu",
|
||||||
|
model: "glm-4.6",
|
||||||
|
responseFormat: "object",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createZhipu,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "zhipu",
|
||||||
|
model: "glm-4.5-air",
|
||||||
|
responseFormat: "object",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createZhipu,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "zhipu",
|
||||||
|
model: "glm-4.5-airx",
|
||||||
|
responseFormat: "object",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createZhipu,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "zhipu",
|
||||||
|
model: "glm-4-long",
|
||||||
|
responseFormat: "object",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createZhipu,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "zhipu",
|
||||||
|
model: "glm-4-flashx-250414",
|
||||||
|
responseFormat: "object",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createZhipu,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "zhipu",
|
||||||
|
model: "glm-4.7-flash",
|
||||||
|
responseFormat: "object",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createZhipu,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "zhipu",
|
||||||
|
model: "glm-4.5-flash",
|
||||||
|
responseFormat: "object",
|
||||||
|
image: false,
|
||||||
|
think: true,
|
||||||
|
instance: createZhipu,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "zhipu",
|
||||||
|
model: "glm-4-flash-250414",
|
||||||
|
responseFormat: "object",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createZhipu,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "zhipu",
|
||||||
|
model: "glm-4.6v",
|
||||||
|
responseFormat: "object",
|
||||||
|
image: true,
|
||||||
|
think: true,
|
||||||
|
instance: createZhipu,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
// Qwen
|
||||||
|
{
|
||||||
|
manufacturer: "qwen",
|
||||||
|
model: "qwen-vl-max",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createQwen,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "qwen",
|
||||||
|
model: "qwen-plus-latest",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createQwen,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "qwen",
|
||||||
|
model: "qwen-max",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createQwen,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "qwen",
|
||||||
|
model: "qwen2.5-72b-instruct",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createQwen,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "qwen",
|
||||||
|
model: "qwen2.5-14b-instruct-1m",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: false,
|
||||||
|
think: false,
|
||||||
|
instance: createQwen,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "qwen",
|
||||||
|
model: "qwen2.5-vl-72b-instruct",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createQwen,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
// OpenAI
|
||||||
|
{
|
||||||
|
manufacturer: "openai",
|
||||||
|
model: "gpt-4o",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createOpenAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "openai",
|
||||||
|
model: "gpt-4o-mini",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createOpenAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "openai",
|
||||||
|
model: "gpt-4.1",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createOpenAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "openai",
|
||||||
|
model: "gpt-5.1",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createOpenAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "openai",
|
||||||
|
model: "gpt-5.2",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createOpenAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
|
||||||
|
// Gemini
|
||||||
|
{
|
||||||
|
manufacturer: "google",
|
||||||
|
model: "gemini-2.5-pro",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: true,
|
||||||
|
instance: createGoogleGenerativeAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "google",
|
||||||
|
model: "gemini-2.5-flash",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: true,
|
||||||
|
instance: createGoogleGenerativeAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "google",
|
||||||
|
model: "gemini-2.0-flash",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createGoogleGenerativeAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "google",
|
||||||
|
model: "gemini-2.0-flash-lite",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createGoogleGenerativeAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "google",
|
||||||
|
model: "gemini-1.5-pro",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createGoogleGenerativeAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "google",
|
||||||
|
model: "gemini-1.5-flash",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createGoogleGenerativeAI,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
// Anthropic (Claude)
|
||||||
|
{
|
||||||
|
manufacturer: "anthropic",
|
||||||
|
model: "claude-opus-4-5",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createAnthropic,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "anthropic",
|
||||||
|
model: "claude-haiku-4-5",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createAnthropic,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "anthropic",
|
||||||
|
model: "claude-sonnet-4-5",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createAnthropic,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "anthropic",
|
||||||
|
model: "claude-opus-4-1",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createAnthropic,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "anthropic",
|
||||||
|
model: "claude-opus-4-0",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createAnthropic,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "anthropic",
|
||||||
|
model: "claude-sonnet-4-0",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createAnthropic,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "anthropic",
|
||||||
|
model: "claude-3-7-sonnet-latest",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createAnthropic,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
manufacturer: "anthropic",
|
||||||
|
model: "claude-3-5-haiku-latest",
|
||||||
|
responseFormat: "schema",
|
||||||
|
image: true,
|
||||||
|
think: false,
|
||||||
|
instance: createAnthropic,
|
||||||
|
tool: true,
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
export default modelList;
|
||||||
88
src/utils/ai/text.ts
Normal file
88
src/utils/ai/text.ts
Normal file
@ -0,0 +1,88 @@
|
|||||||
|
import u from "@/utils";
|
||||||
|
import { generateText, streamText, Output, stepCountIs, ModelMessage, LanguageModel, Tool, GenerateTextResult } from "ai";
|
||||||
|
import { parse } from "best-effort-json-parser";
|
||||||
|
import modelList from "./modelList";
|
||||||
|
import { z } from "zod";
|
||||||
|
|
||||||
|
interface AIInput<T extends Record<string, z.ZodTypeAny> | undefined = undefined> {
|
||||||
|
system?: string;
|
||||||
|
tools?: Record<string, Tool>;
|
||||||
|
maxStep?: number;
|
||||||
|
output?: T;
|
||||||
|
prompt?: string;
|
||||||
|
messages?: Array<ModelMessage>;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface AIConfig {
|
||||||
|
model?: string;
|
||||||
|
apiKey?: string;
|
||||||
|
baseURL?: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
const buildOptions = async (input: AIInput<any>, config: AIConfig) => {
|
||||||
|
const sqlTextModelConfig = await u.getConfig("text");
|
||||||
|
const { model, apiKey, baseURL } = { ...sqlTextModelConfig, ...config };
|
||||||
|
|
||||||
|
const owned = modelList.find((m) => m.model === model);
|
||||||
|
if (!owned) throw new Error("不支持的模型或厂商");
|
||||||
|
|
||||||
|
const modelInstance = owned.instance({ apiKey, baseURL });
|
||||||
|
|
||||||
|
const maxStep = input.maxStep ?? (input.tools ? Object.keys(input.tools).length * 5 : undefined);
|
||||||
|
const outputBuilders: Record<string, (schema: any) => any> = {
|
||||||
|
schema: (s) => Output.object({ schema: z.object(s) }),
|
||||||
|
object: () => {
|
||||||
|
const jsonSchemaPrompt = `\n请按照以下 JSON Schema 格式返回结果:\n${JSON.stringify(
|
||||||
|
z.toJSONSchema(z.object(input.output)),
|
||||||
|
null,
|
||||||
|
2,
|
||||||
|
)}\n只返回结果,不要将Schema返回。`;
|
||||||
|
input.system = (input.system ?? "") + jsonSchemaPrompt;
|
||||||
|
// return Output.json();
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
const output = input.output ? outputBuilders[owned.responseFormat]?.(input.output) ?? null : null;
|
||||||
|
|
||||||
|
return {
|
||||||
|
config: {
|
||||||
|
model: modelInstance(model) as LanguageModel,
|
||||||
|
...(input.system && { system: input.system }),
|
||||||
|
...(input.prompt ? { prompt: input.prompt } : { messages: input.messages! }),
|
||||||
|
...(input.tools && owned.tool && { tools: input.tools }),
|
||||||
|
...(maxStep && { stopWhen: stepCountIs(maxStep) }),
|
||||||
|
...(output && { output }),
|
||||||
|
},
|
||||||
|
responseFormat: owned.responseFormat,
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
type InferOutput<T> = T extends Record<string, z.ZodTypeAny> ? z.infer<z.ZodObject<T>> : GenerateTextResult<Record<string, Tool>, never>;
|
||||||
|
|
||||||
|
const ai = Object.create({}) as {
|
||||||
|
invoke<T extends Record<string, z.ZodTypeAny> | undefined = undefined>(input: AIInput<T>, config?: AIConfig): Promise<InferOutput<T>>;
|
||||||
|
stream(input: AIInput, config?: AIConfig): Promise<ReturnType<typeof streamText>>;
|
||||||
|
};
|
||||||
|
|
||||||
|
ai.invoke = async (input: AIInput<any>, config: AIConfig = {}) => {
|
||||||
|
const options = await buildOptions(input, config);
|
||||||
|
const result = await generateText(options.config);
|
||||||
|
if (options.responseFormat === "object" && input.output) {
|
||||||
|
const pattern = /{[^{}]*}|{(?:[^{}]*|{[^{}]*})*}/g;
|
||||||
|
const jsonLikeTexts = Array.from(result.text.matchAll(pattern), (m) => m[0]);
|
||||||
|
|
||||||
|
const res = jsonLikeTexts.map((jsonText) => parse(jsonText));
|
||||||
|
return res[0];
|
||||||
|
}
|
||||||
|
if (options.responseFormat === "schema" && input.output) {
|
||||||
|
return JSON.parse(result.text);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
};
|
||||||
|
|
||||||
|
ai.stream = async (input: AIInput, config: AIConfig = {}) => {
|
||||||
|
const options = await buildOptions(input, config);
|
||||||
|
return streamText(options.config);
|
||||||
|
};
|
||||||
|
|
||||||
|
export default ai;
|
||||||
43
src/utils/getConfig copy.ts
Normal file
43
src/utils/getConfig copy.ts
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
import u from "@/utils";
|
||||||
|
|
||||||
|
// 只包含 t_setting 表里实际存在的字段
|
||||||
|
const modelFields = {
|
||||||
|
image: "imageModel",
|
||||||
|
language: "languageModel",
|
||||||
|
} as const;
|
||||||
|
|
||||||
|
interface resData {
|
||||||
|
model: string;
|
||||||
|
apiKey: string;
|
||||||
|
baseURL: string;
|
||||||
|
manufacturer: "openAi" | "volcengine" | "runninghub" | "gemini" | "apimart";
|
||||||
|
}
|
||||||
|
|
||||||
|
type ModelType = keyof typeof modelFields;
|
||||||
|
|
||||||
|
// 定义返回类型映射
|
||||||
|
type ReturnType<T extends string> = T extends "video" ? resData[] : resData;
|
||||||
|
|
||||||
|
// 主方法
|
||||||
|
export default async function getConfig<T extends ModelType | "video">(type: T, manufacturer?: string): Promise<ReturnType<T>> {
|
||||||
|
if (type === "video") {
|
||||||
|
// 查询 t_config 表,返回数组
|
||||||
|
const configList = await u.db("t_config").where("manufacturer", manufacturer).orderBy("index", "asc");
|
||||||
|
|
||||||
|
return configList.map((i) => {
|
||||||
|
return {
|
||||||
|
...i,
|
||||||
|
baseURL: i.baseUrl,
|
||||||
|
};
|
||||||
|
}) as ReturnType<T>;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 只查询当前需要的字段
|
||||||
|
const modelName = modelFields[type as ModelType];
|
||||||
|
const data: Record<string, any> | undefined = await u.db("t_setting").where({ id: 1 }).select([modelName]).first();
|
||||||
|
|
||||||
|
if (!data) throw new Error("设置数据不存在");
|
||||||
|
|
||||||
|
// 字段值为 JSON 字符串,解析
|
||||||
|
return JSON.parse(data[modelName] || "{}") as ReturnType<T>;
|
||||||
|
}
|
||||||
@ -1,44 +1,55 @@
|
|||||||
import u from "@/utils";
|
import u from "@/utils";
|
||||||
|
|
||||||
// 只包含 t_setting 表里实际存在的字段
|
type AIType = "text" | "image" | "video";
|
||||||
const modelFields = {
|
|
||||||
image: "imageModel",
|
|
||||||
language: "languageModel",
|
|
||||||
doubao: "doubaoModel",
|
|
||||||
} as const;
|
|
||||||
|
|
||||||
interface resData {
|
interface BaseConfig {
|
||||||
model: string;
|
model: string;
|
||||||
apiKey: string;
|
apiKey: string;
|
||||||
baseURL: string;
|
manufacturer: string;
|
||||||
manufacturer: "openAi" | "volcengine" | "runninghub" | "gemini" | "apimart";
|
|
||||||
}
|
}
|
||||||
|
|
||||||
type ModelType = keyof typeof modelFields;
|
interface TextResData extends BaseConfig {
|
||||||
|
baseURL: string;
|
||||||
|
manufacturer: "deepseek" | "openAi" | "doubao";
|
||||||
|
}
|
||||||
|
|
||||||
// 定义返回类型映射
|
interface ImageResData extends BaseConfig {
|
||||||
type ReturnType<T extends string> = T extends "video" ? resData[] : resData;
|
manufacturer: "openAi" | "gemini" | "volcengine" | "runninghub" | "apimart";
|
||||||
|
}
|
||||||
|
|
||||||
// 主方法
|
interface VideoResData extends BaseConfig {
|
||||||
export default async function getConfig<T extends ModelType | "video">(type: T, manufacturer?: string): Promise<ReturnType<T>> {
|
baseURL: string;
|
||||||
if (type === "video") {
|
manufacturer: "openAi" | "volcengine" | "runninghub" | "apimart" | "confyUI";
|
||||||
// 查询 t_config 表,返回数组
|
}
|
||||||
const configList = await u.db("t_config").where("manufacturer", manufacturer).orderBy("index", "asc");
|
|
||||||
|
|
||||||
return configList.map((i) => {
|
type ResDataMap = {
|
||||||
return {
|
text: TextResData;
|
||||||
...i,
|
image: ImageResData;
|
||||||
baseURL: i.baseUrl,
|
video: VideoResData;
|
||||||
};
|
};
|
||||||
}) as ReturnType<T>;
|
|
||||||
|
const errorMessages: Record<AIType, string> = {
|
||||||
|
text: "文本模型配置不存在",
|
||||||
|
image: "图像模型配置不存在",
|
||||||
|
video: "视频模型配置不存在",
|
||||||
|
};
|
||||||
|
|
||||||
|
const needBaseURL: AIType[] = ["text", "video"];
|
||||||
|
|
||||||
|
export default async function getConfig<T extends AIType>(aiType: T): Promise<ResDataMap[T]> {
|
||||||
|
const config = await u.db("t_config").where("type", aiType).first();
|
||||||
|
|
||||||
|
if (!config) throw new Error(errorMessages[aiType]);
|
||||||
|
|
||||||
|
const result: BaseConfig = {
|
||||||
|
model: config?.model ?? "",
|
||||||
|
apiKey: config?.apiKey ?? "",
|
||||||
|
manufacturer: config?.manufacturer ?? "",
|
||||||
|
};
|
||||||
|
|
||||||
|
if (needBaseURL.includes(aiType)) {
|
||||||
|
return { ...result, baseURL: config.baseUrl } as ResDataMap[T];
|
||||||
}
|
}
|
||||||
|
|
||||||
// 只查询当前需要的字段
|
return result as ResDataMap[T];
|
||||||
const modelName = modelFields[type as ModelType];
|
|
||||||
const data: Record<string, any> | undefined = await u.db("t_setting").where({ id: 1 }).select([modelName]).first();
|
|
||||||
|
|
||||||
if (!data) throw new Error("设置数据不存在");
|
|
||||||
|
|
||||||
// 字段值为 JSON 字符串,解析
|
|
||||||
return JSON.parse(data[modelName] || "{}") as ReturnType<T>;
|
|
||||||
}
|
}
|
||||||
|
|||||||
144
yarn.lock
144
yarn.lock
@ -7,6 +7,95 @@
|
|||||||
resolved "https://registry.npmmirror.com/7zip-bin/-/7zip-bin-5.2.0.tgz#7a03314684dd6572b7dfa89e68ce31d60286854d"
|
resolved "https://registry.npmmirror.com/7zip-bin/-/7zip-bin-5.2.0.tgz#7a03314684dd6572b7dfa89e68ce31d60286854d"
|
||||||
integrity sha512-ukTPVhqG4jNzMro2qA9HSCSSVJN3aN7tlb+hfqYCt3ER0yWroeA2VR38MNrOHLQ/cVj+DaIMad0kFCtWWowh/A==
|
integrity sha512-ukTPVhqG4jNzMro2qA9HSCSSVJN3aN7tlb+hfqYCt3ER0yWroeA2VR38MNrOHLQ/cVj+DaIMad0kFCtWWowh/A==
|
||||||
|
|
||||||
|
"@ai-sdk/anthropic@^3.0.35":
|
||||||
|
version "3.0.35"
|
||||||
|
resolved "https://registry.npmmirror.com/@ai-sdk/anthropic/-/anthropic-3.0.35.tgz#334bf3f5415ebab77cf23d52f197b8027087821e"
|
||||||
|
integrity sha512-Y3g/5uVj621XSB9lGF7WrD7qR+orhV5xpaYkRF8kfj2j4W7e7BBGIvxcdsCf85FjJbc6tKQdNTZ84ZEqT3Y5TQ==
|
||||||
|
dependencies:
|
||||||
|
"@ai-sdk/provider" "3.0.7"
|
||||||
|
"@ai-sdk/provider-utils" "4.0.13"
|
||||||
|
|
||||||
|
"@ai-sdk/deepseek@^2.0.17":
|
||||||
|
version "2.0.17"
|
||||||
|
resolved "https://registry.npmmirror.com/@ai-sdk/deepseek/-/deepseek-2.0.17.tgz#14a8460d141d36fda08040074b887b2fab06948e"
|
||||||
|
integrity sha512-rkZiasQ24UyOMiZd8Mb7R+OF3Yt90bRQyfyzIkrb0zKZj7kU2h2z2nu1CO6j0X8poE+SZhEEaHOBFhRcp6hKVg==
|
||||||
|
dependencies:
|
||||||
|
"@ai-sdk/provider" "3.0.7"
|
||||||
|
"@ai-sdk/provider-utils" "4.0.13"
|
||||||
|
|
||||||
|
"@ai-sdk/gateway@3.0.32":
|
||||||
|
version "3.0.32"
|
||||||
|
resolved "https://registry.npmmirror.com/@ai-sdk/gateway/-/gateway-3.0.32.tgz#4738f75fc2eba7f245f77fd0dc139225a08c9c47"
|
||||||
|
integrity sha512-7clZRr07P9rpur39t1RrbIe7x8jmwnwUWI8tZs+BvAfX3NFgdSVGGIaT7bTz2pb08jmLXzTSDbrOTqAQ7uBkBQ==
|
||||||
|
dependencies:
|
||||||
|
"@ai-sdk/provider" "3.0.7"
|
||||||
|
"@ai-sdk/provider-utils" "4.0.13"
|
||||||
|
"@vercel/oidc" "3.1.0"
|
||||||
|
|
||||||
|
"@ai-sdk/google@^3.0.20":
|
||||||
|
version "3.0.20"
|
||||||
|
resolved "https://registry.npmmirror.com/@ai-sdk/google/-/google-3.0.20.tgz#608ec12a13371439a6a06992fb7e7d1d4d029432"
|
||||||
|
integrity sha512-bVGsulEr6JiipAFlclo9bjL5WaUV0iCSiiekLt+PY6pwmtJeuU2GaD9DoE3OqR8LN2W779mU13IhVEzlTupf8g==
|
||||||
|
dependencies:
|
||||||
|
"@ai-sdk/provider" "3.0.7"
|
||||||
|
"@ai-sdk/provider-utils" "4.0.13"
|
||||||
|
|
||||||
|
"@ai-sdk/openai@^3.0.25":
|
||||||
|
version "3.0.25"
|
||||||
|
resolved "https://registry.npmmirror.com/@ai-sdk/openai/-/openai-3.0.25.tgz#452c8f8ed597468048569ec9476a0b5641888d2a"
|
||||||
|
integrity sha512-DsaN46R98+D1W3lU3fKuPU3ofacboLaHlkAwxJPgJ8eup1AJHmPK1N1y10eJJbJcF6iby8Tf/vanoZxc9JPUfw==
|
||||||
|
dependencies:
|
||||||
|
"@ai-sdk/provider" "3.0.7"
|
||||||
|
"@ai-sdk/provider-utils" "4.0.13"
|
||||||
|
|
||||||
|
"@ai-sdk/provider-utils@4.0.13":
|
||||||
|
version "4.0.13"
|
||||||
|
resolved "https://registry.npmmirror.com/@ai-sdk/provider-utils/-/provider-utils-4.0.13.tgz#d2240b0c4d701eef8a4273ade71585a691e34e04"
|
||||||
|
integrity sha512-HHG72BN4d+OWTcq2NwTxOm/2qvk1duYsnhCDtsbYwn/h/4zeqURu1S0+Cn0nY2Ysq9a9HGKvrYuMn9bgFhR2Og==
|
||||||
|
dependencies:
|
||||||
|
"@ai-sdk/provider" "3.0.7"
|
||||||
|
"@standard-schema/spec" "^1.1.0"
|
||||||
|
eventsource-parser "^3.0.6"
|
||||||
|
|
||||||
|
"@ai-sdk/provider-utils@^2.1.6":
|
||||||
|
version "2.2.8"
|
||||||
|
resolved "https://registry.npmmirror.com/@ai-sdk/provider-utils/-/provider-utils-2.2.8.tgz#ad11b92d5a1763ab34ba7b5fc42494bfe08b76d1"
|
||||||
|
integrity sha512-fqhG+4sCVv8x7nFzYnFo19ryhAa3w096Kmc3hWxMQfW/TubPOmt3A6tYZhl4mUfQWWQMsuSkLrtjlWuXBVSGQA==
|
||||||
|
dependencies:
|
||||||
|
"@ai-sdk/provider" "1.1.3"
|
||||||
|
nanoid "^3.3.8"
|
||||||
|
secure-json-parse "^2.7.0"
|
||||||
|
|
||||||
|
"@ai-sdk/provider-utils@^3.0.0":
|
||||||
|
version "3.0.20"
|
||||||
|
resolved "https://registry.npmmirror.com/@ai-sdk/provider-utils/-/provider-utils-3.0.20.tgz#61d7741065550833eae3ac6440d943e9d3d25120"
|
||||||
|
integrity sha512-iXHVe0apM2zUEzauqJwqmpC37A5rihrStAih5Ks+JE32iTe4LZ58y17UGBjpQQTCRw9YxMeo2UFLxLpBluyvLQ==
|
||||||
|
dependencies:
|
||||||
|
"@ai-sdk/provider" "2.0.1"
|
||||||
|
"@standard-schema/spec" "^1.0.0"
|
||||||
|
eventsource-parser "^3.0.6"
|
||||||
|
|
||||||
|
"@ai-sdk/provider@1.1.3", "@ai-sdk/provider@^1.0.7":
|
||||||
|
version "1.1.3"
|
||||||
|
resolved "https://registry.npmmirror.com/@ai-sdk/provider/-/provider-1.1.3.tgz#ebdda8077b8d2b3f290dcba32c45ad19b2704681"
|
||||||
|
integrity sha512-qZMxYJ0qqX/RfnuIaab+zp8UAeJn/ygXXAffR5I4N0n1IrvA6qBsjc8hXLmBiMV2zoXlifkacF7sEFnYnjBcqg==
|
||||||
|
dependencies:
|
||||||
|
json-schema "^0.4.0"
|
||||||
|
|
||||||
|
"@ai-sdk/provider@2.0.1", "@ai-sdk/provider@^2.0.0":
|
||||||
|
version "2.0.1"
|
||||||
|
resolved "https://registry.npmmirror.com/@ai-sdk/provider/-/provider-2.0.1.tgz#4aba415f1815da33a7a81e5f41a0219af53278c0"
|
||||||
|
integrity sha512-KCUwswvsC5VsW2PWFqF8eJgSCu5Ysj7m1TxiHTVA6g7k360bk0RNQENT8KTMAYEs+8fWPD3Uu4dEmzGHc+jGng==
|
||||||
|
dependencies:
|
||||||
|
json-schema "^0.4.0"
|
||||||
|
|
||||||
|
"@ai-sdk/provider@3.0.7":
|
||||||
|
version "3.0.7"
|
||||||
|
resolved "https://registry.npmmirror.com/@ai-sdk/provider/-/provider-3.0.7.tgz#470bb8f9e46ec9d8d62b07b4c1f5737b991ebe83"
|
||||||
|
integrity sha512-VkPLrutM6VdA924/mG8OS+5frbVTcu6e046D2bgDo00tehBANR1QBJ/mPcZ9tXMFOsVcm6SQArOregxePzTFPw==
|
||||||
|
dependencies:
|
||||||
|
json-schema "^0.4.0"
|
||||||
|
|
||||||
"@aigne/afs-history@^1.2.0":
|
"@aigne/afs-history@^1.2.0":
|
||||||
version "1.2.0"
|
version "1.2.0"
|
||||||
resolved "https://registry.npmmirror.com/@aigne/afs-history/-/afs-history-1.2.0.tgz#42086667ee83f2bbe181b247d6987cd05793d96f"
|
resolved "https://registry.npmmirror.com/@aigne/afs-history/-/afs-history-1.2.0.tgz#42086667ee83f2bbe181b247d6987cd05793d96f"
|
||||||
@ -969,7 +1058,7 @@
|
|||||||
dependencies:
|
dependencies:
|
||||||
"@opentelemetry/api" "^1.3.0"
|
"@opentelemetry/api" "^1.3.0"
|
||||||
|
|
||||||
"@opentelemetry/api@^1.3.0", "@opentelemetry/api@^1.9.0":
|
"@opentelemetry/api@1.9.0", "@opentelemetry/api@^1.3.0", "@opentelemetry/api@^1.9.0":
|
||||||
version "1.9.0"
|
version "1.9.0"
|
||||||
resolved "https://registry.npmmirror.com/@opentelemetry/api/-/api-1.9.0.tgz#d03eba68273dc0f7509e2a3d5cba21eae10379fe"
|
resolved "https://registry.npmmirror.com/@opentelemetry/api/-/api-1.9.0.tgz#d03eba68273dc0f7509e2a3d5cba21eae10379fe"
|
||||||
integrity sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==
|
integrity sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==
|
||||||
@ -1348,7 +1437,7 @@
|
|||||||
resolved "https://registry.npmmirror.com/@sqlite.org/sqlite-wasm/-/sqlite-wasm-3.50.1-build1.tgz#67dd9944b0e37ddb0ef2c8b195baa74ece838e44"
|
resolved "https://registry.npmmirror.com/@sqlite.org/sqlite-wasm/-/sqlite-wasm-3.50.1-build1.tgz#67dd9944b0e37ddb0ef2c8b195baa74ece838e44"
|
||||||
integrity sha512-yH4M/SHN98NibniIwTVk6rwTJjy7n39l7zwWY3u+qsfZBGTi4lC1uEl2NDvIlkzsFtfCBvHBJJFJ1iuU3UzzEQ==
|
integrity sha512-yH4M/SHN98NibniIwTVk6rwTJjy7n39l7zwWY3u+qsfZBGTi4lC1uEl2NDvIlkzsFtfCBvHBJJFJ1iuU3UzzEQ==
|
||||||
|
|
||||||
"@standard-schema/spec@1.1.0":
|
"@standard-schema/spec@1.1.0", "@standard-schema/spec@^1.0.0", "@standard-schema/spec@^1.1.0":
|
||||||
version "1.1.0"
|
version "1.1.0"
|
||||||
resolved "https://registry.npmmirror.com/@standard-schema/spec/-/spec-1.1.0.tgz#a79b55dbaf8604812f52d140b2c9ab41bc150bb8"
|
resolved "https://registry.npmmirror.com/@standard-schema/spec/-/spec-1.1.0.tgz#a79b55dbaf8604812f52d140b2c9ab41bc150bb8"
|
||||||
integrity sha512-l2aFy5jALhniG5HgqrD6jXLi/rUWrKvqN/qJx6yoJsgKhblVd+iqqU4RCXavm/jPityDo5TCvKMnpjKnOriy0w==
|
integrity sha512-l2aFy5jALhniG5HgqrD6jXLi/rUWrKvqN/qJx6yoJsgKhblVd+iqqU4RCXavm/jPityDo5TCvKMnpjKnOriy0w==
|
||||||
@ -1574,6 +1663,11 @@
|
|||||||
resolved "https://registry.npmmirror.com/@ungap/with-resolvers/-/with-resolvers-0.1.0.tgz#63a07b13bbf10ffff074a36498cce8d82aeeecc4"
|
resolved "https://registry.npmmirror.com/@ungap/with-resolvers/-/with-resolvers-0.1.0.tgz#63a07b13bbf10ffff074a36498cce8d82aeeecc4"
|
||||||
integrity sha512-g7f0IkJdPW2xhY7H4iE72DAsIyfuwEFc6JWc2tYFwKDMWWAF699vGjrM348cwQuOXgHpe1gWFe+Eiyjx/ewvvw==
|
integrity sha512-g7f0IkJdPW2xhY7H4iE72DAsIyfuwEFc6JWc2tYFwKDMWWAF699vGjrM348cwQuOXgHpe1gWFe+Eiyjx/ewvvw==
|
||||||
|
|
||||||
|
"@vercel/oidc@3.1.0":
|
||||||
|
version "3.1.0"
|
||||||
|
resolved "https://registry.npmmirror.com/@vercel/oidc/-/oidc-3.1.0.tgz#066caee449b84079f33c7445fc862464fe10ec32"
|
||||||
|
integrity sha512-Fw28YZpRnA3cAHHDlkt7xQHiJ0fcL+NRcIqsocZQUSmbzeIKRpwttJjik5ZGanXP+vlA4SbTg+AbA3bP363l+w==
|
||||||
|
|
||||||
"@xmldom/xmldom@^0.8.8":
|
"@xmldom/xmldom@^0.8.8":
|
||||||
version "0.8.11"
|
version "0.8.11"
|
||||||
resolved "https://registry.npmmirror.com/@xmldom/xmldom/-/xmldom-0.8.11.tgz#b79de2d67389734c57c52595f7a7305e30c2d608"
|
resolved "https://registry.npmmirror.com/@xmldom/xmldom/-/xmldom-0.8.11.tgz#b79de2d67389734c57c52595f7a7305e30c2d608"
|
||||||
@ -1651,6 +1745,16 @@ aggregate-error@^3.0.0:
|
|||||||
clean-stack "^2.0.0"
|
clean-stack "^2.0.0"
|
||||||
indent-string "^4.0.0"
|
indent-string "^4.0.0"
|
||||||
|
|
||||||
|
ai@^6.0.67:
|
||||||
|
version "6.0.67"
|
||||||
|
resolved "https://registry.npmmirror.com/ai/-/ai-6.0.67.tgz#eb808301e0196915b9fe097ac7de47ce8131c2a9"
|
||||||
|
integrity sha512-xBnTcByHCj3OcG6V8G1s6zvSEqK0Bdiu+IEXYcpGrve1iGFFRgcrKeZtr/WAW/7gupnSvBbDF24BEv1OOfqi1g==
|
||||||
|
dependencies:
|
||||||
|
"@ai-sdk/gateway" "3.0.32"
|
||||||
|
"@ai-sdk/provider" "3.0.7"
|
||||||
|
"@ai-sdk/provider-utils" "4.0.13"
|
||||||
|
"@opentelemetry/api" "1.9.0"
|
||||||
|
|
||||||
ajv-formats@^3.0.1:
|
ajv-formats@^3.0.1:
|
||||||
version "3.0.1"
|
version "3.0.1"
|
||||||
resolved "https://registry.npmmirror.com/ajv-formats/-/ajv-formats-3.0.1.tgz#3d5dc762bca17679c3c2ea7e90ad6b7532309578"
|
resolved "https://registry.npmmirror.com/ajv-formats/-/ajv-formats-3.0.1.tgz#3d5dc762bca17679c3c2ea7e90ad6b7532309578"
|
||||||
@ -1911,6 +2015,11 @@ basic-auth@~2.0.1:
|
|||||||
dependencies:
|
dependencies:
|
||||||
safe-buffer "5.1.2"
|
safe-buffer "5.1.2"
|
||||||
|
|
||||||
|
best-effort-json-parser@^1.2.1:
|
||||||
|
version "1.2.1"
|
||||||
|
resolved "https://registry.npmmirror.com/best-effort-json-parser/-/best-effort-json-parser-1.2.1.tgz#e8d0b8355a0c268d918681faa0e3cf6aa192ea00"
|
||||||
|
integrity sha512-UICSLibQdzS1f+PBsi3u2YE3SsdXcWicHUg3IMvfuaePS2AYnZJdJeKhGv5OM8/mqJwPt79aDrEJ1oa84tELvw==
|
||||||
|
|
||||||
better-sqlite3@^12.6.2:
|
better-sqlite3@^12.6.2:
|
||||||
version "12.6.2"
|
version "12.6.2"
|
||||||
resolved "https://registry.npmmirror.com/better-sqlite3/-/better-sqlite3-12.6.2.tgz#770649f28a62e543a360f3dfa1afe4cc944b1937"
|
resolved "https://registry.npmmirror.com/better-sqlite3/-/better-sqlite3-12.6.2.tgz#770649f28a62e543a360f3dfa1afe4cc944b1937"
|
||||||
@ -3779,6 +3888,11 @@ json-schema-typed@^8.0.2:
|
|||||||
resolved "https://registry.npmmirror.com/json-schema-typed/-/json-schema-typed-8.0.2.tgz#e98ee7b1899ff4a184534d1f167c288c66bbeff4"
|
resolved "https://registry.npmmirror.com/json-schema-typed/-/json-schema-typed-8.0.2.tgz#e98ee7b1899ff4a184534d1f167c288c66bbeff4"
|
||||||
integrity sha512-fQhoXdcvc3V28x7C7BMs4P5+kNlgUURe2jmUT1T//oBRMDrqy1QPelJimwZGo7Hg9VPV3EQV5Bnq4hbFy2vetA==
|
integrity sha512-fQhoXdcvc3V28x7C7BMs4P5+kNlgUURe2jmUT1T//oBRMDrqy1QPelJimwZGo7Hg9VPV3EQV5Bnq4hbFy2vetA==
|
||||||
|
|
||||||
|
json-schema@^0.4.0:
|
||||||
|
version "0.4.0"
|
||||||
|
resolved "https://registry.npmmirror.com/json-schema/-/json-schema-0.4.0.tgz#f7de4cf6efab838ebaeb3236474cbba5a1930ab5"
|
||||||
|
integrity sha512-es94M3nTIfsEPisRafak+HDLfHXnKBhV3vU5eqPcS3flIWqcxJWgXHXiey3YrpaNsanY5ei1VoYEbOzijuq9BA==
|
||||||
|
|
||||||
json-stringify-safe@^5.0.1:
|
json-stringify-safe@^5.0.1:
|
||||||
version "5.0.1"
|
version "5.0.1"
|
||||||
resolved "https://registry.npmmirror.com/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz#1296a2d58fd45f19a0f6ce01d65701e2c735b6eb"
|
resolved "https://registry.npmmirror.com/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz#1296a2d58fd45f19a0f6ce01d65701e2c735b6eb"
|
||||||
@ -4327,6 +4441,11 @@ mute-stream@^2.0.0:
|
|||||||
resolved "https://registry.npmmirror.com/mute-stream/-/mute-stream-2.0.0.tgz#a5446fc0c512b71c83c44d908d5c7b7b4c493b2b"
|
resolved "https://registry.npmmirror.com/mute-stream/-/mute-stream-2.0.0.tgz#a5446fc0c512b71c83c44d908d5c7b7b4c493b2b"
|
||||||
integrity sha512-WWdIxpyjEn+FhQJQQv9aQAYlHoNVdzIzUySNV1gHUPDSdZJ3yZn7pAAbQcV7B56Mvu881q9FZV+0Vx2xC44VWA==
|
integrity sha512-WWdIxpyjEn+FhQJQQv9aQAYlHoNVdzIzUySNV1gHUPDSdZJ3yZn7pAAbQcV7B56Mvu881q9FZV+0Vx2xC44VWA==
|
||||||
|
|
||||||
|
nanoid@^3.3.8:
|
||||||
|
version "3.3.11"
|
||||||
|
resolved "https://registry.npmmirror.com/nanoid/-/nanoid-3.3.11.tgz#4f4f112cefbe303202f2199838128936266d185b"
|
||||||
|
integrity sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==
|
||||||
|
|
||||||
napi-build-utils@^2.0.0:
|
napi-build-utils@^2.0.0:
|
||||||
version "2.0.0"
|
version "2.0.0"
|
||||||
resolved "https://registry.npmmirror.com/napi-build-utils/-/napi-build-utils-2.0.0.tgz#13c22c0187fcfccce1461844136372a47ddc027e"
|
resolved "https://registry.npmmirror.com/napi-build-utils/-/napi-build-utils-2.0.0.tgz#13c22c0187fcfccce1461844136372a47ddc027e"
|
||||||
@ -4887,6 +5006,14 @@ quick-lru@^5.1.1:
|
|||||||
resolved "https://registry.npmmirror.com/quick-lru/-/quick-lru-5.1.1.tgz#366493e6b3e42a3a6885e2e99d18f80fb7a8c932"
|
resolved "https://registry.npmmirror.com/quick-lru/-/quick-lru-5.1.1.tgz#366493e6b3e42a3a6885e2e99d18f80fb7a8c932"
|
||||||
integrity sha512-WuyALRjWPDGtt/wzJiadO5AXY+8hZ80hVpe6MyivgraREW751X3SbhRvG3eLKOYN+8VEvqLcf3wdnt44Z4S4SA==
|
integrity sha512-WuyALRjWPDGtt/wzJiadO5AXY+8hZ80hVpe6MyivgraREW751X3SbhRvG3eLKOYN+8VEvqLcf3wdnt44Z4S4SA==
|
||||||
|
|
||||||
|
qwen-ai-provider@^0.1.1:
|
||||||
|
version "0.1.1"
|
||||||
|
resolved "https://registry.npmmirror.com/qwen-ai-provider/-/qwen-ai-provider-0.1.1.tgz#f854379514eed919fe01de20007f6238a8ad2b41"
|
||||||
|
integrity sha512-7dVu97U7fbOGgCYdaOunC4NQqC+7Or3/Gsbx+P16+Ny4VxST7WJxfUCogQl6D2EDxIJdHGz4akHm+5fyEulmyw==
|
||||||
|
dependencies:
|
||||||
|
"@ai-sdk/provider" "^1.0.7"
|
||||||
|
"@ai-sdk/provider-utils" "^2.1.6"
|
||||||
|
|
||||||
radix3@^1.1.2:
|
radix3@^1.1.2:
|
||||||
version "1.1.2"
|
version "1.1.2"
|
||||||
resolved "https://registry.npmmirror.com/radix3/-/radix3-1.1.2.tgz#fd27d2af3896c6bf4bcdfab6427c69c2afc69ec0"
|
resolved "https://registry.npmmirror.com/radix3/-/radix3-1.1.2.tgz#fd27d2af3896c6bf4bcdfab6427c69c2afc69ec0"
|
||||||
@ -5161,6 +5288,11 @@ sax@^1.2.4:
|
|||||||
resolved "https://registry.npmmirror.com/sax/-/sax-1.4.4.tgz#f29c2bba80ce5b86f4343b4c2be9f2b96627cf8b"
|
resolved "https://registry.npmmirror.com/sax/-/sax-1.4.4.tgz#f29c2bba80ce5b86f4343b4c2be9f2b96627cf8b"
|
||||||
integrity sha512-1n3r/tGXO6b6VXMdFT54SHzT9ytu9yr7TaELowdYpMqY/Ao7EnlQGmAQ1+RatX7Tkkdm6hONI2owqNx2aZj5Sw==
|
integrity sha512-1n3r/tGXO6b6VXMdFT54SHzT9ytu9yr7TaELowdYpMqY/Ao7EnlQGmAQ1+RatX7Tkkdm6hONI2owqNx2aZj5Sw==
|
||||||
|
|
||||||
|
secure-json-parse@^2.7.0:
|
||||||
|
version "2.7.0"
|
||||||
|
resolved "https://registry.npmmirror.com/secure-json-parse/-/secure-json-parse-2.7.0.tgz#5a5f9cd6ae47df23dba3151edd06855d47e09862"
|
||||||
|
integrity sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==
|
||||||
|
|
||||||
semver-compare@^1.0.0:
|
semver-compare@^1.0.0:
|
||||||
version "1.0.0"
|
version "1.0.0"
|
||||||
resolved "https://registry.npmmirror.com/semver-compare/-/semver-compare-1.0.0.tgz#0dee216a1c941ab37e9efb1788f6afc5ff5537fc"
|
resolved "https://registry.npmmirror.com/semver-compare/-/semver-compare-1.0.0.tgz#0dee216a1c941ab37e9efb1788f6afc5ff5537fc"
|
||||||
@ -6106,6 +6238,14 @@ yoctocolors-cjs@^2.1.3:
|
|||||||
resolved "https://registry.npmmirror.com/yoctocolors-cjs/-/yoctocolors-cjs-2.1.3.tgz#7e4964ea8ec422b7a40ac917d3a344cfd2304baa"
|
resolved "https://registry.npmmirror.com/yoctocolors-cjs/-/yoctocolors-cjs-2.1.3.tgz#7e4964ea8ec422b7a40ac917d3a344cfd2304baa"
|
||||||
integrity sha512-U/PBtDf35ff0D8X8D0jfdzHYEPFxAI7jJlxZXwCSez5M3190m+QobIfh+sWDWSHMCWWJN2AWamkegn6vr6YBTw==
|
integrity sha512-U/PBtDf35ff0D8X8D0jfdzHYEPFxAI7jJlxZXwCSez5M3190m+QobIfh+sWDWSHMCWWJN2AWamkegn6vr6YBTw==
|
||||||
|
|
||||||
|
zhipu-ai-provider@^0.2.2:
|
||||||
|
version "0.2.2"
|
||||||
|
resolved "https://registry.npmmirror.com/zhipu-ai-provider/-/zhipu-ai-provider-0.2.2.tgz#cbee428475b1c2fca446f273ac09006ef86f6f00"
|
||||||
|
integrity sha512-UjX1ho4DI9ICUv/mrpAnzmrRe5/LXrGkS5hF6h4WDY2aup5GketWWopFzWYCqsbArXAM5wbzzdH9QzZusgGiBg==
|
||||||
|
dependencies:
|
||||||
|
"@ai-sdk/provider" "^2.0.0"
|
||||||
|
"@ai-sdk/provider-utils" "^3.0.0"
|
||||||
|
|
||||||
zip-stream@^6.0.1:
|
zip-stream@^6.0.1:
|
||||||
version "6.0.1"
|
version "6.0.1"
|
||||||
resolved "https://registry.npmmirror.com/zip-stream/-/zip-stream-6.0.1.tgz#e141b930ed60ccaf5d7fa9c8260e0d1748a2bbfb"
|
resolved "https://registry.npmmirror.com/zip-stream/-/zip-stream-6.0.1.tgz#e141b930ed60ccaf5d7fa9c8260e0d1748a2bbfb"
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user