4b7dec2759
- Nytt paket @app/recipe-generation med pipeline, verifieringsgrind, gaprapport och pilotbatch-script. - Ny AAMOS-task GENERATE_RECIPE_CANDIDATES i @app/ai-contracts. - GeminiAamosClient utökat med receptgenereringsstöd. - MockAamosClient uppdaterad med deterministiska kandidater. - Verifieringspipeline: ingrediensmappning (hård spärr), härledda allergener, beräknad näring via nutrition-engine, språk-/kvalitetskontroll, dedup. - Hermetiska tester: 10/10 gröna. - typecheck + test + build: gröna för hela workspace. Refs: docs/32-receptkatalog-buildout.md
40 lines
2.1 KiB
TypeScript
40 lines
2.1 KiB
TypeScript
import { describe, it, expect } from "vitest";
|
|
import { buildGapReport, formatGapReport } from "../src/gap-report.js";
|
|
import type { AnalyticsEvent, RecipeSignal } from "../src/gap-report.js";
|
|
|
|
describe("buildGapReport", () => {
|
|
it("identifierar topp-saknade ingredienser", () => {
|
|
const events: AnalyticsEvent[] = [
|
|
{ eventName: "recipe_search_zero_results", occurredAt: new Date(), properties: { query: "lax", suggestedIngredientId: "laxfile" } },
|
|
{ eventName: "recipe_search_zero_results", occurredAt: new Date(), properties: { query: "lax", suggestedIngredientId: "laxfile" } },
|
|
{ eventName: "recipe_search_zero_results", occurredAt: new Date(), properties: { query: "lax", suggestedIngredientId: "laxfile" } },
|
|
{ eventName: "recipe_search_zero_results", occurredAt: new Date(), properties: { query: "tofu", suggestedIngredientId: "fast_tofu" } },
|
|
{ eventName: "recipe_search_zero_results", occurredAt: new Date(), properties: { query: "tofu", suggestedIngredientId: "fast_tofu" } },
|
|
];
|
|
|
|
const report = buildGapReport(events, [], []);
|
|
expect(report.entries).toHaveLength(2);
|
|
expect(report.topMissingIngredients[0]?.canonicalIngredientId).toBe("laxfile");
|
|
expect(report.topMissingIngredients[0]?.count).toBe(3);
|
|
});
|
|
|
|
it("filtrerar bort enstaka missar", () => {
|
|
const events: AnalyticsEvent[] = [
|
|
{ eventName: "recipe_search_zero_results", occurredAt: new Date(), properties: { query: "enstaka" } },
|
|
];
|
|
const report = buildGapReport(events, [], [], { minMissThreshold: 2 });
|
|
expect(report.entries).toHaveLength(0);
|
|
});
|
|
|
|
it("formaterar rapporten", () => {
|
|
const events: AnalyticsEvent[] = [
|
|
{ eventName: "recipe_search_zero_results", occurredAt: new Date(), properties: { query: "lax" } },
|
|
{ eventName: "recipe_search_zero_results", occurredAt: new Date(), properties: { query: "lax" } },
|
|
];
|
|
const report = buildGapReport(events, [], [], { minMissThreshold: 1 });
|
|
const text = formatGapReport(report);
|
|
expect(text).toContain("Katalog-gaprapport");
|
|
expect(text).toContain("lax");
|
|
});
|
|
});
|