diff --git a/src/permit/permit.controller.ts b/src/permit/permit.controller.ts index 464d6de..7b3d9e6 100644 --- a/src/permit/permit.controller.ts +++ b/src/permit/permit.controller.ts @@ -18,7 +18,7 @@ export async function createPermitHandler( const input = req.body as CreatePermitInput; try { - const permit = await createPermit(input, req.user.tenantId); + const permit = await createPermit(input, req.user); return res.code(201).send(permit); } catch (err) { return err; @@ -62,11 +62,7 @@ export async function updatePermitHandler( const { permitId } = req.params as { permitId: string }; try { - const updatedPermit = await updatePermit( - input, - permitId, - req.user.tenantId - ); + const updatedPermit = await updatePermit(input, permitId, req.user); if (!updatedPermit) return res.code(404).send({ error: "resource not found" }); diff --git a/src/permit/permit.schema.ts b/src/permit/permit.schema.ts index 04e1366..669ca0d 100644 --- a/src/permit/permit.schema.ts +++ b/src/permit/permit.schema.ts @@ -22,7 +22,13 @@ const permitSchema = new mongoose.Schema({ ref: "organization", }, permitDate: Date, - stage: String, + stage: new mongoose.Schema( + { + pipeline: Array, + currentStage: Number, + }, + { _id: false } + ), status: String, assignedTo: { type: mongoose.Types.ObjectId, @@ -59,7 +65,19 @@ const permitCore = { county: z.string().optional(), client: z.string().optional(), permitDate: z.date(), - stage: z.string().optional(), + stage: z + .object({ + pipeline: z.array( + z.object({ + name: z.string(), + date: z.date().nullable().optional(), + description: z.string().optional(), + comment: z.string().optional(), + }) + ), + currentStage: z.number(), + }) + .optional(), status: z.string().optional(), assignedTo: z.string().optional(), }; @@ -105,7 +123,21 @@ const updatePermitInput = z.object({ county: z.string().optional(), client: z.string().optional(), permitDate: z.date().optional(), - stage: z.string().optional(), + stage: z + .object({ + pipeline: z + .array( + z.object({ + name: z.string(), + date: z.date().nullable().optional(), + description: z.string().optional(), + comment: z.string().optional(), + }) + ) + .optional(), + currentStage: z.number().optional(), + }) + .optional(), status: z.string().optional(), assignedTo: z.string().optional(), }); diff --git a/src/permit/permit.service.ts b/src/permit/permit.service.ts index 0b25fa4..9056a92 100644 --- a/src/permit/permit.service.ts +++ b/src/permit/permit.service.ts @@ -1,4 +1,3 @@ -import mongoose from "mongoose"; import { orgModel } from "../organization/organization.schema"; import { getFilterObject, getSortObject, PageQueryParams } from "../pagination"; import { userModel } from "../user/user.schema"; @@ -10,11 +9,25 @@ import { UpdatePermitInput, } from "./permit.schema"; import { ChangeEvent, dbEvents } from "../realtime"; +import { pipeline } from "../utils/pipeline"; +import { AuthenticatedUser } from "../auth"; + +export async function createPermit( + input: CreatePermitInput, + user: AuthenticatedUser +) { + if (!input.stage) { + input.stage = { + pipeline: pipeline, + currentStage: 0, + }; + } -export async function createPermit(input: CreatePermitInput, tenantId: string) { const permit = await permitModel.create({ - tenantId: tenantId, + tenantId: user.tenantId, pid: generateId(), + createdAt: new Date(), + createdBy: user.userId, ...input, }); @@ -92,6 +105,8 @@ export async function listPermits(params: PageQueryParams, tenantId: string) { permitDate: 1, stage: 1, status: 1, + address: 1, + description: 1, county: { $let: { vars: { county: { $arrayElemAt: ["$countyRec", 0] } }, @@ -168,12 +183,12 @@ export async function listPermits(params: PageQueryParams, tenantId: string) { export async function updatePermit( input: UpdatePermitInput, permitId: string, - tenantId: string + user: AuthenticatedUser ) { const updatePermitResult = await permitModel .findOneAndUpdate( { - $and: [{ tenantId: tenantId }, { pid: permitId }], + $and: [{ tenantId: user.tenantId }, { pid: permitId }], }, { ...input, updatedAt: new Date() }, { new: true } diff --git a/src/utils/pipeline.ts b/src/utils/pipeline.ts new file mode 100644 index 0000000..546a677 --- /dev/null +++ b/src/utils/pipeline.ts @@ -0,0 +1,103 @@ +export const pipeline: { + name: string; + date?: Date; + description?: string; + comment?: string; +}[] = [ + { + name: "Ready to submit", + date: null, + description: "", + comment: "", + }, + { + name: "Validating", + date: null, + description: "", + comment: "", + }, + { + name: "Information Required", + date: null, + description: "", + comment: "", + }, + { + name: "In Progress", + date: null, + description: "", + comment: "", + }, + { + name: "On Hold", + date: null, + description: "", + comment: "", + }, + { + name: "Submitted", + date: null, + description: "", + comment: "", + }, + { + name: "In Review", + date: null, + description: "", + comment: "", + }, + { + name: "Awaiting Client Reply", + date: null, + description: "", + comment: "", + }, + { + name: "Fees Due", + date: null, + description: "", + comment: "", + }, + { + name: "Revision Request", + date: null, + description: "", + comment: "", + }, + { + name: "Ready to Issue", + date: null, + description: "", + comment: "", + }, + { + name: "Issued", + date: null, + description: "", + comment: "", + }, + { + name: "Completed", + date: null, + description: "", + comment: "", + }, + { + name: "Invoiced", + date: null, + description: "", + comment: "", + }, + { + name: "Cancel/Void", + date: null, + description: "", + comment: "", + }, + { + name: "Expired", + date: null, + description: "", + comment: "", + }, +];