Adds the three proposal fields (proposed_target_date, proposed_by,
proposed_at) to the cards collection with a partial index that backs
the 'pending proposals' query, plus two new ActivityAction values
(date_proposed, date_proposal_resolved) and column_changed for
return-to-scheduled.
New server actions under src/app/actions/:
- client-proposal.ts: client-manager drag creates a proposal (not
a target_date write); 404 (not 403) on cross-tenant failures and
Done-column cards, matching the rest of /api/client/*.
- owner-plan.ts: accept and dismiss clear the three proposal
fields together and emit the audit rows; returnToScheduledAction
moves a Done card back to the first working column.
Server-side Done-column guards added to:
- src/app/actions/reschedule.ts (was UI-only)
- src/app/api/client/cards/[id]/route.ts (was UI-only)
Both pass through the new writeCardWithAudit helper at
src/lib/cards/write-with-audit.ts — single source of truth for
'patch card + emit activity rows', replacing the inline copies in
the PATCH route and rescheduleCardAction.
Adds src/lib/roadmap/slot-date.ts (slot <-> target_date mapping)
consumed by Pixel's puzzle UI; named SlotId API rather than the
plan's numeric indices for self-documenting callers.
CLIENT_EDITABLE_CARD_FIELDS stays at priority + target_date per
the brief; proposals go through the dedicated action so they get
their own audit row type.
53 lines
1.5 KiB
TypeScript
53 lines
1.5 KiB
TypeScript
import { defineConfig } from "vitest/config";
|
|
import path from "node:path";
|
|
import { fileURLToPath } from "node:url";
|
|
|
|
const serverOnlyStub = fileURLToPath(
|
|
new URL("./src/lib/server-only-stub.ts", import.meta.url)
|
|
);
|
|
|
|
export default defineConfig({
|
|
resolve: {
|
|
alias: { "@": path.resolve(__dirname, "./src") },
|
|
},
|
|
test: {
|
|
projects: [
|
|
{
|
|
// Unit tests can also import server-only modules (e.g.
|
|
// writeCardWithAudit) and replace the guard with the empty stub,
|
|
// matching the integration project's alias.
|
|
resolve: {
|
|
alias: {
|
|
"@": path.resolve(__dirname, "./src"),
|
|
"server-only": serverOnlyStub,
|
|
},
|
|
},
|
|
test: {
|
|
name: "unit",
|
|
environment: "node",
|
|
include: ["src/**/*.test.ts"],
|
|
},
|
|
},
|
|
{
|
|
resolve: {
|
|
alias: {
|
|
"@": path.resolve(__dirname, "./src"),
|
|
// Replace server-only with the empty stub so integration tests
|
|
// can import server modules without "imported from a Client
|
|
// Component module" blowing up at prepare time.
|
|
"server-only": serverOnlyStub,
|
|
},
|
|
conditions: ["react-server", "node", "import", "default"],
|
|
},
|
|
test: {
|
|
name: "integration",
|
|
environment: "node",
|
|
include: ["tests/integration/**/*.test.ts"],
|
|
hookTimeout: 30_000,
|
|
testTimeout: 30_000,
|
|
poolOptions: { forks: { singleFork: true } },
|
|
},
|
|
},
|
|
],
|
|
},
|
|
});
|