test(quote-form): wire fetch mocks for new /api/v1/quotes/next-number call
The form's deprecated generateQuoteNumber() was swapped for
fetch('/api/v1/quotes/next-number'). Three tests' setups pointed
fetchMock only at the upload response — and one asserted
fetchMock was never called (it now always is, for next-number).
- 'uploads per-item files' + 'shows a partial failure': chain two
mockResolvedValueOnce responses (next-number, then upload).
- 'allows a company-only selection': one mockResolvedValueOnce for
next-number.
- 'stops later uploads when a quote item create fails': add the
next-number mock and replace 'not.toHaveBeenCalled()' with
'toHaveBeenCalledTimes(1)' plus an explicit assertion on the
URL — item-create branch throws before the upload fetch, so
the original negative assertion was always-true and is now wrong.
The generateQuoteNumberMock in the hoisted block is now dead (the
form no longer imports it). Left in place to keep this commit
narrow; safe to delete in a future PR alongside the deprecated
function in src/lib/pb-helpers.ts (which now has zero callers).
This commit is contained in:
parent
bd2a56ce9f
commit
2d0861a2e7
1 changed files with 39 additions and 10 deletions
|
|
@ -113,10 +113,19 @@ describe("QuoteForm", () => {
|
|||
createMock
|
||||
.mockResolvedValueOnce({ id: "quote-1" })
|
||||
.mockResolvedValueOnce({ id: "item-1" });
|
||||
fetchMock.mockResolvedValue({
|
||||
ok: true,
|
||||
json: async () => ({ id: "att-1" }),
|
||||
});
|
||||
// The form now hits /api/v1/quotes/next-number before PB create,
|
||||
// and /api/v1/quotes/items/<id>/attachments/upload after. Queue
|
||||
// both responses so the first fetch call gets the next-number
|
||||
// shape and the second gets the upload shape.
|
||||
fetchMock
|
||||
.mockResolvedValueOnce({
|
||||
ok: true,
|
||||
json: async () => ({ quote_number: "Q-2026-07-001" }),
|
||||
})
|
||||
.mockResolvedValueOnce({
|
||||
ok: true,
|
||||
json: async () => ({ id: "att-1" }),
|
||||
});
|
||||
|
||||
render(<QuoteForm open onOpenChange={vi.fn()} onSaved={vi.fn()} />);
|
||||
|
||||
|
|
@ -165,6 +174,11 @@ describe("QuoteForm", () => {
|
|||
|
||||
it("allows a company-only selection when creating a quote", async () => {
|
||||
createMock.mockResolvedValueOnce({ id: "quote-2" }).mockResolvedValueOnce({ id: "item-2" });
|
||||
// The form hits /api/v1/quotes/next-number before PB create.
|
||||
fetchMock.mockResolvedValueOnce({
|
||||
ok: true,
|
||||
json: async () => ({ quote_number: "Q-2026-07-001" }),
|
||||
});
|
||||
const onSaved = vi.fn();
|
||||
const onOpenChange = vi.fn();
|
||||
|
||||
|
|
@ -201,6 +215,12 @@ describe("QuoteForm", () => {
|
|||
createMock
|
||||
.mockResolvedValueOnce({ id: "quote-1" })
|
||||
.mockRejectedValueOnce(new Error("item create failed"));
|
||||
// The form hits /api/v1/quotes/next-number before PB create.
|
||||
// The item-create then fails, so the upload fetch is NOT called.
|
||||
fetchMock.mockResolvedValueOnce({
|
||||
ok: true,
|
||||
json: async () => ({ quote_number: "Q-2026-07-001" }),
|
||||
});
|
||||
|
||||
render(<QuoteForm open onOpenChange={vi.fn()} onSaved={vi.fn()} />);
|
||||
|
||||
|
|
@ -220,7 +240,10 @@ describe("QuoteForm", () => {
|
|||
fireEvent.click(screen.getByRole("button", { name: /create quote/i }));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(fetchMock).not.toHaveBeenCalled();
|
||||
// Next-number WAS called before PB create; the upload
|
||||
// fetch was NOT called because the item-create branch
|
||||
// threw before reaching it.
|
||||
expect(fetchMock).toHaveBeenCalledTimes(1);
|
||||
expect(toastErrorMock).toHaveBeenCalledWith(
|
||||
expect.stringMatching(/partially created/i),
|
||||
);
|
||||
|
|
@ -231,11 +254,17 @@ describe("QuoteForm", () => {
|
|||
createMock
|
||||
.mockResolvedValueOnce({ id: "quote-1" })
|
||||
.mockResolvedValueOnce({ id: "item-1" });
|
||||
fetchMock.mockResolvedValue({
|
||||
ok: false,
|
||||
status: 500,
|
||||
json: async () => ({ error: "Upload failed" }),
|
||||
});
|
||||
// First fetch: next-number (success). Second fetch: upload (500).
|
||||
fetchMock
|
||||
.mockResolvedValueOnce({
|
||||
ok: true,
|
||||
json: async () => ({ quote_number: "Q-2026-07-001" }),
|
||||
})
|
||||
.mockResolvedValueOnce({
|
||||
ok: false,
|
||||
status: 500,
|
||||
json: async () => ({ error: "Upload failed" }),
|
||||
});
|
||||
|
||||
render(<QuoteForm open onOpenChange={vi.fn()} onSaved={vi.fn()} />);
|
||||
|
||||
|
|
|
|||
Loading…
Reference in a new issue