fix(validation): enforce filter prompt limits

This commit is contained in:
vivekvar-dl 2026-09-28 15:58:23 +05:30
parent cfa6c7cb17
commit 84d6f5bd3d
3 changed files with 42 additions and 3 deletions

View file

@ -26,13 +26,14 @@ import {
SearchResponseSchema,
type SearchResult,
SettingsRequestSchema,
SettingsResponseSchema,
UpdateContainerTagSettingsRequestSchema,
} from "../validation/api"
const UpdateSettingsResponseSchema = z.object({
orgId: z.string(),
orgSlug: z.string(),
updated: SettingsRequestSchema,
updated: SettingsResponseSchema,
})
// Analytics request schema - custom to console
@ -190,7 +191,7 @@ export const apiSchema = createSchema({
// Settings operations
"@get/settings": {
output: SettingsRequestSchema,
output: SettingsResponseSchema,
},
"@patch/settings": {
input: SettingsRequestSchema,

View file

@ -6,8 +6,42 @@ import {
ListMemoriesQuerySchema,
SearchRequestSchema,
Searchv4RequestSchema,
SettingsRequestSchema,
SettingsResponseSchema,
} from "./api"
describe("organization settings schemas", () => {
it.each([
"x",
"x".repeat(750),
])("accepts a filter prompt at a documented boundary", (filterPrompt) => {
expect(SettingsRequestSchema.parse({ filterPrompt }).filterPrompt).toBe(
filterPrompt,
)
})
it.each([
"",
"x".repeat(751),
])("rejects a filter prompt outside the documented boundaries", (filterPrompt) => {
expect(SettingsRequestSchema.safeParse({ filterPrompt }).success).toBe(
false,
)
})
it("accepts null to clear the filter prompt", () => {
expect(
SettingsRequestSchema.parse({ filterPrompt: null }).filterPrompt,
).toBe(null)
})
it("continues to parse legacy empty prompts in settings responses", () => {
expect(
SettingsResponseSchema.parse({ filterPrompt: "" }).filterPrompt,
).toBe("")
})
})
describe("search threshold schemas", () => {
it("do not contain redundant number transforms or unreachable range guards", () => {
const source = readFileSync(new URL("./api.ts", import.meta.url), "utf8")

View file

@ -803,12 +803,16 @@ export const ErrorResponseSchema = z.object({
export type SearchResult = z.infer<typeof SearchResultSchema>
export const SettingsRequestSchema = OrganizationSettingsSchema.omit({
export const SettingsResponseSchema = OrganizationSettingsSchema.omit({
id: true,
orgId: true,
updatedAt: true,
}).partial()
export const SettingsRequestSchema = SettingsResponseSchema.extend({
filterPrompt: z.string().min(1).max(750).nullable().optional(),
})
export const ConnectionResponseSchema = z.object({
createdAt: z.string().datetime(),
documentLimit: z.number().optional(),