core: filter sessions at database level to improve session list loading performance

This commit is contained in:
Dax Raad
2026-02-14 13:40:49 -05:00
parent 306fc77076
commit 68bb8ce1da
2 changed files with 35 additions and 17 deletions

View File

@@ -53,15 +53,15 @@ export const SessionRoutes = lazy(() =>
),
async (c) => {
const query = c.req.valid("query")
const term = query.search?.toLowerCase()
const sessions: Session.Info[] = []
for await (const session of Session.list()) {
if (query.directory !== undefined && session.directory !== query.directory) continue
if (query.roots && session.parentID) continue
if (query.start !== undefined && session.time.updated < query.start) continue
if (term !== undefined && !session.title.toLowerCase().includes(term)) continue
for await (const session of Session.list({
directory: query.directory,
roots: query.roots,
start: query.start,
search: query.search,
limit: query.limit,
})) {
sessions.push(session)
if (query.limit !== undefined && sessions.length >= query.limit) break
}
return c.json(sessions)
},

View File

@@ -10,7 +10,7 @@ import { Flag } from "../flag/flag"
import { Identifier } from "../id/id"
import { Installation } from "../installation"
import { Database, NotFoundError, eq, and, or, like } from "../storage/db"
import { Database, NotFoundError, eq, and, or, gte, isNull, desc, like } from "../storage/db"
import { SessionTable, MessageTable, PartTable } from "./session.sql"
import { Storage } from "@/storage/storage"
import { Log } from "../util/log"
@@ -505,20 +505,38 @@ export namespace Session {
},
)
export function* list() {
export function* list(input?: {
directory?: string
roots?: boolean
start?: number
search?: string
limit?: number
}) {
const project = Instance.project
// const rel = path.relative(Instance.worktree, Instance.directory)
// const suffix = path.sep + rel
const conditions = [eq(SessionTable.project_id, project.id)]
if (input?.directory) {
conditions.push(eq(SessionTable.directory, input.directory))
}
if (input?.roots) {
conditions.push(isNull(SessionTable.parent_id))
}
if (input?.start) {
conditions.push(gte(SessionTable.time_updated, input.start))
}
if (input?.search) {
conditions.push(like(SessionTable.title, `%${input.search}%`))
}
const limit = input?.limit ?? 100
const rows = Database.use((db) =>
db
.select()
.from(SessionTable)
.where(
and(
eq(SessionTable.project_id, project.id),
// or(eq(SessionTable.directory, Instance.directory), like(SessionTable.directory, `%${suffix}`)),
),
)
.where(and(...conditions))
.orderBy(desc(SessionTable.time_updated))
.limit(limit)
.all(),
)
for (const row of rows) {