import { describe, expect, it } from "@suaveplan/testing/runner"; import fc from "fast-check"; import { compileWhere, type WhereClause, } from "../src/compile/compile-where.js"; import { DEFAULT_BETTER_AUTH_LINK_FIELDS } from "../src/link-fields/link-fields.js"; const OPERATORS = [ "eq", "ne", "gt", "gte", "lt", "lte", "in", "not_in", "contains", "starts_with", "ends_with", ] as const; const IDENT_FIELD = fc .stringMatching(/^[a-z][a-zA-Z0-9_]{0,10}$/) .filter((s) => s.length > 0); const clauseArb = fc.record({ field: IDENT_FIELD, value: fc.oneof( fc.string(), fc.integer(), fc.boolean(), fc .array(fc.string(), { minLength: 1, maxLength: 4 }) .filter((arr) => arr.every((v) => !v.includes(":"))) ), operator: fc.constantFrom(...OPERATORS), connector: fc.constantFrom("AND", "OR" as const), }) as unknown as fc.Arbitrary; describe("compileWhere property tests", () => { it("placeholder names are always unique and match var keys", { timeout: 30000, }, () => { fc.assert( fc.property( fc.array(clauseArb, { minLength: 1, maxLength: 20 }), (clauses) => { const out = compileWhere(clauses, { model: "user", linkFields: {}, }); const placeholders = Array.from( out.clause.matchAll(/\$\w+/g) ).map((m) => m[0].slice(1)); const dedup = new Set(placeholders); expect(dedup.size).toBe(placeholders.length); expect(new Set(Object.keys(out.vars))).toEqual(dedup); } ), { numRuns: 200 } ); }); it("link-field where values are always pre-resolved", { timeout: 30000, }, () => { const linkField = "userId"; const linkValueArb = fc .string({ minLength: 1, maxLength: 10 }) .filter((s) => !s.includes(":") && /^[a-z0-9]+$/i.test(s)); fc.assert( fc.property( fc.array( fc.record({ field: fc.constant(linkField), value: linkValueArb, operator: fc.constant("eq" as const), }), { minLength: 1, maxLength: 10 } ), (clauses) => { const out = compileWhere(clauses, { model: "session", linkFields: DEFAULT_BETTER_AUTH_LINK_FIELDS, }); for (const placeholder of Object.keys(out.vars)) { const v = out.vars[placeholder]; expect(String(v).startsWith("user:")).toBe(true); } } ), { numRuns: 200 } ); }); });