Skip to content

Commit e2cf328

Browse files
authored
Merge pull request #1963 from tekdi/release-1.11.0
Release 1.11.0 to admin prod
2 parents 6dfe21b + abee62f commit e2cf328

File tree

11 files changed

+362
-250
lines changed

11 files changed

+362
-250
lines changed

libs/shared-lib-v2/src/lib/Card/CommonCard.tsx

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -329,9 +329,16 @@ export const StatusBar: React.FC<StatuPorps> = ({
329329
type,
330330
_card,
331331
}) => {
332+
console.log('status===>', status);
332333
const { t } = useTranslation();
333334

334335
const theme = useTheme();
336+
337+
// Don't render StatusBar if status is undefined or empty
338+
if (!status || status.trim() === '') {
339+
return null;
340+
}
341+
335342
return (
336343
<Box
337344
sx={{

mfes/content/src/components/Content/List.tsx

Lines changed: 90 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -340,6 +340,7 @@ export default function Content(props: Readonly<ContentProps>) {
340340
async (
341341
resultData: ImportedContentSearchResponse[]
342342
): Promise<TrackDataItem[]> => {
343+
console.log('resultData=====>>>>>>', resultData);
343344
if (!resultData.length) return [];
344345

345346
try {
@@ -350,36 +351,88 @@ export default function Content(props: Readonly<ContentProps>) {
350351

351352
if (!userId || !courseList.length) return [];
352353
const userIdArray = userId.split(',').filter(Boolean);
353-
const [courseTrackData, certificates] = await Promise.all([
354-
trackingData(userIdArray, courseList),
355-
getUserCertificates({
356-
userId: userId,
357-
courseId: courseList,
358-
limit: localFilters.limit,
359-
offset: localFilters.offset,
360-
}),
361-
]);
362-
363-
if (!courseTrackData?.data) return [];
364-
365-
const userTrackData =
366-
courseTrackData.data.find((course: any) => course.userId === userId)
367-
?.course ?? [];
368-
369-
return userTrackData.map((item: any) => ({
370-
...item,
371-
...calculateTrackDataItem(
372-
item,
373-
resultData.find(
374-
(subItem) => item.courseId === subItem.identifier
375-
) ?? {}
376-
),
377-
enrolled: Boolean(
378-
certificates.result.data.find(
379-
(cert: any) => cert.courseId === item.courseId
380-
)?.status === 'enrolled'
381-
),
382-
}));
354+
355+
// Fetch certificates first (don't wait for trackingData as it's delayed)
356+
const certificates = await getUserCertificates({
357+
userId: userId,
358+
courseId: courseList,
359+
limit: localFilters.limit,
360+
offset: localFilters.offset,
361+
});
362+
363+
// Fetch tracking data asynchronously without blocking
364+
const trackingPromise = trackingData(userIdArray, courseList);
365+
if (trackingPromise) {
366+
trackingPromise.then((courseTrackData) => {
367+
if (!courseTrackData?.data) return;
368+
369+
const userTrackData =
370+
courseTrackData.data.find((course: any) => course.userId === userId)
371+
?.course ?? [];
372+
373+
const updatedTrackData = userTrackData.map((item: any) => {
374+
const certificate = certificates?.result?.data?.find(
375+
(cert: any) => cert.courseId === item.courseId
376+
);
377+
const certificateStatus = certificate?.status;
378+
379+
const trackDataItem = calculateTrackDataItem(
380+
item,
381+
resultData.find(
382+
(subItem) => item.courseId === subItem.identifier
383+
) ?? {}
384+
);
385+
386+
// Normalize and map certificate status
387+
// let finalStatus = trackDataItem.status; // Default to progress-based status
388+
389+
// if (certificateStatus) {
390+
// // Map certificate status values to standardized status
391+
// if (certificateStatus === 'viewCertificate') {
392+
// finalStatus = 'completed';
393+
// } else if (certificateStatus === 'inprogress' || certificateStatus === 'in-progress') {
394+
// finalStatus = 'in progress';
395+
// } else if (certificateStatus === 'completed') {
396+
// finalStatus = 'completed';
397+
// } else if (certificateStatus === 'enrolled') {
398+
// // If only enrolled but no progress, check if there's progress data
399+
// finalStatus = trackDataItem.status || 'not started';
400+
// } else {
401+
// // For any other certificate status, use it as-is
402+
// finalStatus = certificateStatus;
403+
// }
404+
// }
405+
406+
return {
407+
...item,
408+
...trackDataItem,
409+
// status: finalStatus,
410+
enrolled: certificateStatus === 'enrolled',
411+
};
412+
});
413+
414+
// Update track data state when tracking data arrives
415+
setTrackData((prev) => {
416+
// If offset is 0, replace all data, otherwise append
417+
if (localFilters.offset === 0) {
418+
return updatedTrackData;
419+
} else {
420+
// For load more, merge with existing data
421+
const existingIds = new Set(prev.map((p: any) => p.courseId));
422+
const newItems = updatedTrackData.filter(
423+
(item: any) => !existingIds.has(item.courseId)
424+
);
425+
return [...prev, ...newItems];
426+
}
427+
});
428+
})
429+
.catch((error) => {
430+
console.error('Error fetching track data:', error);
431+
});
432+
}
433+
434+
// Return empty array initially - tracking data will be updated asynchronously
435+
return [];
383436
} catch (error) {
384437
console.error('Error fetching track data:', error);
385438
return [];
@@ -403,23 +456,25 @@ export default function Content(props: Readonly<ContentProps>) {
403456
)
404457
return;
405458

406-
setIsLoading(true);
459+
setIsLoading(true);
407460
try {
408461
const response = await fetchAllContent(localFilters);
409462
if (!response || !isMounted) return;
410463
const newContentData = [
411464
...(response.content ?? []),
412465
...(response?.QuestionSet ?? []),
413466
];
414-
const userTrackData = await fetchDataTrack(newContentData);
415-
console.log('userTrackData', userTrackData);
467+
468+
// Trigger async tracking data fetch (doesn't block UI)
469+
fetchDataTrack(newContentData);
470+
416471
if (!isMounted) return;
417472
if (localFilters.offset === 0) {
418473
setContentData(newContentData);
419-
setTrackData(userTrackData);
474+
setTrackData([]); // Reset trackData, will be updated asynchronously
420475
} else {
421476
setContentData((prev) => [...(prev ?? []), ...newContentData]);
422-
setTrackData((prev) => [...prev, ...userTrackData]);
477+
// trackData will be updated asynchronously by fetchDataTrack
423478
}
424479

425480
setHasMoreData(

mfes/editors/src/components/QuestionSetEditor.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -193,15 +193,15 @@ const QuestionSetEditor: React.FC<{
193193
link.id = "sunbird-editor-css";
194194
link.rel = "stylesheet";
195195
link.href =
196-
"https://cdn.jsdelivr.net/npm/@tekdi/sunbird-questionset-editor-web-component@5.0.0-beta.10/styles.css";
196+
"https://cdn.jsdelivr.net/npm/@tekdi/sunbird-questionset-editor-web-component@5.0.0-beta.13/styles.css";
197197
document.head.appendChild(link);
198198
}
199199

200200
if (!document.getElementById("sunbird-editor-js")) {
201201
const script = document.createElement("script");
202202
script.id = "sunbird-editor-js";
203203
script.src =
204-
"https://cdn.jsdelivr.net/npm/@tekdi/sunbird-questionset-editor-web-component@5.0.0-beta.10/sunbird-questionset-editor.js";
204+
"https://cdn.jsdelivr.net/npm/@tekdi/sunbird-questionset-editor-web-component@5.0.0-beta.13/sunbird-questionset-editor.js";
205205
script.async = true;
206206
script.onload = () => setAssetsLoaded(true);
207207
document.body.appendChild(script);

mfes/scp-teacher-repo/public/locales/en/common.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -753,7 +753,7 @@
753753
"NO_ASSESSMENT_TYPE_FOUND":"No Assessment Type Found",
754754
"IMAGE_UPLOADED": "Image Uploaded",
755755
"VIEW": "View",
756-
"REUPLOAD": "Re-upload"
756+
"REUPLOAD": "Reupload"
757757
},
758758
"BOARD_ENROLMENT": {
759759
"BOARD_ENROLLMENT": "Board Enrollment",

mfes/scp-teacher-repo/src/components/assessment/QuestionMarksManualUpdate.tsx

Lines changed: 20 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -818,10 +818,12 @@ const QuestionMarksManualUpdate: React.FC<QuestionMarksManualUpdateProps> = ({
818818
style={
819819
hasImage
820820
? {
821-
width: '100%',
821+
width: 'fit-content',
822+
display: 'inline-block',
822823
border: '1px solid #eee',
823824
borderRadius: 8,
824825
padding: 8,
826+
paddingRight: 0,
825827
background: '#fff',
826828
marginTop: '0px',
827829
position: 'relative',
@@ -830,6 +832,19 @@ const QuestionMarksManualUpdate: React.FC<QuestionMarksManualUpdateProps> = ({
830832
}
831833
>
832834
<div
835+
onClick={(e) => {
836+
if (!hasImage) return;
837+
const t = e.target as HTMLElement | null;
838+
if (t && t.tagName === 'IMG') {
839+
const srcs = extractImageSrcs(q.questionTitle);
840+
const src = srcs[0] ?? null;
841+
set_zoomImageSrc(src);
842+
const el: any = fullScreenContainerRef.current;
843+
if (src && el && el.requestFullscreen) {
844+
el.requestFullscreen().catch(() => {});
845+
}
846+
}
847+
}}
833848
dangerouslySetInnerHTML={{ __html: questionHtml }}
834849
/>
835850
{hasImage && (
@@ -846,15 +861,16 @@ const QuestionMarksManualUpdate: React.FC<QuestionMarksManualUpdateProps> = ({
846861
}}
847862
sx={{
848863
position: 'absolute',
849-
top: 6,
850-
right: 6,
864+
top: '20%',
865+
right: 0,
866+
transform: 'translateY(-50%)',
851867
bgcolor: 'rgba(255,255,255,0.9)',
852868
boxShadow: 1,
853869
'&:hover': { bgcolor: 'rgba(255,255,255,1)' },
854870
}}
855871
size="small"
856872
>
857-
<ZoomInIcon fontSize="small" />
873+
<ZoomInIcon fontSize="medium" />
858874
</IconButton>
859875
)}
860876
</div>

mfes/scp-teacher-repo/src/pages/manual-assessments/[assessmentId]/[userId]/index.tsx

Lines changed: 51 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -1187,22 +1187,37 @@ const AssessmentDetails = () => {
11871187
handleReUpload();
11881188
}}
11891189
>
1190-
<Box>
1190+
<Box
1191+
sx={{
1192+
display: 'flex',
1193+
alignItems: 'center',
1194+
gap: { xs: 0.5, md: 1 },
1195+
flexWrap: 'nowrap',
1196+
minWidth: 0,
1197+
overflow: 'hidden',
1198+
}}
1199+
>
11911200
<Typography
11921201
sx={{
11931202
color: '#635E57',
1194-
fontSize: { xs: '14px', md: '16px' },
1203+
fontSize: { xs: '12px', md: '16px' },
11951204
fontWeight: 400,
11961205
letterSpacing: '0.1px',
1206+
whiteSpace: 'nowrap',
11971207
}}
11981208
>
11991209
{assessmentData?.fileUrls &&
1200-
assessmentData.fileUrls.length > 0 ? (
1210+
assessmentData.fileUrls.length > 0
1211+
? `${assessmentData.fileUrls.length} ${
1212+
assessmentData.fileUrls.length === 1
1213+
? 'image'
1214+
: 'images'
1215+
} uploaded`
1216+
: 'No images uploaded'}
1217+
</Typography>
1218+
{assessmentData?.fileUrls &&
1219+
assessmentData.fileUrls.length > 0 && (
12011220
<>
1202-
{`${assessmentData.fileUrls.length} ${assessmentData.fileUrls.length === 1
1203-
? 'image'
1204-
: 'images'
1205-
} uploaded`}
12061221
<Button
12071222
variant="contained"
12081223
size="small"
@@ -1211,18 +1226,16 @@ const AssessmentDetails = () => {
12111226
handleUploadInfoClick();
12121227
}}
12131228
sx={{
1214-
ml: 1,
1229+
ml: 0,
12151230
textTransform: 'none',
12161231
borderRadius: '8px',
12171232
fontWeight: 600,
1218-
fontSize: '14px',
1219-
height: '32px',
1220-
padding: '2px 8px',
1221-
display: 'inline-flex',
1233+
fontSize: { xs: '12px', md: '14px' },
1234+
height: { xs: '28px', md: '32px' },
1235+
px: { xs: 1, md: 1.5 },
12221236
backgroundColor: '#FFC107',
12231237
color: '#1F1B13',
12241238
'&:hover': { backgroundColor: '#FFB300' },
1225-
mb: 1,
12261239
}}
12271240
>
12281241
{t('ASSESSMENTS.VIEW')}
@@ -1233,37 +1246,31 @@ const AssessmentDetails = () => {
12331246
'AI Pending',
12341247
'Approved',
12351248
].includes(assessmentData?.status || '') && (
1236-
<>
1237-
<Button
1238-
variant="contained"
1239-
size="small"
1240-
onClick={(e) => {
1241-
// e.stopPropagation();
1242-
// handleReUpload();
1243-
}}
1244-
sx={{
1245-
ml: 1,
1246-
textTransform: 'none',
1247-
borderRadius: '8px',
1248-
fontWeight: 600,
1249-
fontSize: '14px',
1250-
height: '32px',
1251-
padding: '2px 8px',
1252-
backgroundColor: '#FFC107',
1253-
color: '#1F1B13',
1254-
'&:hover': { backgroundColor: '#FFB300' },
1255-
mb: 1,
1256-
}}
1257-
>
1258-
{t('ASSESSMENTS.REUPLOAD')}
1259-
</Button>
1260-
</>
1261-
)}
1249+
<Button
1250+
variant="contained"
1251+
size="small"
1252+
onClick={(e) => {
1253+
// e.stopPropagation();
1254+
// handleReUpload();
1255+
}}
1256+
sx={{
1257+
ml: 0,
1258+
textTransform: 'none',
1259+
borderRadius: '8px',
1260+
fontWeight: 600,
1261+
fontSize: { xs: '12px', md: '14px' },
1262+
height: { xs: '28px', md: '32px' },
1263+
px: { xs: 1, md: 1.5 },
1264+
backgroundColor: '#FFC107',
1265+
color: '#1F1B13',
1266+
'&:hover': { backgroundColor: '#FFB300' },
1267+
}}
1268+
>
1269+
{t('ASSESSMENTS.REUPLOAD')}
1270+
</Button>
1271+
)}
12621272
</>
1263-
) : (
1264-
'No images uploaded'
12651273
)}
1266-
</Typography>
12671274
</Box>
12681275
<IconButton
12691276
onClick={(e) => {
@@ -1274,9 +1281,9 @@ const AssessmentDetails = () => {
12741281
color: '#1F1B13',
12751282
p: 0,
12761283
'& .MuiSvgIcon-root': {
1277-
fontSize: { xs: 24, md: 28 },
1284+
fontSize: { xs: 22, md: 28 },
12781285
},
1279-
mb: 1,
1286+
mb: 0,
12801287
}}
12811288
>
12821289
<FileUploadIcon />

0 commit comments

Comments
 (0)