From 525661c593ce8fdcef80c4627c8172057b559486 Mon Sep 17 00:00:00 2001 From: Julius Schlapbach <80708107+sjschlapbach@users.noreply.github.com> Date: Fri, 24 May 2024 14:46:18 +0200 Subject: [PATCH] enhance: add possibility to change live quiz name and displayname independent of status (#4131) --- .../sessions/LiveQuizNameChangeModal.tsx | 162 ++++++++++++++++++ .../src/components/sessions/Session.tsx | 20 ++- .../cypress/e2e/F-live-quiz-workflow.cy.ts | 24 ++- .../graphql/ops/MChangeLiveQuizName.graphql | 11 ++ packages/graphql/src/ops.schema.json | 61 +++++++ packages/graphql/src/ops.ts | 18 ++ packages/graphql/src/public/client.json | 1 + packages/graphql/src/public/schema.graphql | 1 + packages/graphql/src/public/server.json | 1 + packages/graphql/src/schema/mutation.ts | 13 ++ packages/graphql/src/services/sessions.ts | 23 +++ packages/i18n/messages/de.ts | 5 + packages/i18n/messages/en.ts | 4 + 13 files changed, 339 insertions(+), 5 deletions(-) create mode 100644 apps/frontend-manage/src/components/sessions/LiveQuizNameChangeModal.tsx create mode 100644 packages/graphql/src/graphql/ops/MChangeLiveQuizName.graphql diff --git a/apps/frontend-manage/src/components/sessions/LiveQuizNameChangeModal.tsx b/apps/frontend-manage/src/components/sessions/LiveQuizNameChangeModal.tsx new file mode 100644 index 0000000000..14c5a3949e --- /dev/null +++ b/apps/frontend-manage/src/components/sessions/LiveQuizNameChangeModal.tsx @@ -0,0 +1,162 @@ +import { useMutation } from '@apollo/client' +import { ChangeLiveQuizNameDocument } from '@klicker-uzh/graphql/dist/ops' +import { Button, FormikTextField, Modal, Toast } from '@uzh-bf/design-system' +import { Formik } from 'formik' +import { useTranslations } from 'next-intl' +import { useState } from 'react' +import { twMerge } from 'tailwind-merge' +import * as Yup from 'yup' + +interface LiveQuizNameChangeModalProps { + quizId: string + name: string + displayName: string + open: boolean + setOpen: (value: boolean) => void +} + +function LiveQuizNameChangeModal({ + quizId, + name, + displayName, + open, + setOpen, +}: LiveQuizNameChangeModalProps) { + const t = useTranslations() + const [changeLiveQuizName] = useMutation(ChangeLiveQuizNameDocument) + const [successToast, setSuccessToast] = useState(false) + const [errorToast, setErrorToast] = useState(false) + + const schema = Yup.object().shape({ + name: Yup.string().required(t('manage.sessionForms.sessionName')), + displayName: Yup.string().required( + t('manage.sessionForms.sessionDisplayName') + ), + }) + + return ( + <> + setOpen(false)} + title={t('manage.sessions.changeLiveQuizName')} + className={{ + content: 'w-[30rem] min-h-max h-max self-center pt-0', + title: 'text-xl', + }} + > + { + setSubmitting(true) + const result = await changeLiveQuizName({ + variables: { + id: quizId, + name: values.name, + displayName: values.displayName, + }, + optimisticResponse: { + __typename: 'Mutation', + changeLiveQuizName: { + id: quizId, + name: values.name, + displayName: values.displayName, + }, + }, + }) + + if (result.data?.changeLiveQuizName?.id) { + setSuccessToast(true) + setSubmitting(false) + setOpen(false) + } else { + setErrorToast(true) + setSubmitting(false) + } + }} + validationSchema={schema} + isInitialValid={true} + > + {({ isValid, isSubmitting, submitForm }) => ( + <> + true} + /> + +
+ + +
+ + )} +
+
+ + {t('manage.sessions.liveQuizNameChangeSuccess')} + + + {t('manage.sessions.liveQuizNameChangeError')} + + + ) +} + +export default LiveQuizNameChangeModal diff --git a/apps/frontend-manage/src/components/sessions/Session.tsx b/apps/frontend-manage/src/components/sessions/Session.tsx index 950d756ea7..9532077ed4 100644 --- a/apps/frontend-manage/src/components/sessions/Session.tsx +++ b/apps/frontend-manage/src/components/sessions/Session.tsx @@ -30,6 +30,7 @@ import { useRouter } from 'next/router' import { useState } from 'react' import DeletionModal from '../courses/modals/DeletionModal' import EmbeddingModal from './EmbeddingModal' +import LiveQuizNameChangeModal from './LiveQuizNameChangeModal' import { WizardMode } from './creation/SessionCreation' interface SessionProps { @@ -98,6 +99,7 @@ function Session({ session }: SessionProps) { const [embedModalOpen, setEmbedModalOpen] = useState(false) const [deletionModal, setDeletionModal] = useState(false) const [softDeletionModal, setSoftDeletionModal] = useState(false) + const [changeName, setChangeName] = useState(false) const timeIcon: Record = { [SessionStatus.Prepared]: faCalendarDays, @@ -134,7 +136,16 @@ function Session({ session }: SessionProps) { className="flex flex-row justify-between" data-cy="session-block" > -

{session.name}

+
+

{session.name}

+ setChangeName(true)} + className="hover:cursor-pointer" + data-cy={`change-liveQuiz-name-${session.name}`} + /> +
{session.blocks?.length !== 0 && ( <> @@ -366,6 +377,13 @@ function Session({ session }: SessionProps) { primaryData={{ cy: 'confirm-delete-live-quiz' }} secondaryData={{ cy: 'cancel-delete-live-quiz' }} /> + ) } diff --git a/cypress/cypress/e2e/F-live-quiz-workflow.cy.ts b/cypress/cypress/e2e/F-live-quiz-workflow.cy.ts index e6d7434149..358cd87729 100644 --- a/cypress/cypress/e2e/F-live-quiz-workflow.cy.ts +++ b/cypress/cypress/e2e/F-live-quiz-workflow.cy.ts @@ -60,13 +60,29 @@ describe('Different live-quiz workflows', () => { cy.get('[data-cy="load-session-list"]').click() cy.contains('[data-cy="session-block"]', sessionName) - // delete this session again + // rename the session + const newSessionName = uuid() + const newSessionDisplayName = uuid() cy.findByText(sessionName).should('exist') - cy.get(`[data-cy="delete-session-${sessionName}"]`).click() + cy.get(`[data-cy="change-liveQuiz-name-${sessionName}"]`).click() + cy.get('[data-cy="live-quiz-name-change-confirm"]').should( + 'not.be.disabled' + ) + cy.get('[data-cy="live-quiz-name-change-cancel"]').click() + cy.get(`[data-cy="change-liveQuiz-name-${sessionName}"]`).click() + cy.get('[data-cy="insert-live-quiz-name"]').clear().type(newSessionName) + cy.get('[data-cy="insert-live-quiz-display-name"]') + .clear() + .type(newSessionDisplayName) + cy.get('[data-cy="live-quiz-name-change-confirm"]').click() + + // delete this session again + cy.findByText(newSessionName).should('exist') + cy.get(`[data-cy="delete-session-${newSessionName}"]`).click() cy.get(`[data-cy="cancel-delete-live-quiz"]`).click() - cy.get(`[data-cy="delete-session-${sessionName}"]`).click() + cy.get(`[data-cy="delete-session-${newSessionName}"]`).click() cy.get(`[data-cy="confirm-delete-live-quiz"]`).click() - cy.findByText(sessionName).should('not.exist') + cy.findByText(newSessionName).should('not.exist') }) it('creates a session, starts it and aborts it and then restarts it', () => { diff --git a/packages/graphql/src/graphql/ops/MChangeLiveQuizName.graphql b/packages/graphql/src/graphql/ops/MChangeLiveQuizName.graphql new file mode 100644 index 0000000000..ed6946f37c --- /dev/null +++ b/packages/graphql/src/graphql/ops/MChangeLiveQuizName.graphql @@ -0,0 +1,11 @@ +mutation ChangeLiveQuizName( + $id: String! + $name: String! + $displayName: String! +) { + changeLiveQuizName(id: $id, name: $name, displayName: $displayName) { + id + name + displayName + } +} diff --git a/packages/graphql/src/ops.schema.json b/packages/graphql/src/ops.schema.json index 373988102c..fff1a152a5 100644 --- a/packages/graphql/src/ops.schema.json +++ b/packages/graphql/src/ops.schema.json @@ -6212,6 +6212,67 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "changeLiveQuizName", + "description": null, + "args": [ + { + "name": "displayName", + "description": null, + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "id", + "description": null, + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "name", + "description": null, + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + }, + "defaultValue": null, + "isDeprecated": false, + "deprecationReason": null + } + ], + "type": { + "kind": "OBJECT", + "name": "Session", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "changeParticipantLocale", "description": null, diff --git a/packages/graphql/src/ops.ts b/packages/graphql/src/ops.ts index 214a9f85c1..51788f4fa4 100644 --- a/packages/graphql/src/ops.ts +++ b/packages/graphql/src/ops.ts @@ -602,6 +602,7 @@ export type Mutation = { changeCourseDescription?: Maybe; changeEmailSettings?: Maybe; changeInitialSettings?: Maybe; + changeLiveQuizName?: Maybe; changeParticipantLocale?: Maybe; changeSessionSettings?: Maybe; changeShortname?: Maybe; @@ -734,6 +735,13 @@ export type MutationChangeInitialSettingsArgs = { }; +export type MutationChangeLiveQuizNameArgs = { + displayName: Scalars['String']['input']; + id: Scalars['String']['input']; + name: Scalars['String']['input']; +}; + + export type MutationChangeParticipantLocaleArgs = { locale: LocaleType; }; @@ -1946,6 +1954,15 @@ export type ChangeInitialSettingsMutationVariables = Exact<{ export type ChangeInitialSettingsMutation = { __typename?: 'Mutation', changeInitialSettings?: { __typename?: 'User', id: string, email: string, shortname: string, locale: LocaleType, firstLogin: boolean, catalyst: boolean, catalystTier?: string | null } | null }; +export type ChangeLiveQuizNameMutationVariables = Exact<{ + id: Scalars['String']['input']; + name: Scalars['String']['input']; + displayName: Scalars['String']['input']; +}>; + + +export type ChangeLiveQuizNameMutation = { __typename?: 'Mutation', changeLiveQuizName?: { __typename?: 'Session', id: string, name: string, displayName: string } | null }; + export type ChangeParticipantLocaleMutationVariables = Exact<{ locale: LocaleType; }>; @@ -2900,6 +2917,7 @@ export const ChangeCourseDatesDocument = {"kind":"Document","definitions":[{"kin export const ChangeCourseDescriptionDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"ChangeCourseDescription"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"input"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"String"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"courseId"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"String"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"changeCourseDescription"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"input"},"value":{"kind":"Variable","name":{"kind":"Name","value":"input"}}},{"kind":"Argument","name":{"kind":"Name","value":"courseId"},"value":{"kind":"Variable","name":{"kind":"Name","value":"courseId"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"description"}}]}}]}}]} as unknown as DocumentNode; export const ChangeEmailSettingsDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"ChangeEmailSettings"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"projectUpdates"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"Boolean"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"changeEmailSettings"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"projectUpdates"},"value":{"kind":"Variable","name":{"kind":"Name","value":"projectUpdates"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"sendProjectUpdates"}}]}}]}}]} as unknown as DocumentNode; export const ChangeInitialSettingsDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"ChangeInitialSettings"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"shortname"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"String"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"locale"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"LocaleType"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"sendUpdates"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"Boolean"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"changeInitialSettings"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"shortname"},"value":{"kind":"Variable","name":{"kind":"Name","value":"shortname"}}},{"kind":"Argument","name":{"kind":"Name","value":"locale"},"value":{"kind":"Variable","name":{"kind":"Name","value":"locale"}}},{"kind":"Argument","name":{"kind":"Name","value":"sendUpdates"},"value":{"kind":"Variable","name":{"kind":"Name","value":"sendUpdates"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"email"}},{"kind":"Field","name":{"kind":"Name","value":"shortname"}},{"kind":"Field","name":{"kind":"Name","value":"locale"}},{"kind":"Field","name":{"kind":"Name","value":"firstLogin"}},{"kind":"Field","name":{"kind":"Name","value":"catalyst"}},{"kind":"Field","name":{"kind":"Name","value":"catalystTier"}}]}}]}}]} as unknown as DocumentNode; +export const ChangeLiveQuizNameDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"ChangeLiveQuizName"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"id"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"String"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"name"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"String"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"displayName"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"String"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"changeLiveQuizName"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"id"},"value":{"kind":"Variable","name":{"kind":"Name","value":"id"}}},{"kind":"Argument","name":{"kind":"Name","value":"name"},"value":{"kind":"Variable","name":{"kind":"Name","value":"name"}}},{"kind":"Argument","name":{"kind":"Name","value":"displayName"},"value":{"kind":"Variable","name":{"kind":"Name","value":"displayName"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"name"}},{"kind":"Field","name":{"kind":"Name","value":"displayName"}}]}}]}}]} as unknown as DocumentNode; export const ChangeParticipantLocaleDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"ChangeParticipantLocale"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"locale"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"LocaleType"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"changeParticipantLocale"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"locale"},"value":{"kind":"Variable","name":{"kind":"Name","value":"locale"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"locale"}}]}}]}}]} as unknown as DocumentNode; export const ChangeSessionSettingsDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"ChangeSessionSettings"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"id"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"String"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"isLiveQAEnabled"}},"type":{"kind":"NamedType","name":{"kind":"Name","value":"Boolean"}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"isConfusionFeedbackEnabled"}},"type":{"kind":"NamedType","name":{"kind":"Name","value":"Boolean"}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"isModerationEnabled"}},"type":{"kind":"NamedType","name":{"kind":"Name","value":"Boolean"}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"isGamificationEnabled"}},"type":{"kind":"NamedType","name":{"kind":"Name","value":"Boolean"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"changeSessionSettings"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"id"},"value":{"kind":"Variable","name":{"kind":"Name","value":"id"}}},{"kind":"Argument","name":{"kind":"Name","value":"isLiveQAEnabled"},"value":{"kind":"Variable","name":{"kind":"Name","value":"isLiveQAEnabled"}}},{"kind":"Argument","name":{"kind":"Name","value":"isConfusionFeedbackEnabled"},"value":{"kind":"Variable","name":{"kind":"Name","value":"isConfusionFeedbackEnabled"}}},{"kind":"Argument","name":{"kind":"Name","value":"isModerationEnabled"},"value":{"kind":"Variable","name":{"kind":"Name","value":"isModerationEnabled"}}},{"kind":"Argument","name":{"kind":"Name","value":"isGamificationEnabled"},"value":{"kind":"Variable","name":{"kind":"Name","value":"isGamificationEnabled"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"isLiveQAEnabled"}},{"kind":"Field","name":{"kind":"Name","value":"isConfusionFeedbackEnabled"}},{"kind":"Field","name":{"kind":"Name","value":"isModerationEnabled"}},{"kind":"Field","name":{"kind":"Name","value":"isGamificationEnabled"}}]}}]}}]} as unknown as DocumentNode; export const ChangeShortnameDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"ChangeShortname"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"shortname"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"String"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"changeShortname"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"shortname"},"value":{"kind":"Variable","name":{"kind":"Name","value":"shortname"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"shortname"}}]}}]}}]} as unknown as DocumentNode; diff --git a/packages/graphql/src/public/client.json b/packages/graphql/src/public/client.json index 98eae888bd..d727230891 100644 --- a/packages/graphql/src/public/client.json +++ b/packages/graphql/src/public/client.json @@ -8,6 +8,7 @@ "ChangeCourseDescription": "b11fa59c1381e2682eb55a8f06436a0eff89006c0c31eaf3db05472b888c616d", "ChangeEmailSettings": "4eb1aea4a048c1f61c892d0efe44e45ce29c2f45066a91d1bebfeae593ff6fa3", "ChangeInitialSettings": "7ece161fac94af2c9bdd1dfb69e71e2e7b980bfcd4c29f9895d97a7b3f38e81d", + "ChangeLiveQuizName": "6e7ca0b348377937206556530031fd73cca9584f69d01d6a6e2de4b7b5a1ed0b", "ChangeParticipantLocale": "a35b384c5614ee4c314767f21d4310c0b1be94ef14c6759ef275a4bea5efbba3", "ChangeSessionSettings": "a96f0ba9beeae844e8db86511cdc85cf00d71679116880554a24e23415b1d627", "ChangeShortname": "07ed8db96ea01e17e68f1b598ba830a22199d44248cc473072fe2428491c4656", diff --git a/packages/graphql/src/public/schema.graphql b/packages/graphql/src/public/schema.graphql index 40232b695b..fe773f245c 100644 --- a/packages/graphql/src/public/schema.graphql +++ b/packages/graphql/src/public/schema.graphql @@ -547,6 +547,7 @@ type Mutation { changeCourseDescription(courseId: String!, input: String!): Course changeEmailSettings(projectUpdates: Boolean!): User changeInitialSettings(locale: LocaleType!, sendUpdates: Boolean!, shortname: String!): User + changeLiveQuizName(displayName: String!, id: String!, name: String!): Session changeParticipantLocale(locale: LocaleType!): Participant changeSessionSettings(id: String!, isConfusionFeedbackEnabled: Boolean, isGamificationEnabled: Boolean, isLiveQAEnabled: Boolean, isModerationEnabled: Boolean): Session changeShortname(shortname: String!): User diff --git a/packages/graphql/src/public/server.json b/packages/graphql/src/public/server.json index 4371d76e00..97c32590bc 100644 --- a/packages/graphql/src/public/server.json +++ b/packages/graphql/src/public/server.json @@ -8,6 +8,7 @@ "b11fa59c1381e2682eb55a8f06436a0eff89006c0c31eaf3db05472b888c616d": "mutation ChangeCourseDescription($input: String!, $courseId: String!) {\n changeCourseDescription(input: $input, courseId: $courseId) {\n id\n description\n __typename\n }\n}", "4eb1aea4a048c1f61c892d0efe44e45ce29c2f45066a91d1bebfeae593ff6fa3": "mutation ChangeEmailSettings($projectUpdates: Boolean!) {\n changeEmailSettings(projectUpdates: $projectUpdates) {\n id\n sendProjectUpdates\n __typename\n }\n}", "7ece161fac94af2c9bdd1dfb69e71e2e7b980bfcd4c29f9895d97a7b3f38e81d": "mutation ChangeInitialSettings($shortname: String!, $locale: LocaleType!, $sendUpdates: Boolean!) {\n changeInitialSettings(shortname: $shortname, locale: $locale, sendUpdates: $sendUpdates) {\n id\n email\n shortname\n locale\n firstLogin\n catalyst\n catalystTier\n __typename\n }\n}", + "6e7ca0b348377937206556530031fd73cca9584f69d01d6a6e2de4b7b5a1ed0b": "mutation ChangeLiveQuizName($id: String!, $name: String!, $displayName: String!) {\n changeLiveQuizName(id: $id, name: $name, displayName: $displayName) {\n id\n name\n displayName\n __typename\n }\n}", "a35b384c5614ee4c314767f21d4310c0b1be94ef14c6759ef275a4bea5efbba3": "mutation ChangeParticipantLocale($locale: LocaleType!) {\n changeParticipantLocale(locale: $locale) {\n id\n locale\n __typename\n }\n}", "a96f0ba9beeae844e8db86511cdc85cf00d71679116880554a24e23415b1d627": "mutation ChangeSessionSettings($id: String!, $isLiveQAEnabled: Boolean, $isConfusionFeedbackEnabled: Boolean, $isModerationEnabled: Boolean, $isGamificationEnabled: Boolean) {\n changeSessionSettings(id: $id, isLiveQAEnabled: $isLiveQAEnabled, isConfusionFeedbackEnabled: $isConfusionFeedbackEnabled, isModerationEnabled: $isModerationEnabled, isGamificationEnabled: $isGamificationEnabled) {\n id\n isLiveQAEnabled\n isConfusionFeedbackEnabled\n isModerationEnabled\n isGamificationEnabled\n __typename\n }\n}", "07ed8db96ea01e17e68f1b598ba830a22199d44248cc473072fe2428491c4656": "mutation ChangeShortname($shortname: String!) {\n changeShortname(shortname: $shortname) {\n id\n shortname\n __typename\n }\n}", diff --git a/packages/graphql/src/schema/mutation.ts b/packages/graphql/src/schema/mutation.ts index b47d4194fe..5e9008b3b7 100644 --- a/packages/graphql/src/schema/mutation.ts +++ b/packages/graphql/src/schema/mutation.ts @@ -926,6 +926,19 @@ export const Mutation = builder.mutationType({ }, }), + changeLiveQuizName: t.withAuth(asUserFullAccess).field({ + nullable: true, + type: Session, + args: { + id: t.arg.string({ required: true }), + name: t.arg.string({ required: true }), + displayName: t.arg.string({ required: true }), + }, + resolve(_, args, ctx) { + return SessionService.changeLiveQuizName(args, ctx) + }, + }), + getFileUploadSas: t.withAuth(asUserFullAccess).field({ nullable: true, type: FileUploadSAS, diff --git a/packages/graphql/src/services/sessions.ts b/packages/graphql/src/services/sessions.ts index 5c319420ee..1dd833259d 100644 --- a/packages/graphql/src/services/sessions.ts +++ b/packages/graphql/src/services/sessions.ts @@ -2223,3 +2223,26 @@ export async function softDeleteLiveSession( return deletedLiveSession } + +export async function changeLiveQuizName( + { id, name, displayName }: { id: string; name: string; displayName: string }, + ctx: ContextWithUser +) { + const updatedSession = await ctx.prisma.liveSession.update({ + where: { + id, + ownerId: ctx.user.sub, + }, + data: { + name, + displayName, + }, + }) + + ctx.emitter.emit('invalidate', { + typename: 'Session', + id, + }) + + return updatedSession +} diff --git a/packages/i18n/messages/de.ts b/packages/i18n/messages/de.ts index b4a6456001..ad8669f6e0 100644 --- a/packages/i18n/messages/de.ts +++ b/packages/i18n/messages/de.ts @@ -1046,6 +1046,11 @@ Da die KlickerUZH-App noch nicht im iOS-App-Store verfügbar ist, folgen Sie die noSessions: 'Keine Sessionen gefunden', creationExplanation: 'Um Ihre erste Session zu erstellen, gehen Sie zurück in den Fragepool. Dort können alle verschiedenen Arten von KlickerUZH-Elementen erstellt und Fragen aus dem Fragepool hinzufügen werden.', + changeLiveQuizName: 'Änderung Live Quiz Namen', + liveQuizNameChangeSuccess: + 'Der Name des Live Quizzes wurde erfolgreich geändert.', + liveQuizNameChangeError: + 'Der Name des Live Quizzes konnte nicht geändert werden.', }, cockpit: { qrCodeAccountLinkTitle: 'Konto-Link', diff --git a/packages/i18n/messages/en.ts b/packages/i18n/messages/en.ts index 7500dbf6e3..c7769f75f6 100644 --- a/packages/i18n/messages/en.ts +++ b/packages/i18n/messages/en.ts @@ -1040,6 +1040,10 @@ Since the KlickerUZH app is not yet available on the iOS App Store, follow these noSessions: 'No live quizzes available', creationExplanation: 'To create your first live quiz, go back to the question pool. There you can create all different types of KlickerUZH activities and add questions from the question pool.', + changeLiveQuizName: 'Change live quiz name', + liveQuizNameChangeSuccess: 'The name of the live quiz has been changed.', + liveQuizNameChangeError: + 'The name of the live quiz could not be changed.', }, cockpit: { qrCodeAccountLinkTitle: 'Account Link',