Skip to content

Commit

Permalink
MCR-4450: Update rate resolver to return questions field (#2804)
Browse files Browse the repository at this point in the history
* Add fetchRateWithQuestions query

* Update helpers to work with both types of questions.

* Fix import in indexContracts test

* Add questions field to rateResolver

* Use helper function to convert question to payload

* Update services/app-api/src/resolvers/rate/fetchRate.test.ts

* Update test.
  • Loading branch information
JasonLin0991 authored Oct 3, 2024
1 parent c73f239 commit cecad96
Show file tree
Hide file tree
Showing 13 changed files with 663 additions and 175 deletions.
22 changes: 20 additions & 2 deletions services/app-api/src/domain-models/QuestionsType.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { z } from 'zod'
import { cmsUserSchema } from './UserType'
import { cmsUsersUnionSchema } from './UserType'
import { questionResponseType } from './QuestionResponseType'
import { divisionType } from './DivisionType'

Expand All @@ -12,7 +12,7 @@ const document = z.object({
const commonQuestionSchema = z.object({
id: z.string().uuid(),
createdAt: z.date(),
addedBy: cmsUserSchema,
addedBy: cmsUsersUnionSchema,
division: divisionType, // DMCO, DMCP, OACT
documents: z.array(document),
responses: z.array(questionResponseType),
Expand All @@ -30,17 +30,32 @@ const questionEdge = z.object({
node: question,
})

const rateQuestionEdge = z.object({
node: rateQuestion,
})

const questionList = z.object({
totalCount: z.number(),
edges: z.array(questionEdge),
})

const rateQuestionList = z.object({
totalCount: z.number(),
edges: z.array(rateQuestionEdge),
})

const indexQuestionsPayload = z.object({
DMCOQuestions: questionList,
DMCPQuestions: questionList,
OACTQuestions: questionList,
})

const indexRateQuestionsPayload = z.object({
DMCOQuestions: rateQuestionList,
DMCPQuestions: rateQuestionList,
OACTQuestions: rateQuestionList,
})

const createQuestionPayload = z.object({
question: question,
})
Expand Down Expand Up @@ -71,6 +86,8 @@ type QuestionList = z.infer<typeof questionList>

type Document = z.infer<typeof document>

type IndexRateQuestionsPayload = z.infer<typeof indexRateQuestionsPayload>

export type {
IndexQuestionsPayload,
CreateQuestionPayload,
Expand All @@ -80,6 +97,7 @@ export type {
QuestionList,
RateQuestionType,
CreateRateQuestionInputType,
IndexRateQuestionsPayload,
}

export {
Expand Down
12 changes: 10 additions & 2 deletions services/app-api/src/domain-models/UserType.ts
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ const cmsApproverUserSchema = baseUserSchema.extend({
divisionAssignment: divisionType.optional(),
})

const cmsUsersUnionSchema = z.union([cmsUserSchema, cmsApproverUserSchema])

const adminUserSchema = baseUserSchema.extend({
role: z.literal(userRolesSchema.enum.ADMIN_USER),
})
Expand All @@ -68,7 +70,7 @@ type CMSUserType = z.infer<typeof cmsUserSchema>

type CMSApproverUserType = z.infer<typeof cmsApproverUserSchema>

type CMSUsersUnionType = CMSUserType | CMSApproverUserType
type CMSUsersUnionType = z.infer<typeof cmsUsersUnionSchema>

type BaseUserType = z.infer<typeof baseUserSchema>

Expand All @@ -87,4 +89,10 @@ export type {
BaseUserType,
}

export { cmsUserSchema, stateUserSchema, userRolesSchema, baseUserSchema }
export {
cmsUserSchema,
stateUserSchema,
userRolesSchema,
baseUserSchema,
cmsUsersUnionSchema,
}
1 change: 1 addition & 0 deletions services/app-api/src/domain-models/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ export type {
QuestionList,
RateQuestionType,
CreateRateQuestionInputType,
IndexRateQuestionsPayload,
} from './QuestionsType'

export type {
Expand Down
1 change: 1 addition & 0 deletions services/app-api/src/postgres/questionResponse/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ export {
convertToIndexQuestionsPayload,
questionPrismaToDomainType,
rateQuestionPrismaToDomainType,
convertToIndexRateQuestionsPayload,
} from './questionHelpers'
export { insertQuestionResponse } from './insertQuestionResponse'
export { insertRateQuestion } from './insertRateQuestion'
Expand Down
97 changes: 48 additions & 49 deletions services/app-api/src/postgres/questionResponse/questionHelpers.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import type {
CMSUserType,
CMSUsersUnionType,
IndexQuestionsPayload,
IndexRateQuestionsPayload,
Question,
QuestionResponseType,
RateQuestionType,
Expand All @@ -22,7 +23,11 @@ const questionInclude = {
createdAt: 'desc',
},
},
addedBy: true,
addedBy: {
include: {
stateAssignments: true,
},
},
} satisfies Prisma.QuestionInclude

type PrismaQuestionType = Prisma.QuestionGetPayload<{
Expand All @@ -35,66 +40,60 @@ type PrismaRateQuestionType = Prisma.RateQuestionGetPayload<{

// Both types are similar only difference is one related to a contract and the other a rate.
const commonQuestionPrismaToDomainType = <
T extends PrismaQuestionType | PrismaRateQuestionType,
U extends Question | RateQuestionType,
P extends PrismaQuestionType | PrismaRateQuestionType,
R extends Question | RateQuestionType,
>(
prismaQuestion: T
): U =>
prismaQuestion: P
): R =>
({
...prismaQuestion,
addedBy: {
...prismaQuestion.addedBy,
stateAssignments: [],
} as CMSUserType,
addedBy: prismaQuestion.addedBy as CMSUsersUnionType,
responses: prismaQuestion.responses as QuestionResponseType[],
}) as unknown as U
}) as unknown as R

const questionPrismaToDomainType = commonQuestionPrismaToDomainType<
PrismaQuestionType,
Question
>
const rateQuestionPrismaToDomainType = commonQuestionPrismaToDomainType<
PrismaRateQuestionType,
RateQuestionType
>
const questionPrismaToDomainType = (
prismaQuestion: PrismaQuestionType
): Question => commonQuestionPrismaToDomainType(prismaQuestion)
const rateQuestionPrismaToDomainType = (
prismaQuestion: PrismaRateQuestionType
): RateQuestionType => commonQuestionPrismaToDomainType(prismaQuestion)

const convertToIndexQuestionsPayload = (
questions: Question[]
): IndexQuestionsPayload => {
const questionsPayload: IndexQuestionsPayload = {
DMCOQuestions: {
totalCount: 0,
edges: [],
},
DMCPQuestions: {
totalCount: 0,
edges: [],
},
OACTQuestions: {
totalCount: 0,
edges: [],
},
}

questions.forEach((question) => {
if (question.division === 'DMCP') {
questionsPayload.DMCPQuestions.edges.push({ node: question })
questionsPayload.DMCPQuestions.totalCount++
} else if (question.division === 'OACT') {
questionsPayload.OACTQuestions.edges.push({ node: question })
questionsPayload.OACTQuestions.totalCount++
} else if (question.division === 'DMCO') {
questionsPayload.DMCOQuestions.edges.push({ node: question })
questionsPayload.DMCOQuestions.totalCount++
}
const convertToCommonIndexQuestionsPayload = <
P extends Question | RateQuestionType,
R extends IndexQuestionsPayload | IndexRateQuestionsPayload,
>(
questions: P[]
): R => {
const getDivisionQuestionsEdge = (
division: 'DMCP' | 'DMCO' | 'OACT',
questions: P[]
) => ({
totalCount: questions.filter((q) => q.division === division).length,
edges: questions
.filter((q) => q.division === division)
.map((question) => ({ node: question })),
})

return questionsPayload
return {
DMCOQuestions: getDivisionQuestionsEdge('DMCO', questions),
DMCPQuestions: getDivisionQuestionsEdge('DMCP', questions),
OACTQuestions: getDivisionQuestionsEdge('OACT', questions),
} as unknown as R
}

const convertToIndexQuestionsPayload = (
contractQuestions: Question[]
): IndexQuestionsPayload =>
convertToCommonIndexQuestionsPayload(contractQuestions)
const convertToIndexRateQuestionsPayload = (
rateQuestions: RateQuestionType[]
): IndexRateQuestionsPayload =>
convertToCommonIndexQuestionsPayload(rateQuestions)

export {
questionInclude,
questionPrismaToDomainType,
convertToIndexQuestionsPayload,
convertToIndexRateQuestionsPayload,
rateQuestionPrismaToDomainType,
}
2 changes: 1 addition & 1 deletion services/app-api/src/resolvers/configureResolvers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -185,7 +185,7 @@ export function configureResolvers(
CMSUser: cmsUserResolver,
CMSApproverUser: cmsApproverUserResolver,
HealthPlanPackage: healthPlanPackageResolver(store),
Rate: rateResolver,
Rate: rateResolver(store),
RateRevision: rateRevisionResolver(store),
Contract: contractResolver(store),
UnlockedContract: unlockedContractResolver(),
Expand Down
46 changes: 2 additions & 44 deletions services/app-api/src/resolvers/contract/contractResolver.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ import {
setErrorAttributesOnActiveSpan,
setResolverDetailsOnActiveSpan,
} from '../attributeHelper'
import type { IndexQuestionsPayload } from '../../domain-models/QuestionsType'
import { convertToIndexQuestionsPayload } from '../../postgres/questionResponse'

export function contractResolver(store: Store): Resolvers['Contract'] {
return {
Expand Down Expand Up @@ -145,49 +145,7 @@ export function contractResolver(store: Store): Resolvers['Contract'] {
})
}

const dmcoQuestions = questionsForContract
.filter((question) => question.division === 'DMCO')
.map((question) => {
return {
node: {
...question,
},
}
})
const dmcpQuestions = questionsForContract
.filter((question) => question.division === 'DMCP')
.map((question) => {
return {
node: {
...question,
},
}
})
const oactQuestions = questionsForContract
.filter((question) => question.division === 'OACT')
.map((question) => {
return {
node: {
...question,
},
}
})

const questionPayload: IndexQuestionsPayload = {
DMCOQuestions: {
totalCount: dmcoQuestions.length,
edges: dmcoQuestions,
},
DMCPQuestions: {
totalCount: dmcpQuestions.length,
edges: dmcpQuestions,
},
OACTQuestions: {
totalCount: oactQuestions.length,
edges: oactQuestions,
},
}
return questionPayload
return convertToIndexQuestionsPayload(questionsForContract)
},
}
}
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import INDEX_CONTRACTS from '../../../../app-graphql/src/queries/indexContracts.graphql'
import INDEX_CONTRACTS from '../../../../app-graphql/src/queries/indexContractsForDashboard.graphql'
import {
constructTestPostgresServer,
createTestHealthPlanPackage,
Expand Down
Loading

0 comments on commit cecad96

Please sign in to comment.