diff --git a/CHANGELOG.md b/CHANGELOG.md
index c00bbd4ea..9c3ddc33d 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -5,6 +5,18 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/).
+
+## [1.0.0-alpha.6] - 2024-09-27
+
+### Added
+- Added po and sm forms for the weekly checkin for the appropriate teams https://github.com/chingu-x/chingu-dashboard/issues/216
+
+### Changed
+- Changed how we're accessing meeting data to match changes in backend https://github.com/chingu-x/chingu-dashboard/pull/269
+
+
+### Fixed
+
## [1.0.0-alpha.5] - 2024-09-19
### Added
diff --git a/src/app/(main)/dashboard/components/voyage-dashboard/getDashboardData.ts b/src/app/(main)/dashboard/components/voyage-dashboard/getDashboardData.ts
index 4e235a30e..ef0a600a7 100644
--- a/src/app/(main)/dashboard/components/voyage-dashboard/getDashboardData.ts
+++ b/src/app/(main)/dashboard/components/voyage-dashboard/getDashboardData.ts
@@ -200,7 +200,7 @@ export const getDashboardData = async (
.map((sprint) =>
fetchMeeting({
sprintNumber: sprint.number,
- meetingId: sprint.teamMeetings[0]?.id,
+ meetingId: sprint.teamMeetings[0],
}),
);
diff --git a/src/app/(main)/my-voyage/[teamId]/sprints/components/EmptySprintWrapper.tsx b/src/app/(main)/my-voyage/[teamId]/sprints/components/EmptySprintWrapper.tsx
index fa0b33d4f..9fac4f77f 100644
--- a/src/app/(main)/my-voyage/[teamId]/sprints/components/EmptySprintWrapper.tsx
+++ b/src/app/(main)/my-voyage/[teamId]/sprints/components/EmptySprintWrapper.tsx
@@ -24,8 +24,8 @@ import ErrorComponent from "@/components/Error";
function getMeeting(sprints: Sprint[], sprintNumber: number) {
const sprint = sprints.find((sprint) => sprint.number === sprintNumber);
- if (sprint?.teamMeetings && sprint?.teamMeetings.length > 0)
- return sprint.teamMeetings[0];
+ if (sprint?.teamMeetingsData && sprint?.teamMeetingsData.length > 0)
+ return sprint.teamMeetingsData[0];
return null;
}
diff --git a/src/app/(main)/my-voyage/[teamId]/sprints/components/ProgressStepper.tsx b/src/app/(main)/my-voyage/[teamId]/sprints/components/ProgressStepper.tsx
index 89ef4b78f..8c25ef6db 100644
--- a/src/app/(main)/my-voyage/[teamId]/sprints/components/ProgressStepper.tsx
+++ b/src/app/(main)/my-voyage/[teamId]/sprints/components/ProgressStepper.tsx
@@ -31,7 +31,7 @@ export default function ProgressStepper({
function handleClick(sprintNumber: number) {
const meetingId = sprints.find((sprint) => sprint.number === sprintNumber)!
- .teamMeetings[0]?.id;
+ .teamMeetings[0];
if (meetingId) {
router.push(
diff --git a/src/app/(main)/my-voyage/[teamId]/sprints/components/RedirectToCurrentSprintWrapper.tsx b/src/app/(main)/my-voyage/[teamId]/sprints/components/RedirectToCurrentSprintWrapper.tsx
index cdf368a7f..67abcb457 100644
--- a/src/app/(main)/my-voyage/[teamId]/sprints/components/RedirectToCurrentSprintWrapper.tsx
+++ b/src/app/(main)/my-voyage/[teamId]/sprints/components/RedirectToCurrentSprintWrapper.tsx
@@ -51,7 +51,6 @@ export default async function RedirectToCurrentSprintWrapper({
const teamId = Number(params.teamId);
let currentSprintNumber: number;
- let currentMeetingId: number;
const [user, error] = await getUser();
@@ -110,12 +109,12 @@ export default async function RedirectToCurrentSprintWrapper({
);
}
const { teamMeetings, number } = getCurrentSprint(res!.sprints) as Sprint;
+
currentSprintNumber = number;
- currentMeetingId = teamMeetings[0]?.id;
- if (currentMeetingId) {
+ if (teamMeetings.length !== 0) {
redirect(
- `/my-voyage/${teamId}/sprints/${currentSprintNumber}/meeting/${currentMeetingId}`,
+ `/my-voyage/${teamId}/sprints/${currentSprintNumber}/meeting/${teamMeetings[0]}`,
);
} else {
redirect(`/my-voyage/${teamId}/sprints/${currentSprintNumber}`);
diff --git a/src/app/(main)/my-voyage/[teamId]/sprints/components/SprintWrapper.tsx b/src/app/(main)/my-voyage/[teamId]/sprints/components/SprintWrapper.tsx
index 4f9e7a93c..b5edac318 100644
--- a/src/app/(main)/my-voyage/[teamId]/sprints/components/SprintWrapper.tsx
+++ b/src/app/(main)/my-voyage/[teamId]/sprints/components/SprintWrapper.tsx
@@ -125,7 +125,7 @@ export default async function SprintWrapper({ params }: SprintWrapperProps) {
const correspondingMeetingId = voyageData.sprints.find(
(sprint) => sprint.number === sprintNumber,
- )?.teamMeetings[0]?.id;
+ )?.teamMeetings[0];
if (meetingId === correspondingMeetingId) {
const [res, error] = await fetchMeeting({ sprintNumber, meetingId });
diff --git a/src/app/(main)/my-voyage/[teamId]/sprints/components/WeeklyCheckInWrapper.tsx b/src/app/(main)/my-voyage/[teamId]/sprints/components/WeeklyCheckInWrapper.tsx
index fc21649b9..ab645f770 100644
--- a/src/app/(main)/my-voyage/[teamId]/sprints/components/WeeklyCheckInWrapper.tsx
+++ b/src/app/(main)/my-voyage/[teamId]/sprints/components/WeeklyCheckInWrapper.tsx
@@ -12,7 +12,7 @@ import { CacheTag } from "@/utils/cacheTag";
import { type AsyncActionResponse, handleAsync } from "@/utils/handleAsync";
import { getCurrentVoyageData } from "@/utils/getCurrentVoyageData";
import routePaths from "@/utils/routePaths";
-import { Forms } from "@/utils/form/formsEnums";
+import { Forms, UserRole } from "@/utils/form/formsEnums";
import { type Question, type TeamMemberForCheckbox } from "@/utils/form/types";
import { getSprintCheckinIsStatus } from "@/utils/getFormStatus";
import { getCurrentSprint } from "@/utils/getCurrentSprint";
@@ -75,6 +75,11 @@ export default async function WeeklyCheckInWrapper({
let description = "";
let questions = [] as Question[];
+ let hasProductOwner = false;
+ let hasScrumMaster = false;
+ let isScrumMaster = false;
+ let isProductOwner = false;
+
const [user, error] = await getUser();
const { errorResponse, data } = await getCurrentVoyageData({
@@ -141,6 +146,25 @@ export default async function WeeklyCheckInWrapper({
}).voyageTeamMemberId;
}
+ // Check if a team has a product owner or a scrum muster and if a user is a team has a product owner or a scrum muster
+ hasScrumMaster = !!res.voyageTeamMembers.find(
+ (member) =>
+ member.voyageRole.name === UserRole.scrumMaster.toString(),
+ );
+
+ hasProductOwner = !!res.voyageTeamMembers.find(
+ (member) =>
+ member.voyageRole.name === UserRole.productOwner.toString(),
+ );
+
+ const currentUserRole = res.voyageTeamMembers.find(
+ (member) => member.id === voyageTeamMemberId,
+ )?.voyageRole.name;
+
+ isScrumMaster = currentUserRole === UserRole.scrumMaster.toString();
+
+ isProductOwner = currentUserRole === UserRole.productOwner.toString();
+
// Get all teamMembers except for the current user
if (voyageTeamMemberId) {
teamMembers = res.voyageTeamMembers
@@ -163,7 +187,7 @@ export default async function WeeklyCheckInWrapper({
);
}
- // Fetch form
+ // Fetch general checkin form
const [formRes, formError] = await fetchFormQuestions({
formId: Forms.checkIn,
});
@@ -176,8 +200,49 @@ export default async function WeeklyCheckInWrapper({
/>
);
}
+
if (formRes && formRes?.description) description = formRes.description;
if (formRes && formRes?.questions) questions = formRes.questions;
+
+ // Fetch PO checkin questions (form)
+ if (hasProductOwner && !isProductOwner) {
+ const [POformRes, POformError] = await fetchFormQuestions({
+ formId: Forms.checkinPO,
+ });
+
+ if (POformError) {
+ return (
+
+ );
+ }
+
+ if (POformRes && POformRes?.questions)
+ questions = [...questions, ...POformRes.questions];
+ }
+
+ // Fetch SM checkin questions (form)
+ if (hasScrumMaster && !isScrumMaster) {
+ const [SMformRes, SMformError] = await fetchFormQuestions({
+ formId: Forms.checkinSM,
+ });
+
+ if (SMformError) {
+ return (
+
+ );
+ }
+
+ if (SMformRes && SMformRes?.questions)
+ questions = [...questions, ...SMformRes.questions];
+ }
+
+ questions = questions.sort((a, b) => a.order - b.order);
}
} else {
redirect(routePaths.dashboardPage());
diff --git a/src/app/(main)/my-voyage/[teamId]/sprints/components/forms/AgendaTopicForm.tsx b/src/app/(main)/my-voyage/[teamId]/sprints/components/forms/AgendaTopicForm.tsx
index 484dcd038..5bd2032c7 100644
--- a/src/app/(main)/my-voyage/[teamId]/sprints/components/forms/AgendaTopicForm.tsx
+++ b/src/app/(main)/my-voyage/[teamId]/sprints/components/forms/AgendaTopicForm.tsx
@@ -160,9 +160,13 @@ export default function AgendaTopicForm() {
useEffect(() => {
if (sprintNumber && agendaId) {
- const topic = sprints
- .find((sprint) => sprint.number === sprintNumber)
- ?.teamMeetings[0].agendas?.find((topic) => topic.id === agendaId);
+ const sprint = sprints.find((sprint) => sprint.number === sprintNumber);
+
+ const topic =
+ sprint?.teamMeetingsData &&
+ sprint.teamMeetingsData[0].agendas?.find(
+ (topic) => topic.id === agendaId,
+ );
setTopicData(topic);
setEditMode(true);
diff --git a/src/app/(main)/my-voyage/[teamId]/sprints/components/forms/MeetingForm.tsx b/src/app/(main)/my-voyage/[teamId]/sprints/components/forms/MeetingForm.tsx
index b6329a69c..e5e1a68b1 100644
--- a/src/app/(main)/my-voyage/[teamId]/sprints/components/forms/MeetingForm.tsx
+++ b/src/app/(main)/my-voyage/[teamId]/sprints/components/forms/MeetingForm.tsx
@@ -177,8 +177,10 @@ export default function MeetingForm() {
useEffect(() => {
if (params.meetingId) {
const meeting = sprints.find(
- (sprint) => sprint.teamMeetings[0]?.id === +params.meetingId,
- )?.teamMeetings[0];
+ (sprint) =>
+ sprint.teamMeetingsData &&
+ sprint.teamMeetingsData[0].id === +params.meetingId,
+ );
setMeetingData(meeting as Meeting);
setEditMode(true);
diff --git a/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Notes.tsx b/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Notes.tsx
index a68113bb5..797f5b5de 100644
--- a/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Notes.tsx
+++ b/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Notes.tsx
@@ -43,7 +43,10 @@ export default function Notes() {
} = useSprint();
useEffect(() => {
- setData(sprints[sprintNumber - 1].teamMeetings[0].notes);
+ const sprint = sprints[sprintNumber - 1];
+ if (sprint.teamMeetingsData && sprint.teamMeetingsData.length) {
+ setData(sprint.teamMeetingsData[0].notes);
+ }
}, [sprints, sprintNumber]);
const {
diff --git a/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Planning.tsx b/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Planning.tsx
index 9ab2fb24d..3a2f8b831 100644
--- a/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Planning.tsx
+++ b/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Planning.tsx
@@ -52,11 +52,14 @@ export default function Planning() {
} = useSprint();
useEffect(() => {
- setData(
- sprints[sprintNumber - 1].teamMeetings[0].formResponseMeeting?.find(
- (form) => form.form.id === Number(Forms.planning),
- ),
- );
+ const sprint = sprints[sprintNumber - 1];
+ if (sprint.teamMeetingsData && sprint.teamMeetingsData.length) {
+ setData(
+ sprint.teamMeetingsData[0].formResponseMeeting?.find(
+ (form) => form.form.id === Number(Forms.planning),
+ ),
+ );
+ }
}, [sprints, sprintNumber]);
const goal = data?.responseGroup.responses.find(
diff --git a/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Review.tsx b/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Review.tsx
index f6c4a709c..0bd047506 100644
--- a/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Review.tsx
+++ b/src/app/(main)/my-voyage/[teamId]/sprints/components/sections/Review.tsx
@@ -56,11 +56,14 @@ export default function Review() {
} = useSprint();
useEffect(() => {
- setData(
- sprints[sprintNumber - 1].teamMeetings[0].formResponseMeeting?.find(
- (form) => form.form.id === Number(Forms.review),
- ),
- );
+ const sprint = sprints[sprintNumber - 1];
+ if (sprint.teamMeetingsData && sprint.teamMeetingsData.length) {
+ setData(
+ sprint.teamMeetingsData[0].formResponseMeeting?.find(
+ (form) => form.form.id === Number(Forms.review),
+ ),
+ );
+ }
}, [sprints, sprintNumber]);
const what_right = data?.responseGroup.responses.find(
diff --git a/src/app/(main)/my-voyage/[teamId]/sprints/sprintsService.ts b/src/app/(main)/my-voyage/[teamId]/sprints/sprintsService.ts
index 09ca2670c..b42cd3dde 100644
--- a/src/app/(main)/my-voyage/[teamId]/sprints/sprintsService.ts
+++ b/src/app/(main)/my-voyage/[teamId]/sprints/sprintsService.ts
@@ -95,7 +95,7 @@ export interface SprintsResponse {
number: number;
startDate: string;
endDate: string;
- teamMeetings: { id: number }[];
+ teamMeetings: number[];
}[];
}
diff --git a/src/store/features/sprint/sprintSlice.ts b/src/store/features/sprint/sprintSlice.ts
index 8b64eb63b..1e6284a05 100644
--- a/src/store/features/sprint/sprintSlice.ts
+++ b/src/store/features/sprint/sprintSlice.ts
@@ -45,7 +45,8 @@ export interface Sprint {
number: number;
startDate: string;
endDate: string;
- teamMeetings: Meeting[];
+ teamMeetings: number[];
+ teamMeetingsData?: Meeting[];
}
export interface Voyage {
@@ -89,16 +90,11 @@ export const sprintSlice = createSlice({
const updatedSprints = state.voyage.sprints.map((sprint) => {
if (sprint.id === sprintId) {
- const updatedMeetings = sprint.teamMeetings.map((meeting) => {
- if (meeting.id === action.payload.id) {
- return action.payload;
- }
- return meeting;
- });
- return { ...sprint, teamMeetings: updatedMeetings };
+ return { ...sprint, teamMeetingsData: [action.payload] };
}
return sprint;
});
+
state.voyage.sprints = updatedSprints;
state.loading = true;
},
diff --git a/src/utils/form/formsEnums.ts b/src/utils/form/formsEnums.ts
index f37943027..308cba151 100644
--- a/src/utils/form/formsEnums.ts
+++ b/src/utils/form/formsEnums.ts
@@ -1,5 +1,7 @@
export enum Forms {
- submitProject = 6,
+ submitProject = 8,
+ checkinSM = 5,
+ checkinPO = 4,
checkIn = 3,
planning = 2,
review = 1,
@@ -20,3 +22,9 @@ export enum ReviewQuestions {
what_to_improve = 2,
what_to_change = 1,
}
+
+export enum UserRole {
+ developer = "Developer",
+ productOwner = "Product Owner",
+ scrumMaster = "Scrum Master",
+}
diff --git a/src/utils/getCurrentSprint.ts b/src/utils/getCurrentSprint.ts
index 2ea96c1d9..4b1cd9e82 100644
--- a/src/utils/getCurrentSprint.ts
+++ b/src/utils/getCurrentSprint.ts
@@ -4,7 +4,7 @@ import { type Sprint } from "@/store/features/sprint/sprintSlice";
export const currentDate =
process.env.NODE_ENV === "development"
- ? new Date(2024, 5, 10, 12)
+ ? new Date(2024, 5, 1, 12)
: new Date();
export function getCurrentSprint(sprints: Sprint[]) {