feat: add product to opportunity route, local product sequencing

- Add POST /v1/sales/opportunities/:identifier/products with field-level permission gating
- Add CWForecastItemCreate type for forecast item creation
- Store product display order locally (productSequence Int[] on Opportunity)
- Rewrite resequenceProducts to be local-only (no CW PUT, stable IDs)
- Remove reorderProducts CW util (PUT regenerated IDs & broke procurement)
- Update fetchProducts to apply local ordering with CW sequenceNumber fallback
- Add productSequence to OpportunityController.toJson()
- Update API_ROUTES.md, PERMISSIONS.md, PermissionNodes.ts
This commit is contained in:
2026-03-01 18:01:02 -06:00
parent d7b374f8ab
commit 30b408e0db
19 changed files with 1030 additions and 107 deletions
+11 -9
View File
@@ -24,9 +24,10 @@ Keep each layer focused:
## Runtime / tooling
The project runs on **Bun**. DB tooling uses **Prisma**; the generated client lives under `generated/prisma` (do NOT edit generated files). Key scripts in `package.json`:
The project runs on **Bun** exclusively — **always use `bun` commands, never `npm`, `npx`, or `yarn`**. DB tooling uses **Prisma**; the generated client lives under `generated/prisma` (do NOT edit generated files). Test preloads are configured in `bunfig.toml` so bare `bun test` works. Key scripts in `package.json`:
- `dev``NODE_ENV=development bun --watch src/index.ts` (start dev server with hot reload)
- `test``bun test` (runs all tests with preload from `bunfig.toml`)
- `db:gen``prisma generate`
- `db:push``prisma migrate dev --skip-generate`
- `utils:dev``docker compose -f .docker/docker-compose.yml up --build`
@@ -36,7 +37,7 @@ The project runs on **Bun**. DB tooling uses **Prisma**; the generated client li
## Data layer
Prisma schema is at `prisma/schema.prisma`. The app imports the generated Prisma client from `generated/prisma/client.ts` (or `generated/prisma/browser.ts` for browser type contexts). The shared `prisma` instance is exported from `src/constants.ts`. Always run `npm run db:gen` after updating `schema.prisma`.
Prisma schema is at `prisma/schema.prisma`. The app imports the generated Prisma client from `generated/prisma/client.ts` (or `generated/prisma/browser.ts` for browser type contexts). The shared `prisma` instance is exported from `src/constants.ts`. Always run `bun run db:gen` after updating `schema.prisma`.
## Shared constants (`src/constants.ts`)
@@ -174,13 +175,14 @@ The `UnifiClient` class in `src/modules/unifi-api/UnifiClient.ts` wraps all UniF
## Local dev / quick checks
- Start dev server: `npm run dev`
- Regenerate Prisma client: `npm run db:gen`
- Apply DB migrations locally: `npm run db:push`
- Docker dev utilities: `npm run utils:dev`
- Generate private keys: `npm run utils:gen_private_keys`
- Create admin role: `npm run utils:create_admin_role`
- Assign user role: `npm run utils:assign_user_role`
- Start dev server: `bun run dev`
- Run tests: `bun test`
- Regenerate Prisma client: `bun run db:gen`
- Apply DB migrations locally: `bun run db:push`
- Docker dev utilities: `bun run utils:dev`
- Generate private keys: `bun run utils:gen_private_keys`
- Create admin role: `bun run utils:create_admin_role`
- Assign user role: `bun run utils:assign_user_role`
## When editing generated or infra files