Skip to content

Commit

Permalink
use it as actual submitContract
Browse files Browse the repository at this point in the history
  • Loading branch information
mojotalantikite committed Mar 6, 2024
1 parent b9942dd commit e5380b7
Show file tree
Hide file tree
Showing 2 changed files with 18 additions and 171 deletions.
Original file line number Diff line number Diff line change
@@ -1,9 +1,6 @@
import { sharedTestPrismaClient } from '../../testHelpers/storeHelpers'
import { v4 as uuidv4 } from 'uuid'
import {
submitContract,
submitContractSubmitInfosFirst,
} from './submitContract'
import { submitContract } from './submitContract'
import { insertDraftContract } from './insertContract'
import { insertDraftRate } from './insertRate'
import { submitRate } from './submitRate'
Expand Down Expand Up @@ -49,36 +46,43 @@ describe('submitContract', () => {
}

// create a draft rate
const draftRateData = mockInsertRateArgs({
const draftRateDataA = mockInsertRateArgs({
rateCertificationName: 'rate-cert-name',
})

const draftRateDataB = mockInsertRateArgs({
rateCertificationName: 'rate-cert-number-two',
})

const draftContractWithRates = must(
await updateDraftContractWithRates(client, {
contractID: contract.id,
formData: draftContractForm2,
rateFormDatas: [draftRateData],
rateFormDatas: [draftRateDataA, draftRateDataB],
})
)

// submit the draft contract and connect submitInfos
const result = must(
await submitContractSubmitInfosFirst(client, {
await submitContract(client, {
contractID: draftContractWithRates.id,
submittedByUserID: stateUser.id,
submittedReason: 'initial submit',
})
)
//console.info(JSON.stringify(result, null, ' '))

expect(result.status).toBe('SUBMITTED')

// check that they have the same submitInfos
const contractSubmitInfo = result.revisions[0].submitInfo
const rateSubmitInfo = result.revisions[0].rateRevisions[0].submitInfo
const rateSubmitInfoA = result.revisions[0].rateRevisions[0].submitInfo
const rateSubmitInfoB = result.revisions[0].rateRevisions[1].submitInfo
expect(contractSubmitInfo).toBeDefined()
expect(rateSubmitInfo).toBeDefined()
expect(contractSubmitInfo).toEqual(rateSubmitInfo)
expect(rateSubmitInfoA).toBeDefined()
expect(rateSubmitInfoB).toBeDefined()
expect(contractSubmitInfo).toEqual(rateSubmitInfoA)
expect(contractSubmitInfo).toEqual(rateSubmitInfoB)
expect(rateSubmitInfoA).toEqual(rateSubmitInfoB)
})

it('creates a submission from a draft', async () => {
Expand Down
163 changes: 3 additions & 160 deletions services/app-api/src/postgres/contractAndRates/submitContract.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,174 +3,17 @@ import type { ContractType } from '../../domain-models/contractAndRates'
import { findContractWithHistory } from './findContractWithHistory'
import { NotFoundError } from '../postgresErrors'
import type { UpdateInfoType } from '../../domain-models'
import {
includeFullRate,
includeLatestSubmittedRateRev,
} from './prismaSubmittedRateHelpers'
import { includeFullRate } from './prismaSubmittedRateHelpers'

type SubmitContractArgsType = {
export type SubmitContractArgsType = {
contractID: string // revision ID
submittedByUserID: UpdateInfoType['updatedBy']
submittedReason: UpdateInfoType['updatedReason']
}
// Update the given revision
// * invalidate relationships of previous revision by marking as outdated
// * set the UpdateInfo
async function submitContract(
client: PrismaClient,
args: SubmitContractArgsType
): Promise<ContractType | NotFoundError | Error> {
const { contractID, submittedByUserID, submittedReason } = args
const currentDateTime = new Date()

try {
// Find current contract revision with related rates
// query only the submitted revisions on the related rates
return await client.$transaction(async (tx) => {
const currentRev = await tx.contractRevisionTable.findFirst({
where: {
contractID: contractID,
submitInfoID: null,
},
include: {
draftRates: {
include: includeLatestSubmittedRateRev,
},
},
})

if (!currentRev) {
const err = `PRISMA ERROR: Cannot find the current rev to submit with contract id: ${contractID}`
console.error(err)
return new NotFoundError(err)
}

// Given related rates, confirm rates valid by submitted by checking for revisions
// If rates have no revisions, we know it is invalid and can throw error
const relatedRateRevs = currentRev.draftRates.map(
(c) => c.revisions[0]
)
const everyRelatedRateIsSubmitted = relatedRateRevs.every(
(rev) => rev !== undefined
)
if (!everyRelatedRateIsSubmitted) {
const message =
'Attempted to submit a contract related to a rate that has not been submitted.'
console.error(message)
return new Error(message)
}

const updated = await tx.contractRevisionTable.update({
where: {
id: currentRev.id,
},
data: {
submitInfo: {
create: {
updatedAt: currentDateTime,
updatedByID: submittedByUserID,
updatedReason: submittedReason,
},
},
rateRevisions: {
createMany: {
data: relatedRateRevs.map((rev, idx) => ({
rateRevisionID: rev.id,
// Since rates come out the other side ordered by validAfter, we need to order things on the way in that way.
validAfter: new Date(
currentDateTime.getTime() -
relatedRateRevs.length +
idx +
1
),
})),
},
},
draftRates: {
set: [],
},
},
include: {
rateRevisions: {
include: {
rateRevision: true,
},
},
},
})

// oldRev is the previously submitted revision of this contract (the one just superseded by the update)
// on an initial submission, there won't be an oldRev
const oldRev = await tx.contractRevisionTable.findFirst({
where: {
contractID: updated.contractID,
NOT: {
id: updated.id,
},
},
include: {
rateRevisions: {
include: {
rateRevision: true,
},
},
},
orderBy: {
createdAt: 'desc',
},
})

// Take oldRev, invalidate all relationships and add any removed entries to the join table.
if (oldRev) {
// If any of the old rev's Rates aren't in the new Rates, add an entry in revisions join table
// isRemoval field shows that this is a previous rate related with this contract that is now removed
const oldRateRevs = oldRev.rateRevisions
.filter((rrevjoin) => !rrevjoin.validUntil)
.map((rrevjoin) => rrevjoin.rateRevision)
const removedRateRevs = oldRateRevs.filter(
(rrev) =>
!currentRev.draftRates
.map((r) => r.id)
.includes(rrev.rateID)
)

if (removedRateRevs.length > 0) {
await tx.rateRevisionsOnContractRevisionsTable.createMany({
data: removedRateRevs.map((rrev) => ({
contractRevisionID: updated.id,
rateRevisionID: rrev.id,
validAfter: currentDateTime,
validUntil: currentDateTime,
isRemoval: true,
})),
})
}

// Invalidate old revision join table links by updating validUntil
// these links are considered outdated going forward
await tx.rateRevisionsOnContractRevisionsTable.updateMany({
where: {
contractRevisionID: oldRev.id,
validUntil: null,
},
data: {
validUntil: currentDateTime,
},
})
}

return await findContractWithHistory(tx, contractID)
})
} catch (err) {
console.error('Prisma error submitting contract', err)
return err
}
}

export { submitContract }
export type { SubmitContractArgsType }

export async function submitContractSubmitInfosFirst(
export async function submitContract(
client: PrismaClient,
args: SubmitContractArgsType
): Promise<ContractType | NotFoundError | Error> {
Expand Down

0 comments on commit e5380b7

Please sign in to comment.