diff --git a/node/src/gql/query/mentor-client-data.ts b/node/src/gql/query/mentor-client-data.ts index 1c673b2..1e7b616 100644 --- a/node/src/gql/query/mentor-client-data.ts +++ b/node/src/gql/query/mentor-client-data.ts @@ -22,7 +22,7 @@ import { import { AnswerMedia } from '../../models/Answer'; import { Question, QuestionType } from '../../models/Question'; import SettingModel, { Config } from '../../models/Setting'; -import { SubjectQuestion, Topic } from '../../models/Subject'; +import { Category, SubjectQuestion, Topic } from '../../models/Subject'; import OrganizationModel, { Organization } from '../../models/Organization'; import { User } from '../../models/User'; import { isAnswerComplete, Mentor } from '../../models/Mentor'; @@ -36,6 +36,7 @@ import { IExternalVideoIds, externalVideoIdsDefault, } from '../mutation/api/update-answers'; +import { UseDefaultTopics } from 'gql/mutation/me/helpers'; export interface MentorClientData { _id: string; @@ -126,7 +127,8 @@ async function getQuestions( async function getCompletedQuestions( mentor: Mentor, sQuestions: SubjectQuestion[], - questions: Question[] + questions: Question[], + categories: Category[] ): Promise { let answers = await AnswerModel.find({ mentor: mentor._id, @@ -140,7 +142,30 @@ async function getCompletedQuestions( ) ); const questionIds = answers.map((a) => `${a.question}`); - return sQuestions.filter((sq) => questionIds.includes(`${sq.question}`)); + const completedQuestions = sQuestions.filter((sq) => + questionIds.includes(`${sq.question}`) + ); + // Add category default topics + const subjectQuestionsWithUpdatedTopics: SubjectQuestion[] = + completedQuestions.map((sQuestion) => { + if (!sQuestion.category) { + return sQuestion; + } + const shouldAddDefaultTopics = + sQuestion.useDefaultTopics === UseDefaultTopics.TRUE || + (sQuestion.useDefaultTopics === UseDefaultTopics.DEFAULT && + sQuestion.topics.length === 0); + if (!shouldAddDefaultTopics) { + return sQuestion; + } + const category = categories.find((c) => c.id === sQuestion.category); + if (!category) { + return sQuestion; + } + sQuestion.topics = [...sQuestion.topics, ...category.defaultTopics]; + return sQuestion; + }); + return subjectQuestionsWithUpdatedTopics; } export const mentorData = { @@ -191,13 +216,19 @@ export const mentorData = { // get recorded questions in subject order const sqs = subject.questions; questions = await getQuestions(mentor, sqs); - sQuestions = await getCompletedQuestions(mentor, sqs, questions); + sQuestions = await getCompletedQuestions( + mentor, + sqs, + questions, + subject.categories + ); } // no specified or default subject, use all subjects else { const subjects = await SubjectModel.find({ _id: { $in: mentor.subjects }, }); + const allCategories = subjects.map((s) => s.categories).flat(); // get topics in alphabetical order topics = subjects.reduce((acc, cur) => { const newTopics = cur.topics.filter( @@ -211,7 +242,12 @@ export const mentorData = { // get recorded questions in alphabetical order const sqs = subjects.reduce((acc, cur) => [...acc, ...cur.questions], []); questions = await getQuestions(mentor, sqs); - sQuestions = await getCompletedQuestions(mentor, sqs, questions); + sQuestions = await getCompletedQuestions( + mentor, + sqs, + questions, + allCategories + ); sQuestions.sort((a, b) => { const qa = questions.find((q) => `${q._id}` === `${a.question}`); const qb = questions.find((q) => `${q._id}` === `${b.question}`); diff --git a/node/test/fixtures/mongodb/data-default.js b/node/test/fixtures/mongodb/data-default.js index c091c49..df0946b 100644 --- a/node/test/fixtures/mongodb/data-default.js +++ b/node/test/fixtures/mongodb/data-default.js @@ -118,6 +118,13 @@ module.exports = { mentorIds: ['5ffdf41a1ee2c62119991114'], userRole: 'USER', }, + { + _id: ObjectId('5ffdf41a1ee2c62119991235'), + name: 'Test Default Topics User', + email: 'defaultTopics@mentor.com', + mentorIds: ['5ffdf41a1ee2c62119991234'], + userRole: 'USER', + }, ], mentors: [ @@ -252,6 +259,17 @@ module.exports = { mentorConfig: ObjectId('5ffdf41a1ee2c62111111132'), lockedToConfig: true, }, + { + _id: ObjectId('5ffdf41a1ee2c62119991234'), + name: 'Test Default Topics Mentor', + firstName: 'DefaultTopics', + isPrivate: false, + user: ObjectId('5ffdf41a1ee2c62119991235'), + subjects: [ObjectId('5ffdf41a1ee2c62119991236')], + keywords: ['Nonbinary'], + orgPermissions: [], + lockedToConfig: false, + }, ], mentorpanels: [ @@ -367,6 +385,57 @@ module.exports = { questions: [{ question: ObjectId('511111111111111111111115') }], deleted: true, }, + { + _id: ObjectId('5ffdf41a1ee2c62119991236'), + name: 'Subject Topic Question Test', + description: 'Testing subject question test', + categories: [ + { + id: 'category', + name: 'Test Category', + description: 'A test category', + defaultTopics: ['5ffdf41a1ee2c62119991237'], + }, + ], + topics: [ + { + id: ObjectId('5ffdf41a1ee2c62320b21ec3'), + name: 'Unused Category', + description: 'Unused Category', + }, + { + id: ObjectId('5ffdf41a1ee2c62119991237'), + name: '(Default Topic) Test Category', + description: 'Categories default topic', + }, + ], + questions: [ + { + question: ObjectId('511111111111111111111115'), + topics: [], + category: 'category', + useDefaultTopics: 'TRUE', + }, + { + question: ObjectId('511111111111111111111113'), + topics: [], + category: 'category', + // useDefaultTopics: 'DEFAULT', should automatically be default + }, + { + question: ObjectId('511111111111111111111117'), + topics: [], + category: 'category', + useDefaultTopics: 'FALSE', + }, + { + question: ObjectId('511111111111111111111114'), + topics: [], + category: '', + useDefaultTopics: 'DEFAULT', + }, + ], + }, ], questions: [ @@ -538,6 +607,82 @@ module.exports = { url: 'videos/5ffdf41a1ee2c62111111111/511111111111111111111111/mobile.mp4', }, }, + { + _id: ObjectId('511111111111111111111196'), + mentor: ObjectId('5ffdf41a1ee2c62119991234'), + question: ObjectId('511111111111111111111115'), + hasEditedTranscript: true, + transcript: 'answer transcript', + video: 'https://idle/url', + status: 'COMPLETE', + webMedia: { + type: 'video', + tag: 'web', + url: 'videos/5ffdf41a1ee2c62111111111/511111111111111111111111/web.mp4', + }, + mobileMedia: { + type: 'video', + tag: 'mobile', + url: 'videos/5ffdf41a1ee2c62111111111/511111111111111111111111/mobile.mp4', + }, + }, + { + _id: ObjectId('511111111111111111111197'), + mentor: ObjectId('5ffdf41a1ee2c62119991234'), + question: ObjectId('511111111111111111111113'), + hasEditedTranscript: true, + transcript: 'answer transcript', + video: 'https://idle/url', + status: 'COMPLETE', + webMedia: { + type: 'video', + tag: 'web', + url: 'videos/5ffdf41a1ee2c62111111111/511111111111111111111111/web.mp4', + }, + mobileMedia: { + type: 'video', + tag: 'mobile', + url: 'videos/5ffdf41a1ee2c62111111111/511111111111111111111111/mobile.mp4', + }, + }, + { + _id: ObjectId('511111111111111111111198'), + mentor: ObjectId('5ffdf41a1ee2c62119991234'), + question: ObjectId('511111111111111111111117'), + hasEditedTranscript: true, + transcript: 'answer transcript', + video: 'https://idle/url', + status: 'COMPLETE', + webMedia: { + type: 'video', + tag: 'web', + url: 'videos/5ffdf41a1ee2c62111111111/511111111111111111111111/web.mp4', + }, + mobileMedia: { + type: 'video', + tag: 'mobile', + url: 'videos/5ffdf41a1ee2c62111111111/511111111111111111111111/mobile.mp4', + }, + }, + { + _id: ObjectId('511111111111111111111199'), + mentor: ObjectId('5ffdf41a1ee2c62119991234'), + question: ObjectId('511111111111111111111114'), + hasEditedTranscript: true, + transcript: 'answer transcript', + video: 'https://idle/url', + status: 'COMPLETE', + webMedia: { + type: 'video', + tag: 'web', + url: 'videos/5ffdf41a1ee2c62111111111/511111111111111111111111/web.mp4', + }, + mobileMedia: { + type: 'video', + tag: 'mobile', + url: 'videos/5ffdf41a1ee2c62111111111/511111111111111111111111/mobile.mp4', + }, + }, ], userquestions: [ diff --git a/node/test/graphql/query/answers.spec.ts b/node/test/graphql/query/answers.spec.ts index f580f72..0ddbd45 100644 --- a/node/test/graphql/query/answers.spec.ts +++ b/node/test/graphql/query/answers.spec.ts @@ -43,50 +43,48 @@ describe('answers', () => { }`, }); expect(response.status).to.equal(200); - expect(response.body.data.answers).to.eql({ - edges: [ - { - node: { - _id: '511111111111111111111195', - externalVideoIds: { - wistiaId: '', - }, + expect(response.body.data.answers.edges).to.deep.include.members([ + { + node: { + _id: '511111111111111111111195', + externalVideoIds: { + wistiaId: '', }, }, - { - node: { - _id: '511111111111111111111174', - externalVideoIds: { - wistiaId: '', - }, + }, + { + node: { + _id: '511111111111111111111174', + externalVideoIds: { + wistiaId: '', }, }, - { - node: { - _id: '511111111111111111111114', - externalVideoIds: { - wistiaId: '', - }, + }, + { + node: { + _id: '511111111111111111111114', + externalVideoIds: { + wistiaId: '', }, }, - { - node: { - _id: '511111111111111111111113', - externalVideoIds: { - wistiaId: '', - }, + }, + { + node: { + _id: '511111111111111111111113', + externalVideoIds: { + wistiaId: '', }, }, - { - node: { - _id: '511111111111111111111112', - externalVideoIds: { - wistiaId: '5ffdf41a1ee2c62111111111-wistia-id', - }, + }, + { + node: { + _id: '511111111111111111111112', + externalVideoIds: { + wistiaId: '5ffdf41a1ee2c62111111111-wistia-id', }, }, - ], - }); + }, + ]); }); it('does not get answers from private mentors if not owner or super user', async () => { @@ -106,35 +104,33 @@ describe('answers', () => { }`, }); expect(response.status).to.equal(200); - expect(response.body.data.answers).to.eql({ - edges: [ - { - node: { - _id: '511111111111111111111195', - }, + expect(response.body.data.answers.edges).to.deep.include.members([ + { + node: { + _id: '511111111111111111111195', }, - { - node: { - _id: '511111111111111111111174', - }, + }, + { + node: { + _id: '511111111111111111111174', }, - { - node: { - _id: '511111111111111111111114', - }, + }, + { + node: { + _id: '511111111111111111111114', }, - { - node: { - _id: '511111111111111111111113', - }, + }, + { + node: { + _id: '511111111111111111111113', }, - { - node: { - _id: '511111111111111111111112', - }, + }, + { + node: { + _id: '511111111111111111111112', }, - ], - }); + }, + ]); }); it('gets answers from private mentor if content manager', async () => { @@ -154,40 +150,38 @@ describe('answers', () => { }`, }); expect(response.status).to.equal(200); - expect(response.body.data.answers).to.eql({ - edges: [ - { - node: { - _id: '511111111111111111111195', - }, + expect(response.body.data.answers.edges).to.deep.include.members([ + { + node: { + _id: '511111111111111111111195', }, - { - node: { - _id: '511111111111111111111174', - }, + }, + { + node: { + _id: '511111111111111111111174', }, - { - node: { - _id: '511111111111111111111119', - }, + }, + { + node: { + _id: '511111111111111111111119', }, - { - node: { - _id: '511111111111111111111114', - }, + }, + { + node: { + _id: '511111111111111111111114', }, - { - node: { - _id: '511111111111111111111113', - }, + }, + { + node: { + _id: '511111111111111111111113', }, - { - node: { - _id: '511111111111111111111112', - }, + }, + { + node: { + _id: '511111111111111111111112', }, - ], - }); + }, + ]); }); it('gets answers from private mentor if admin', async () => { @@ -207,40 +201,38 @@ describe('answers', () => { }`, }); expect(response.status).to.equal(200); - expect(response.body.data.answers).to.eql({ - edges: [ - { - node: { - _id: '511111111111111111111195', - }, + expect(response.body.data.answers.edges).to.deep.include.members([ + { + node: { + _id: '511111111111111111111195', }, - { - node: { - _id: '511111111111111111111174', - }, + }, + { + node: { + _id: '511111111111111111111174', }, - { - node: { - _id: '511111111111111111111119', - }, + }, + { + node: { + _id: '511111111111111111111119', }, - { - node: { - _id: '511111111111111111111114', - }, + }, + { + node: { + _id: '511111111111111111111114', }, - { - node: { - _id: '511111111111111111111113', - }, + }, + { + node: { + _id: '511111111111111111111113', }, - { - node: { - _id: '511111111111111111111112', - }, + }, + { + node: { + _id: '511111111111111111111112', }, - ], - }); + }, + ]); }); it('gets answers from private mentor if owner', async () => { @@ -260,39 +252,37 @@ describe('answers', () => { }`, }); expect(response.status).to.equal(200); - expect(response.body.data.answers).to.eql({ - edges: [ - { - node: { - _id: '511111111111111111111195', - }, + expect(response.body.data.answers.edges).to.deep.include.members([ + { + node: { + _id: '511111111111111111111195', }, - { - node: { - _id: '511111111111111111111174', - }, + }, + { + node: { + _id: '511111111111111111111174', }, - { - node: { - _id: '511111111111111111111119', - }, + }, + { + node: { + _id: '511111111111111111111119', }, - { - node: { - _id: '511111111111111111111114', - }, + }, + { + node: { + _id: '511111111111111111111114', }, - { - node: { - _id: '511111111111111111111113', - }, + }, + { + node: { + _id: '511111111111111111111113', }, - { - node: { - _id: '511111111111111111111112', - }, + }, + { + node: { + _id: '511111111111111111111112', }, - ], - }); + }, + ]); }); }); diff --git a/node/test/graphql/query/mentor-client-data.spec.ts b/node/test/graphql/query/mentor-client-data.spec.ts index 61e88d7..04685c1 100644 --- a/node/test/graphql/query/mentor-client-data.spec.ts +++ b/node/test/graphql/query/mentor-client-data.spec.ts @@ -221,4 +221,52 @@ describe('mentorClientData', () => { utterances: [], }); }); + + it('get mentorClientData topicsQuestions', async () => { + const response = await request(app) + .post('/graphql') + .send({ + query: `query { + mentorClientData(mentor: "5ffdf41a1ee2c62119991234") { + _id + name + title + mentorType + topicQuestions { + topic + questions + } + utterances { + _id + name + transcript + webMedia { + type + tag + url + } + mobileMedia { + type + tag + url + } + } + } + }`, + }); + expect(response.status).to.equal(200); + expect(response.body.data.mentorClientData).to.eql({ + _id: '5ffdf41a1ee2c62119991234', + name: 'Test Default Topics Mentor', + title: null, + mentorType: 'VIDEO', + topicQuestions: [ + { + topic: '(Default Topic) Test Category', + questions: ['Is STEM fun?', 'How old are you?'], + }, + ], + utterances: [], + }); + }); }); diff --git a/node/test/graphql/query/mentors-by-keyword.spec.ts b/node/test/graphql/query/mentors-by-keyword.spec.ts index 4b53ef4..c7d9b3d 100644 --- a/node/test/graphql/query/mentors-by-keyword.spec.ts +++ b/node/test/graphql/query/mentors-by-keyword.spec.ts @@ -37,7 +37,7 @@ describe('mentorsByKeyword', () => { }`, }); expect(response.status).to.equal(200); - expect(response.body.data.mentorsByKeyword).to.eql([ + expect(response.body.data.mentorsByKeyword).to.deep.include.members([ { _id: '5ffdf41a1ee2c62111111119', name: 'Aaron Klunder', @@ -79,7 +79,7 @@ describe('mentorsByKeyword', () => { }`, }); expect(response.status).to.equal(200); - expect(response.body.data.mentorsByKeyword).to.eql([ + expect(response.body.data.mentorsByKeyword).to.deep.include.members([ { _id: '5ffdf41a1ee2c62111111119', name: 'Aaron Klunder', @@ -121,7 +121,7 @@ describe('mentorsByKeyword', () => { }`, }); expect(response.status).to.equal(200); - expect(response.body.data.mentorsByKeyword).to.eql([ + expect(response.body.data.mentorsByKeyword).to.deep.include.members([ { _id: '5ffdf41a1ee2c62111111119', name: 'Aaron Klunder', @@ -167,7 +167,7 @@ describe('mentorsByKeyword', () => { }`, }); expect(response.status).to.equal(200); - expect(response.body.data.mentorsByKeyword).to.eql([ + expect(response.body.data.mentorsByKeyword).to.deep.include.members([ { _id: '5ffdf41a1ee2c62111111119', name: 'Aaron Klunder', @@ -213,7 +213,7 @@ describe('mentorsByKeyword', () => { }`, }); expect(response.status).to.equal(200); - expect(response.body.data.mentorsByKeyword).to.eql([ + expect(response.body.data.mentorsByKeyword).to.deep.include.members([ { _id: '5ffdf41a1ee2c62111111119', name: 'Aaron Klunder', @@ -276,6 +276,9 @@ describe('mentorsByKeyword', () => { { name: 'Locked Down Mentor', }, + { + name: 'Test Default Topics Mentor', + }, ]); }); @@ -292,6 +295,9 @@ describe('mentorsByKeyword', () => { }); expect(response.status).to.equal(200); expect(response.body.data.mentorsByKeyword).to.eql([ + { + name: 'Test Default Topics Mentor', + }, { name: 'Locked Down Mentor', }, @@ -326,6 +332,9 @@ describe('mentorsByKeyword', () => { }); expect(response.status).to.equal(200); expect(response.body.data.mentorsByKeyword).to.eql([ + { + name: 'Test Default Topics Mentor', + }, { name: 'Locked Down Mentor', }, @@ -426,6 +435,9 @@ describe('mentorsByKeyword', () => { { name: 'Locked Down Mentor', }, + { + name: 'Test Default Topics Mentor', + }, ]); // sort female first response = await request(app) @@ -458,6 +470,9 @@ describe('mentorsByKeyword', () => { { name: 'Locked Down Mentor', }, + { + name: 'Test Default Topics Mentor', + }, ]); // sort male + stem first response = await request(app) @@ -492,6 +507,9 @@ describe('mentorsByKeyword', () => { { name: 'Locked Down Mentor', }, + { + name: 'Test Default Topics Mentor', + }, ]); }); diff --git a/node/test/graphql/query/subjects.spec.ts b/node/test/graphql/query/subjects.spec.ts index bdb5bce..240ac81 100644 --- a/node/test/graphql/query/subjects.spec.ts +++ b/node/test/graphql/query/subjects.spec.ts @@ -45,35 +45,29 @@ describe('subjects', () => { }`, }); expect(response.status).to.equal(200); - expect(response.body.data.subjects).to.eql({ - edges: [ - { - node: { - _id: '5ffdf41a1ee2c62320b49eb3', - name: 'STEM', - isRequired: false, - }, + expect(response.body.data.subjects.edges).to.deep.include.members([ + { + node: { + _id: '5ffdf41a1ee2c62320b49eb3', + name: 'STEM', + isRequired: false, }, - { - node: { - _id: '5ffdf41a1ee2c62320b49eb2', - name: 'Background', - isRequired: true, - }, + }, + { + node: { + _id: '5ffdf41a1ee2c62320b49eb2', + name: 'Background', + isRequired: true, }, - { - node: { - _id: '5ffdf41a1ee2c62320b49eb1', - name: 'Repeat After Me', - isRequired: true, - }, + }, + { + node: { + _id: '5ffdf41a1ee2c62320b49eb1', + name: 'Repeat After Me', + isRequired: true, }, - ], - pageInfo: { - hasNextPage: false, - endCursor: null, }, - }); + ]); }); it('does not get deleted subjects', async () => { @@ -144,6 +138,12 @@ describe('subjects', () => { name: 'STEM', }, }, + { + node: { + _id: '5ffdf41a1ee2c62119991236', + name: 'Subject Topic Question Test', + }, + }, ], pageInfo: { hasNextPage: false, @@ -174,6 +174,12 @@ describe('subjects', () => { expect(response.status).to.equal(200); expect(response.body.data.subjects).to.eql({ edges: [ + { + node: { + _id: '5ffdf41a1ee2c62119991236', + name: 'Subject Topic Question Test', + }, + }, { node: { _id: '5ffdf41a1ee2c62320b49eb3', @@ -273,6 +279,11 @@ describe('subjects', () => { _id: '5ffdf41a1ee2c62320b49eb1', }, }, + { + node: { + _id: '5ffdf41a1ee2c62119991236', + }, + }, ], pageInfo: { hasPreviousPage: true,