Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions docs/ASSIGNMENT_STATUS_FLOW.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
# Assignment Status Flow

This diagram describes how an engagement assignment moves between statuses and the conditions for each transition.
Assignment rows are preserved after terminal transitions; unassignment and assignment removal mark active rows as `TERMINATED` instead of deleting them.

```mermaid
stateDiagram-v2
Expand Down
2 changes: 1 addition & 1 deletion packages/engagements-prisma-client/edge.js
Original file line number Diff line number Diff line change
Expand Up @@ -248,7 +248,7 @@ const config = {
"clientVersion": "7.2.0",
"engineVersion": "0c8ef2ce45c83248ab3df073180d5eda9e8be7a3",
"activeProvider": "postgresql",
"inlineSchema": "generator client {\n provider = \"prisma-client-js\"\n}\n\ngenerator externalClient {\n provider = \"prisma-client-js\"\n output = \"../packages/engagements-prisma-client\"\n binaryTargets = [\"native\", \"debian-openssl-3.0.x\"]\n}\n\ndatasource db {\n provider = \"postgresql\"\n}\n\nenum EngagementStatus {\n OPEN\n ACTIVE\n CANCELLED\n CLOSED\n ON_HOLD\n}\n\nenum ApplicationStatus {\n SUBMITTED\n UNDER_REVIEW\n SELECTED\n ACCEPTED\n REJECTED\n}\n\nenum AssignmentStatus {\n SELECTED\n OFFER_REJECTED\n ASSIGNED\n COMPLETED\n TERMINATED\n}\n\nenum Role {\n DESIGNER\n SOFTWARE_DEVELOPER\n DATA_SCIENTIST\n DATA_ENGINEER\n}\n\nenum Workload {\n FULL_TIME\n FRACTIONAL\n}\n\nenum AnticipatedStart {\n IMMEDIATE\n FEW_DAYS\n FEW_WEEKS\n}\n\nmodel Engagement {\n id String @id @default(uuid())\n projectId String\n title String\n description String\n durationStartDate DateTime?\n durationEndDate DateTime?\n durationWeeks Int?\n durationMonths Int?\n timeZones String[]\n countries String[]\n requiredSkills String[]\n anticipatedStart AnticipatedStart\n status EngagementStatus @default(OPEN)\n isPrivate Boolean @default(false)\n requiredMemberCount Int?\n role Role?\n workload Workload?\n compensationRange String?\n createdAt DateTime @default(now())\n createdBy String\n updatedAt DateTime @updatedAt\n updatedBy String?\n\n applications EngagementApplication[]\n assignments EngagementAssignment[]\n\n @@index([projectId])\n @@index([status])\n @@index([role])\n @@index([workload])\n}\n\nmodel EngagementApplication {\n id String @id @default(uuid())\n engagementId String\n userId String\n handle String?\n email String\n name String\n address String?\n mobileNumber String?\n coverLetter String?\n resumeUrl String?\n portfolioUrls String[]\n yearsOfExperience Int?\n availability String?\n status ApplicationStatus @default(SUBMITTED)\n createdAt DateTime @default(now())\n updatedAt DateTime @updatedAt\n updatedBy String?\n\n engagement Engagement @relation(fields: [engagementId], references: [id], onDelete: Cascade)\n\n @@unique([engagementId, userId])\n @@index([userId])\n @@index([engagementId])\n @@index([status])\n}\n\nmodel EngagementAssignment {\n id String @id @default(uuid())\n engagementId String\n memberId String\n memberHandle String\n status AssignmentStatus @default(SELECTED)\n agreementRate String?\n ratePerHour String?\n standardHoursPerWeek Float?\n durationMonths Int?\n otherRemarks String?\n terminationReason String?\n startDate DateTime?\n endDate DateTime?\n createdAt DateTime @default(now())\n updatedAt DateTime @updatedAt\n\n engagement Engagement @relation(fields: [engagementId], references: [id], onDelete: Cascade)\n feedback EngagementFeedback[]\n memberExperiences MemberExperience[]\n\n @@unique([engagementId, memberId])\n @@index([engagementId])\n @@index([memberId])\n}\n\nmodel EngagementFeedback {\n id String @id @default(uuid())\n engagementAssignmentId String\n feedbackText String\n rating Int?\n givenByMemberId String?\n givenByHandle String?\n givenByEmail String?\n secretToken String? @unique\n secretTokenExpiresAt DateTime?\n createdAt DateTime @default(now())\n updatedAt DateTime @updatedAt\n\n assignment EngagementAssignment @relation(fields: [engagementAssignmentId], references: [id], onDelete: Cascade)\n\n @@index([engagementAssignmentId])\n @@index([givenByMemberId])\n}\n\nmodel MemberExperience {\n id String @id @default(uuid())\n engagementAssignmentId String\n experienceText String\n createdAt DateTime @default(now())\n updatedAt DateTime @updatedAt\n\n assignment EngagementAssignment @relation(fields: [engagementAssignmentId], references: [id], onDelete: Cascade)\n\n @@index([engagementAssignmentId])\n}\n"
"inlineSchema": "generator client {\n provider = \"prisma-client-js\"\n}\n\ngenerator externalClient {\n provider = \"prisma-client-js\"\n output = \"../packages/engagements-prisma-client\"\n binaryTargets = [\"native\", \"debian-openssl-3.0.x\"]\n}\n\ndatasource db {\n provider = \"postgresql\"\n}\n\nenum EngagementStatus {\n OPEN\n ACTIVE\n CANCELLED\n CLOSED\n ON_HOLD\n}\n\nenum ApplicationStatus {\n SUBMITTED\n UNDER_REVIEW\n SELECTED\n ACCEPTED\n REJECTED\n}\n\nenum AssignmentStatus {\n SELECTED\n OFFER_REJECTED\n ASSIGNED\n COMPLETED\n TERMINATED\n}\n\nenum Role {\n DESIGNER\n SOFTWARE_DEVELOPER\n DATA_SCIENTIST\n DATA_ENGINEER\n}\n\nenum Workload {\n FULL_TIME\n FRACTIONAL\n}\n\nenum AnticipatedStart {\n IMMEDIATE\n FEW_DAYS\n FEW_WEEKS\n}\n\nmodel Engagement {\n id String @id @default(uuid())\n projectId String\n title String\n description String\n durationStartDate DateTime?\n durationEndDate DateTime?\n durationWeeks Int?\n durationMonths Int?\n timeZones String[]\n countries String[]\n requiredSkills String[]\n anticipatedStart AnticipatedStart\n status EngagementStatus @default(OPEN)\n isPrivate Boolean @default(false)\n requiredMemberCount Int?\n role Role?\n workload Workload?\n compensationRange String?\n createdAt DateTime @default(now())\n createdBy String\n updatedAt DateTime @updatedAt\n updatedBy String?\n\n applications EngagementApplication[]\n assignments EngagementAssignment[]\n\n @@index([projectId])\n @@index([status])\n @@index([role])\n @@index([workload])\n}\n\nmodel EngagementApplication {\n id String @id @default(uuid())\n engagementId String\n userId String\n handle String?\n email String\n name String\n address String?\n mobileNumber String?\n coverLetter String?\n resumeUrl String?\n portfolioUrls String[]\n yearsOfExperience Int?\n availability String?\n status ApplicationStatus @default(SUBMITTED)\n createdAt DateTime @default(now())\n updatedAt DateTime @updatedAt\n updatedBy String?\n\n engagement Engagement @relation(fields: [engagementId], references: [id], onDelete: Cascade)\n\n @@unique([engagementId, userId])\n @@index([userId])\n @@index([engagementId])\n @@index([status])\n}\n\nmodel EngagementAssignment {\n id String @id @default(uuid())\n engagementId String\n memberId String\n memberHandle String\n status AssignmentStatus @default(SELECTED)\n agreementRate String?\n ratePerHour String?\n standardHoursPerWeek Float?\n durationMonths Int?\n otherRemarks String?\n terminationReason String?\n startDate DateTime?\n endDate DateTime?\n createdAt DateTime @default(now())\n updatedAt DateTime @updatedAt\n\n engagement Engagement @relation(fields: [engagementId], references: [id], onDelete: Restrict)\n feedback EngagementFeedback[]\n memberExperiences MemberExperience[]\n\n @@index([engagementId])\n @@index([engagementId, memberId])\n @@index([memberId])\n}\n\nmodel EngagementFeedback {\n id String @id @default(uuid())\n engagementAssignmentId String\n feedbackText String\n rating Int?\n givenByMemberId String?\n givenByHandle String?\n givenByEmail String?\n secretToken String? @unique\n secretTokenExpiresAt DateTime?\n createdAt DateTime @default(now())\n updatedAt DateTime @updatedAt\n\n assignment EngagementAssignment @relation(fields: [engagementAssignmentId], references: [id], onDelete: Cascade)\n\n @@index([engagementAssignmentId])\n @@index([givenByMemberId])\n}\n\nmodel MemberExperience {\n id String @id @default(uuid())\n engagementAssignmentId String\n experienceText String\n createdAt DateTime @default(now())\n updatedAt DateTime @updatedAt\n\n assignment EngagementAssignment @relation(fields: [engagementAssignmentId], references: [id], onDelete: Cascade)\n\n @@index([engagementAssignmentId])\n}\n"
}

config.runtimeDataModel = JSON.parse("{\"models\":{\"Engagement\":{\"fields\":[{\"name\":\"id\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"projectId\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"title\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"description\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"durationStartDate\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"durationEndDate\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"durationWeeks\",\"kind\":\"scalar\",\"type\":\"Int\"},{\"name\":\"durationMonths\",\"kind\":\"scalar\",\"type\":\"Int\"},{\"name\":\"timeZones\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"countries\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"requiredSkills\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"anticipatedStart\",\"kind\":\"enum\",\"type\":\"AnticipatedStart\"},{\"name\":\"status\",\"kind\":\"enum\",\"type\":\"EngagementStatus\"},{\"name\":\"isPrivate\",\"kind\":\"scalar\",\"type\":\"Boolean\"},{\"name\":\"requiredMemberCount\",\"kind\":\"scalar\",\"type\":\"Int\"},{\"name\":\"role\",\"kind\":\"enum\",\"type\":\"Role\"},{\"name\":\"workload\",\"kind\":\"enum\",\"type\":\"Workload\"},{\"name\":\"compensationRange\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"createdAt\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"createdBy\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"updatedAt\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"updatedBy\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"applications\",\"kind\":\"object\",\"type\":\"EngagementApplication\",\"relationName\":\"EngagementToEngagementApplication\"},{\"name\":\"assignments\",\"kind\":\"object\",\"type\":\"EngagementAssignment\",\"relationName\":\"EngagementToEngagementAssignment\"}],\"dbName\":null},\"EngagementApplication\":{\"fields\":[{\"name\":\"id\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"engagementId\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"userId\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"handle\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"email\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"name\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"address\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"mobileNumber\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"coverLetter\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"resumeUrl\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"portfolioUrls\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"yearsOfExperience\",\"kind\":\"scalar\",\"type\":\"Int\"},{\"name\":\"availability\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"status\",\"kind\":\"enum\",\"type\":\"ApplicationStatus\"},{\"name\":\"createdAt\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"updatedAt\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"updatedBy\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"engagement\",\"kind\":\"object\",\"type\":\"Engagement\",\"relationName\":\"EngagementToEngagementApplication\"}],\"dbName\":null},\"EngagementAssignment\":{\"fields\":[{\"name\":\"id\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"engagementId\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"memberId\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"memberHandle\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"status\",\"kind\":\"enum\",\"type\":\"AssignmentStatus\"},{\"name\":\"agreementRate\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"ratePerHour\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"standardHoursPerWeek\",\"kind\":\"scalar\",\"type\":\"Float\"},{\"name\":\"durationMonths\",\"kind\":\"scalar\",\"type\":\"Int\"},{\"name\":\"otherRemarks\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"terminationReason\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"startDate\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"endDate\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"createdAt\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"updatedAt\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"engagement\",\"kind\":\"object\",\"type\":\"Engagement\",\"relationName\":\"EngagementToEngagementAssignment\"},{\"name\":\"feedback\",\"kind\":\"object\",\"type\":\"EngagementFeedback\",\"relationName\":\"EngagementAssignmentToEngagementFeedback\"},{\"name\":\"memberExperiences\",\"kind\":\"object\",\"type\":\"MemberExperience\",\"relationName\":\"EngagementAssignmentToMemberExperience\"}],\"dbName\":null},\"EngagementFeedback\":{\"fields\":[{\"name\":\"id\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"engagementAssignmentId\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"feedbackText\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"rating\",\"kind\":\"scalar\",\"type\":\"Int\"},{\"name\":\"givenByMemberId\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"givenByHandle\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"givenByEmail\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"secretToken\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"secretTokenExpiresAt\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"createdAt\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"updatedAt\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"assignment\",\"kind\":\"object\",\"type\":\"EngagementAssignment\",\"relationName\":\"EngagementAssignmentToEngagementFeedback\"}],\"dbName\":null},\"MemberExperience\":{\"fields\":[{\"name\":\"id\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"engagementAssignmentId\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"experienceText\",\"kind\":\"scalar\",\"type\":\"String\"},{\"name\":\"createdAt\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"updatedAt\",\"kind\":\"scalar\",\"type\":\"DateTime\"},{\"name\":\"assignment\",\"kind\":\"object\",\"type\":\"EngagementAssignment\",\"relationName\":\"EngagementAssignmentToMemberExperience\"}],\"dbName\":null}},\"enums\":{},\"types\":{}}")
Expand Down
8 changes: 1 addition & 7 deletions packages/engagements-prisma-client/index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8102,7 +8102,6 @@ export namespace Prisma {

export type EngagementAssignmentWhereUniqueInput = Prisma.AtLeast<{
id?: string
engagementId_memberId?: EngagementAssignmentEngagementIdMemberIdCompoundUniqueInput
AND?: EngagementAssignmentWhereInput | EngagementAssignmentWhereInput[]
OR?: EngagementAssignmentWhereInput[]
NOT?: EngagementAssignmentWhereInput | EngagementAssignmentWhereInput[]
Expand All @@ -8123,7 +8122,7 @@ export namespace Prisma {
engagement?: XOR<EngagementScalarRelationFilter, EngagementWhereInput>
feedback?: EngagementFeedbackListRelationFilter
memberExperiences?: MemberExperienceListRelationFilter
}, "id" | "engagementId_memberId">
}, "id">

export type EngagementAssignmentOrderByWithAggregationInput = {
id?: SortOrder
Expand Down Expand Up @@ -9387,11 +9386,6 @@ export namespace Prisma {
_count?: SortOrder
}

export type EngagementAssignmentEngagementIdMemberIdCompoundUniqueInput = {
engagementId: string
memberId: string
}

export type EngagementAssignmentCountOrderByAggregateInput = {
id?: SortOrder
engagementId?: SortOrder
Expand Down
Loading