test(orders): cover auth + matcher-isolation for backfill endpoint, document response shape
This commit is contained in:
parent
f0c5daa99e
commit
14347c4b4b
2 changed files with 56 additions and 0 deletions
|
|
@ -1,6 +1,9 @@
|
|||
import { describe, it, expect, vi, beforeEach } from "vitest";
|
||||
import { NextRequest } from "next/server";
|
||||
import { POST } from "./route";
|
||||
import { suggestOrderNumberDuplicate } from "@/lib/server/order-number-duplicate-link-service";
|
||||
import { suggestOrderDuplicate } from "@/lib/server/order-order-duplicate-link-service";
|
||||
import { suggestDeliveryNoteForOrder } from "@/lib/server/order-delivery-note-link-service";
|
||||
|
||||
vi.mock("@/lib/server/order-number-duplicate-link-service", () => ({
|
||||
suggestOrderNumberDuplicate: vi.fn().mockResolvedValue({ duplicateOrderId: null }),
|
||||
|
|
@ -45,5 +48,47 @@ describe("POST /api/v1/orders/backfill-duplicate-checks", () => {
|
|||
expect(res.status).toBe(200);
|
||||
const body = await res.json();
|
||||
expect(body.ordersProcessed).toBe(2);
|
||||
|
||||
expect(suggestOrderNumberDuplicate).toHaveBeenCalledTimes(2);
|
||||
expect(suggestOrderDuplicate).toHaveBeenCalledTimes(2);
|
||||
expect(suggestDeliveryNoteForOrder).toHaveBeenCalledTimes(2);
|
||||
expect(suggestOrderNumberDuplicate).toHaveBeenCalledWith("order-1");
|
||||
expect(suggestOrderNumberDuplicate).toHaveBeenCalledWith("order-2");
|
||||
});
|
||||
|
||||
it("returns 401 when AGENT_API_KEY is missing", async () => {
|
||||
delete process.env.AGENT_API_KEY;
|
||||
const res = await POST(backfillRequest());
|
||||
expect(res.status).toBe(401);
|
||||
const body = await res.json();
|
||||
expect(body.error).toBeTruthy();
|
||||
});
|
||||
|
||||
it("returns 401 when AGENT_API_KEY is wrong", async () => {
|
||||
process.env.AGENT_API_KEY = AGENT_API_KEY;
|
||||
const req = new NextRequest(
|
||||
"http://localhost/api/v1/orders/backfill-duplicate-checks",
|
||||
{
|
||||
method: "POST",
|
||||
headers: { authorization: "Bearer wrong-key" },
|
||||
},
|
||||
);
|
||||
const res = await POST(req);
|
||||
expect(res.status).toBe(401);
|
||||
});
|
||||
|
||||
it("continues processing when one matcher throws for one order", async () => {
|
||||
vi.mocked(suggestOrderNumberDuplicate)
|
||||
.mockRejectedValueOnce(new Error("boom"))
|
||||
.mockResolvedValueOnce({ duplicateOrderId: null });
|
||||
|
||||
const res = await POST(backfillRequest());
|
||||
expect(res.status).toBe(200);
|
||||
const body = await res.json();
|
||||
expect(body.ordersProcessed).toBe(2);
|
||||
expect(body.failures.length).toBe(1);
|
||||
expect(body.failures[0].orderId).toBe("order-1");
|
||||
expect(body.failures[0].error).toContain("order_number:");
|
||||
expect(body.failures[0].error).toContain("boom");
|
||||
});
|
||||
});
|
||||
|
|
|
|||
|
|
@ -11,6 +11,17 @@
|
|||
* over the full orders table, and PocketBase's admin client doesn't
|
||||
* love thousands of concurrent requests. This is a background/admin
|
||||
* operation, not a user-facing latency path.
|
||||
*
|
||||
* Returns: `{ ordersProcessed, failures }` where `failures` is
|
||||
* `Array<{ orderId, error }>`. The `error` string is prefixed with
|
||||
* the matcher name (`order_number:`, `item_duplicate:`, or
|
||||
* `delivery_note:`) followed by the underlying error message, so
|
||||
* callers can tell which matcher tripped without re-running.
|
||||
*
|
||||
* Errors:
|
||||
* 401 — missing/wrong `AGENT_API_KEY`.
|
||||
* (per-order matcher failures are reported in `failures`, not
|
||||
* surfaced as HTTP errors)
|
||||
*/
|
||||
export const runtime = "nodejs";
|
||||
export const dynamic = "force-dynamic";
|
||||
|
|
|
|||
Loading…
Reference in a new issue