feat(21-06): add search and agentId filter to listConversations
- Add ilike import and search/agentId conditions in chatService.listConversations - Extract search and agentId from req.query in GET /conversations route - Extend chatApi.listConversations opts with search and agentId params - Update useChatConversations to accept opts.search and include in queryKey
This commit is contained in:
parent
444a3476df
commit
d6ff48c0f3
4 changed files with 19 additions and 7 deletions
|
|
@ -16,11 +16,13 @@ export function chatRoutes(db: Db): Router {
|
||||||
router.get("/companies/:companyId/conversations", async (req, res) => {
|
router.get("/companies/:companyId/conversations", async (req, res) => {
|
||||||
assertBoard(req);
|
assertBoard(req);
|
||||||
assertCompanyAccess(req, req.params.companyId!);
|
assertCompanyAccess(req, req.params.companyId!);
|
||||||
const { cursor, limit, includeArchived } = req.query;
|
const { cursor, limit, includeArchived, search, agentId } = req.query;
|
||||||
const result = await svc.listConversations(req.params.companyId!, {
|
const result = await svc.listConversations(req.params.companyId!, {
|
||||||
cursor: cursor as string | undefined,
|
cursor: cursor as string | undefined,
|
||||||
limit: limit ? Number(limit) : undefined,
|
limit: limit ? Number(limit) : undefined,
|
||||||
includeArchived: includeArchived === "true",
|
includeArchived: includeArchived === "true",
|
||||||
|
search: search as string | undefined,
|
||||||
|
agentId: agentId as string | undefined,
|
||||||
});
|
});
|
||||||
res.json(result);
|
res.json(result);
|
||||||
});
|
});
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,4 @@
|
||||||
import { and, desc, eq, isNull, lt } from "drizzle-orm";
|
import { and, desc, eq, ilike, isNull, lt } from "drizzle-orm";
|
||||||
import type { Db } from "@paperclipai/db";
|
import type { Db } from "@paperclipai/db";
|
||||||
import { chatConversations, chatMessages } from "@paperclipai/db";
|
import { chatConversations, chatMessages } from "@paperclipai/db";
|
||||||
import { notFound } from "../errors.js";
|
import { notFound } from "../errors.js";
|
||||||
|
|
@ -7,7 +7,7 @@ export function chatService(db: Db) {
|
||||||
return {
|
return {
|
||||||
async listConversations(
|
async listConversations(
|
||||||
companyId: string,
|
companyId: string,
|
||||||
opts: { cursor?: string; limit?: number; includeArchived?: boolean },
|
opts: { cursor?: string; limit?: number; includeArchived?: boolean; search?: string; agentId?: string },
|
||||||
) {
|
) {
|
||||||
const limit = Math.min(opts.limit ?? 30, 100);
|
const limit = Math.min(opts.limit ?? 30, 100);
|
||||||
const includeArchived = opts.includeArchived ?? false;
|
const includeArchived = opts.includeArchived ?? false;
|
||||||
|
|
@ -25,6 +25,14 @@ export function chatService(db: Db) {
|
||||||
conditions.push(lt(chatConversations.updatedAt, new Date(opts.cursor)));
|
conditions.push(lt(chatConversations.updatedAt, new Date(opts.cursor)));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (opts.search) {
|
||||||
|
conditions.push(ilike(chatConversations.title, `%${opts.search}%`));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (opts.agentId) {
|
||||||
|
conditions.push(eq(chatConversations.agentId, opts.agentId));
|
||||||
|
}
|
||||||
|
|
||||||
const rows = await db
|
const rows = await db
|
||||||
.select()
|
.select()
|
||||||
.from(chatConversations)
|
.from(chatConversations)
|
||||||
|
|
|
||||||
|
|
@ -7,10 +7,12 @@ import type {
|
||||||
} from "@paperclipai/shared";
|
} from "@paperclipai/shared";
|
||||||
|
|
||||||
export const chatApi = {
|
export const chatApi = {
|
||||||
listConversations(companyId: string, opts?: { cursor?: string; limit?: number }) {
|
listConversations(companyId: string, opts?: { cursor?: string; limit?: number; search?: string; agentId?: string }) {
|
||||||
const params = new URLSearchParams();
|
const params = new URLSearchParams();
|
||||||
if (opts?.cursor) params.set("cursor", opts.cursor);
|
if (opts?.cursor) params.set("cursor", opts.cursor);
|
||||||
if (opts?.limit) params.set("limit", String(opts.limit));
|
if (opts?.limit) params.set("limit", String(opts.limit));
|
||||||
|
if (opts?.search) params.set("search", opts.search);
|
||||||
|
if (opts?.agentId) params.set("agentId", opts.agentId);
|
||||||
const qs = params.toString();
|
const qs = params.toString();
|
||||||
return api.get<ChatConversationListResponse>(
|
return api.get<ChatConversationListResponse>(
|
||||||
`/companies/${companyId}/conversations${qs ? `?${qs}` : ""}`,
|
`/companies/${companyId}/conversations${qs ? `?${qs}` : ""}`,
|
||||||
|
|
|
||||||
|
|
@ -2,13 +2,13 @@ import { useInfiniteQuery, useMutation, useQueryClient } from "@tanstack/react-q
|
||||||
import { chatApi } from "../api/chat";
|
import { chatApi } from "../api/chat";
|
||||||
import type { ChatConversationListResponse } from "@paperclipai/shared";
|
import type { ChatConversationListResponse } from "@paperclipai/shared";
|
||||||
|
|
||||||
export function useChatConversations(companyId: string | null) {
|
export function useChatConversations(companyId: string | null, opts?: { search?: string }) {
|
||||||
const queryClient = useQueryClient();
|
const queryClient = useQueryClient();
|
||||||
|
|
||||||
const query = useInfiniteQuery({
|
const query = useInfiniteQuery({
|
||||||
queryKey: ["chat", "conversations", companyId],
|
queryKey: ["chat", "conversations", companyId, opts?.search ?? ""],
|
||||||
queryFn: ({ pageParam }) =>
|
queryFn: ({ pageParam }) =>
|
||||||
chatApi.listConversations(companyId!, { cursor: pageParam as string | undefined }),
|
chatApi.listConversations(companyId!, { cursor: pageParam as string | undefined, search: opts?.search || undefined }),
|
||||||
initialPageParam: undefined as string | undefined,
|
initialPageParam: undefined as string | undefined,
|
||||||
getNextPageParam: (lastPage: ChatConversationListResponse) =>
|
getNextPageParam: (lastPage: ChatConversationListResponse) =>
|
||||||
lastPage.hasMore ? lastPage.items.at(-1)?.updatedAt : undefined,
|
lastPage.hasMore ? lastPage.items.at(-1)?.updatedAt : undefined,
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue