You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
49 lines
1.7 KiB
49 lines
1.7 KiB
import { z } from "zod";
|
|
import { dbGlobal } from "drizzle-pkg/lib/db";
|
|
import { items, itemTags, tags } from "drizzle-pkg/lib/schema/collection";
|
|
import { eq, and, like, or as orOp } from "drizzle-orm";
|
|
import { getContextUser } from "#server/utils/context";
|
|
|
|
export default defineWrappedResponseHandler({ auth: "required" }, async (event) => {
|
|
const user = getContextUser(event)!;
|
|
const body = await readBody(event);
|
|
const parsed = z.object({
|
|
message: z.string().min(1),
|
|
}).safeParse(body);
|
|
if (!parsed.success) return R.error("请输入问题", parsed.error.issues);
|
|
|
|
const { message } = parsed.data;
|
|
|
|
// Search items matching the query
|
|
const keywords = message.split(/\s+/).filter(k => k.length > 0);
|
|
if (keywords.length === 0) return R.success({ answer: "请问有什么可以帮助你的?", items: [] });
|
|
|
|
const conditions = keywords.map(k =>
|
|
orOp(
|
|
like(items.title, `%${k}%`),
|
|
like(items.description, `%${k}%`),
|
|
like(items.content, `%${k}%`)
|
|
)
|
|
);
|
|
|
|
const matched = await dbGlobal
|
|
.select()
|
|
.from(items)
|
|
.where(and(eq(items.userId, user.id), conditions[0]));
|
|
|
|
if (matched.length === 0) {
|
|
return R.success({
|
|
answer: `没有找到与"${message}"相关的收藏。试试其他关键词?`,
|
|
items: [],
|
|
});
|
|
}
|
|
|
|
// Build a conversational response
|
|
const previews = matched.slice(0, 3).map(item =>
|
|
`- **${item.title}**${item.description ? `:${item.description.slice(0, 60)}` : ''}`
|
|
).join("\n");
|
|
|
|
const answer = `找到 ${matched.length} 条相关收藏:\n${previews}\n\n${matched.length > 3 ? `以及其他 ${matched.length - 3} 条...` : ''}`;
|
|
|
|
return R.success({ answer, items: matched.slice(0, 5) });
|
|
});
|
|
|