# Task D.1: Enquiry Assignment and CRM Role Stabilization

## 1. Files Added

- `src/app/api/crm/enquiries/[id]/_schemas.ts`
- `src/app/api/crm/enquiries/[id]/assign/route.ts`
- `src/app/api/crm/enquiries/[id]/reassign/route.ts`
- `src/features/crm/enquiries/components/enquiry-assignment-dialog.tsx`
- `drizzle/0008_clean_justin_hammer.sql`
- `drizzle/meta/0008_snapshot.json`

## 2. Files Modified

- `src/db/schema.ts`
- `src/lib/auth/rbac.ts`
- `src/app/dashboard/crm/enquiries/page.tsx`
- `src/app/dashboard/crm/enquiries/[id]/page.tsx`
- `src/features/crm/enquiries/api/types.ts`
- `src/features/crm/enquiries/api/service.ts`
- `src/features/crm/enquiries/api/mutations.ts`
- `src/features/crm/enquiries/server/service.ts`
- `src/features/crm/enquiries/components/enquiry-columns.tsx`
- `src/features/crm/enquiries/components/enquiries-table.tsx`
- `src/features/crm/enquiries/components/enquiry-listing.tsx`
- `src/features/crm/enquiries/components/enquiry-detail.tsx`
- `src/features/crm/enquiries/components/enquiry-cell-action.tsx`
- `src/features/users/api/types.ts`
- `src/features/users/schemas/user.ts`
- `src/features/users/components/user-form-sheet.tsx`
- `src/app/api/users/_lib.ts`
- `src/app/api/users/route.ts`
- `src/app/api/organizations/route.ts`
- `src/features/foundation/auth-context/service.ts`

## 3. Schema Added

Added assignment fields to `crm_enquiries`:

- `assigned_to_user_id`
- `assigned_at`
- `assigned_by`
- `assignment_remark`

Rules implemented:

- assignee must belong to the same organization
- assigner is the current user
- latest assignment timestamp is persisted
- assignment remark is optional

## 4. API Routes Added

- `POST /api/crm/enquiries/[id]/assign`
- `POST /api/crm/enquiries/[id]/reassign`

Payload:

```ts
{
  assignedToUserId: string;
  remark?: string;
}
```

Behavior:

- requires organization access
- enforces `crm.enquiry.assign` or `crm.enquiry.reassign`
- validates assignee organization membership
- rejects assign on already-assigned enquiry
- rejects reassign on unassigned enquiry

## 5. Permissions Added

- `crm.enquiry.assign`
- `crm.enquiry.reassign`

CRM business-role set was also stabilized around:

- `sales_manager`
- `sales`
- `sales_support`
- `department_manager`
- `top_manager`

Legacy IT-CENTER business roles were removed from active runtime paths and defaults.

## 6. UI Added

Enquiry detail now supports:

- `Assign Sales`
- `Reassign Sales`
- assigned sales metadata display

Enquiry list now shows:

- `Assigned Sales` column

Assignment dialog now includes:

- `Sales User`
- `Remark`

The sales-user dropdown is populated from organization memberships instead of hardcoded values.

## 7. Audit Integration

Assignment writes audit logs under:

- `entityType = crm_enquiry`

Actions added:

- `assign`
- `reassign`

Audit payload shape:

- `beforeData.oldAssignedToUserId`
- `afterData.newAssignedToUserId`
- `afterData.remark`

## 8. Membership / Permission Stabilization

Workspace membership management now uses CRM-aligned business roles instead of the old template roles.

Updated areas:

- user API types and validation
- membership defaults
- organization-management fallbacks
- auth-context business-role fallback

## 9. Remaining Risks

- current `sales` access still operates at organization scope; there is not yet a server-enforced “own or assigned only” data policy
- old database rows that still carry removed legacy business-role strings may need a one-time data backfill if they exist in a real environment
- assignable-user filtering currently accepts organization admins plus sales-oriented roles; if future CRM staffing rules become stricter, that policy should move into a dedicated assignment rule layer

## 10. Verification

- `npx tsc --noEmit`
- `npx oxlint` on changed Task D.1 files
