@hed-hog/lms 0.0.330 → 0.0.338

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (128) hide show
  1. package/dist/class-group/class-group.controller.d.ts +3 -3
  2. package/dist/class-group/class-group.service.d.ts +3 -3
  3. package/dist/course/course.service.d.ts.map +1 -1
  4. package/dist/course/course.service.js +12 -20
  5. package/dist/course/course.service.js.map +1 -1
  6. package/dist/enterprise/enterprise.controller.d.ts +72 -0
  7. package/dist/enterprise/enterprise.controller.d.ts.map +1 -1
  8. package/dist/enterprise/enterprise.controller.js +10 -0
  9. package/dist/enterprise/enterprise.controller.js.map +1 -1
  10. package/dist/enterprise/enterprise.service.d.ts +78 -0
  11. package/dist/enterprise/enterprise.service.d.ts.map +1 -1
  12. package/dist/enterprise/enterprise.service.js +413 -40
  13. package/dist/enterprise/enterprise.service.js.map +1 -1
  14. package/dist/enterprise/training/training-admin.controller.d.ts +6 -3
  15. package/dist/enterprise/training/training-admin.controller.d.ts.map +1 -1
  16. package/dist/enterprise/training/training-admin.controller.js +10 -6
  17. package/dist/enterprise/training/training-admin.controller.js.map +1 -1
  18. package/dist/enterprise/training/training-admin.service.d.ts +8 -2
  19. package/dist/enterprise/training/training-admin.service.d.ts.map +1 -1
  20. package/dist/enterprise/training/training-admin.service.js +108 -52
  21. package/dist/enterprise/training/training-admin.service.js.map +1 -1
  22. package/dist/enterprise/training/training-viewer.controller.d.ts +3 -0
  23. package/dist/enterprise/training/training-viewer.controller.d.ts.map +1 -1
  24. package/dist/evaluation/evaluation.controller.d.ts +4 -4
  25. package/dist/evaluation/evaluation.service.d.ts +4 -4
  26. package/dist/instructor/dto/create-instructor-skill.dto.d.ts +0 -4
  27. package/dist/instructor/dto/create-instructor-skill.dto.d.ts.map +1 -1
  28. package/dist/instructor/dto/create-instructor-skill.dto.js +0 -21
  29. package/dist/instructor/dto/create-instructor-skill.dto.js.map +1 -1
  30. package/dist/instructor/dto/update-instructor-skill.dto.d.ts +0 -4
  31. package/dist/instructor/dto/update-instructor-skill.dto.d.ts.map +1 -1
  32. package/dist/instructor/dto/update-instructor-skill.dto.js +0 -22
  33. package/dist/instructor/dto/update-instructor-skill.dto.js.map +1 -1
  34. package/dist/instructor/instructor-skill.controller.d.ts +4 -4
  35. package/dist/instructor/instructor-skill.service.d.ts +4 -7
  36. package/dist/instructor/instructor-skill.service.d.ts.map +1 -1
  37. package/dist/instructor/instructor-skill.service.js +2 -89
  38. package/dist/instructor/instructor-skill.service.js.map +1 -1
  39. package/dist/instructor/instructor.controller.d.ts +20 -0
  40. package/dist/instructor/instructor.controller.d.ts.map +1 -1
  41. package/dist/instructor/instructor.controller.js +19 -0
  42. package/dist/instructor/instructor.controller.js.map +1 -1
  43. package/dist/instructor/instructor.service.d.ts +25 -0
  44. package/dist/instructor/instructor.service.d.ts.map +1 -1
  45. package/dist/instructor/instructor.service.js +70 -18
  46. package/dist/instructor/instructor.service.js.map +1 -1
  47. package/dist/lms.module.d.ts.map +1 -1
  48. package/dist/lms.module.js.map +1 -1
  49. package/hedhog/data/route.yaml +23 -1
  50. package/hedhog/frontend/app/_components/class-form-sheet.tsx.ejs +42 -24
  51. package/hedhog/frontend/app/_components/create-lms-instructor-sheet.tsx.ejs +591 -0
  52. package/hedhog/frontend/app/certificates/issued/page.tsx.ejs +6 -1
  53. package/hedhog/frontend/app/certificates/models/page.tsx.ejs +7 -2
  54. package/hedhog/frontend/app/classes/[id]/page.tsx.ejs +17 -17
  55. package/hedhog/frontend/app/classes/page.tsx.ejs +6 -1
  56. package/hedhog/frontend/app/courses/[id]/_components/CourseClassificationCard.tsx.ejs +3 -33
  57. package/hedhog/frontend/app/courses/[id]/_components/CourseContentCard.tsx.ejs +9 -9
  58. package/hedhog/frontend/app/courses/[id]/_components/CourseMainInfoCard.tsx.ejs +109 -0
  59. package/hedhog/frontend/app/courses/[id]/_components/CourseMultiEntityPicker.tsx.ejs +42 -15
  60. package/hedhog/frontend/app/courses/[id]/_components/CourseRelationsCard.tsx.ejs +76 -81
  61. package/hedhog/frontend/app/courses/[id]/_components/CourseSummaryCard.tsx.ejs +60 -0
  62. package/hedhog/frontend/app/courses/[id]/page.tsx.ejs +3 -3
  63. package/hedhog/frontend/app/courses/[id]/structure/_components/course-scheduled-classes-tab.tsx.ejs +406 -0
  64. package/hedhog/frontend/app/courses/[id]/structure/_components/course-tree-dnd.tsx.ejs +1 -1
  65. package/hedhog/frontend/app/courses/[id]/structure/_components/course-tree.tsx.ejs +134 -0
  66. package/hedhog/frontend/app/courses/[id]/structure/_components/detail-course.tsx.ejs +113 -0
  67. package/hedhog/frontend/app/courses/[id]/structure/_components/detail-lesson.tsx.ejs +314 -0
  68. package/hedhog/frontend/app/courses/[id]/structure/_components/detail-session.tsx.ejs +174 -0
  69. package/hedhog/frontend/app/courses/[id]/structure/_components/editor-course.tsx.ejs +242 -33
  70. package/hedhog/frontend/app/courses/[id]/structure/_components/editor-lesson.tsx.ejs +228 -152
  71. package/hedhog/frontend/app/courses/[id]/structure/_components/mock-data.ts.ejs +185 -0
  72. package/hedhog/frontend/app/courses/[id]/structure/_components/shortcuts-help.tsx.ejs +71 -31
  73. package/hedhog/frontend/app/courses/page.tsx.ejs +6 -1
  74. package/hedhog/frontend/app/enterprise/[id]/page.tsx.ejs +37 -41
  75. package/hedhog/frontend/app/enterprise/_components/enterprise-activity-timeline.tsx.ejs +87 -0
  76. package/hedhog/frontend/app/enterprise/_components/enterprise-admin-create-sheet.tsx.ejs +4 -0
  77. package/hedhog/frontend/app/enterprise/_components/enterprise-administrators-tab.tsx.ejs +31 -5
  78. package/hedhog/frontend/app/enterprise/_components/enterprise-classes-tab.tsx.ejs +79 -20
  79. package/hedhog/frontend/app/enterprise/_components/enterprise-company-identity-card.tsx.ejs +11 -2
  80. package/hedhog/frontend/app/enterprise/_components/enterprise-course-edit-sheet.tsx.ejs +201 -0
  81. package/hedhog/frontend/app/enterprise/_components/enterprise-courses-tab.tsx.ejs +55 -24
  82. package/hedhog/frontend/app/enterprise/_components/enterprise-detail-sheet.tsx.ejs +430 -296
  83. package/hedhog/frontend/app/enterprise/_components/enterprise-mocks.ts.ejs +277 -0
  84. package/hedhog/frontend/app/enterprise/_components/enterprise-overview-analytics.tsx.ejs +205 -0
  85. package/hedhog/frontend/app/enterprise/_components/enterprise-person-edit-sheet.tsx.ejs +97 -0
  86. package/hedhog/frontend/app/enterprise/_components/enterprise-sheet.tsx.ejs +82 -57
  87. package/hedhog/frontend/app/enterprise/_components/enterprise-student-create-sheet.tsx.ejs +4 -0
  88. package/hedhog/frontend/app/enterprise/_components/enterprise-students-tab.tsx.ejs +60 -22
  89. package/hedhog/frontend/app/enterprise/_components/enterprise-types.ts.ejs +54 -0
  90. package/hedhog/frontend/app/enterprise/_components/enterprise-user-create-sheet.tsx.ejs +211 -0
  91. package/hedhog/frontend/app/enterprise/page.tsx.ejs +39 -7
  92. package/hedhog/frontend/app/evaluations/_components/evaluation-topic-form-sheet.tsx.ejs +1 -1
  93. package/hedhog/frontend/app/exams/[id]/questions/page.tsx.ejs +6 -1
  94. package/hedhog/frontend/app/exams/page.tsx.ejs +12 -3
  95. package/hedhog/frontend/app/instructor-skills/page.tsx.ejs +51 -104
  96. package/hedhog/frontend/app/instructors/_components/instructor-form-sheet.tsx.ejs +712 -427
  97. package/hedhog/frontend/app/instructors/page.tsx.ejs +77 -53
  98. package/hedhog/frontend/app/paths/page.tsx.ejs +14 -5
  99. package/hedhog/frontend/app/reports/courses/page.tsx.ejs +5 -5
  100. package/hedhog/frontend/app/reports/dashboard/page.tsx.ejs +8 -8
  101. package/hedhog/frontend/app/reports/evaluations/page.tsx.ejs +6 -1
  102. package/hedhog/frontend/app/reports/page.tsx.ejs +7 -7
  103. package/hedhog/frontend/app/reports/students/page.tsx.ejs +6 -6
  104. package/hedhog/frontend/app/training/page.tsx.ejs +8 -3
  105. package/hedhog/frontend/messages/en.json +394 -55
  106. package/hedhog/frontend/messages/pt.json +389 -48
  107. package/hedhog/frontend/widgets/active-classes-kpi.tsx.ejs +1 -1
  108. package/hedhog/frontend/widgets/active-courses-kpi.tsx.ejs +1 -1
  109. package/hedhog/frontend/widgets/approval-rate-kpi.tsx.ejs +1 -1
  110. package/hedhog/frontend/widgets/class-calendar.tsx.ejs +2 -2
  111. package/hedhog/frontend/widgets/completion-rate-kpi.tsx.ejs +1 -1
  112. package/hedhog/frontend/widgets/issued-certificates-kpi.tsx.ejs +1 -1
  113. package/hedhog/frontend/widgets/total-students-kpi.tsx.ejs +1 -1
  114. package/hedhog/table/enterprise_student_license_event.yaml +30 -0
  115. package/hedhog/table/instructor_qualification.yaml +1 -1
  116. package/hedhog/table/instructor_skill.yaml +0 -11
  117. package/package.json +8 -8
  118. package/src/course/course.service.ts +12 -24
  119. package/src/enterprise/enterprise.controller.ts +5 -0
  120. package/src/enterprise/enterprise.service.ts +507 -29
  121. package/src/enterprise/training/training-admin.controller.ts +4 -0
  122. package/src/enterprise/training/training-admin.service.ts +115 -51
  123. package/src/instructor/dto/create-instructor-skill.dto.ts +0 -17
  124. package/src/instructor/dto/update-instructor-skill.dto.ts +0 -18
  125. package/src/instructor/instructor-skill.service.ts +2 -97
  126. package/src/instructor/instructor.controller.ts +16 -0
  127. package/src/instructor/instructor.service.ts +85 -10
  128. package/src/lms.module.ts +1 -0
@@ -1,3 +1,4 @@
1
+ import { RichTextEditor } from '@/components/rich-text-editor';
1
2
  import {
2
3
  FormControl,
3
4
  FormField,
@@ -5,7 +6,6 @@ import {
5
6
  FormLabel,
6
7
  FormMessage,
7
8
  } from '@/components/ui/form';
8
- import { Textarea } from '@/components/ui/textarea';
9
9
  import { Network } from 'lucide-react';
10
10
  import type { UseFormReturn } from 'react-hook-form';
11
11
 
@@ -26,6 +26,8 @@ type CourseRelationsCardProps = {
26
26
  values: Record<string, string>
27
27
  ) => Promise<PickerOption | null>;
28
28
  onCreateInstructor: () => void;
29
+ onEditCategory: (categorySlug: string) => void;
30
+ onEditInstructor: (instructorId: string) => void;
29
31
  };
30
32
 
31
33
  export function CourseRelationsCard({
@@ -35,6 +37,8 @@ export function CourseRelationsCard({
35
37
  instructorOptions,
36
38
  onCreateCategory,
37
39
  onCreateInstructor,
40
+ onEditCategory,
41
+ onEditInstructor,
38
42
  }: CourseRelationsCardProps) {
39
43
  return (
40
44
  <CourseSectionCard
@@ -43,83 +47,74 @@ export function CourseRelationsCard({
43
47
  icon={Network}
44
48
  >
45
49
  <div className="space-y-3">
46
- <FormField
47
- control={form.control}
48
- name="categorias"
49
- render={({ field }) => (
50
- <FormItem>
51
- <FormLabel>{t('form.fields.categories.label')}</FormLabel>
52
- <CourseMultiEntityPicker
53
- value={field.value}
54
- onChange={field.onChange}
55
- options={categoryOptions}
56
- placeholder={t('form.fields.categories.selectPlaceholder')}
57
- searchPlaceholder={t(
58
- 'form.fields.categories.searchPlaceholder'
59
- )}
60
- entityLabel="categoria"
61
- emptyStateDescription={t('form.fields.categories.noResults')}
62
- emptyHint="Nenhuma categoria vinculada ainda."
63
- createActionLabel="Criar categoria"
64
- createTitle="Criar categoria"
65
- createDescription="Cadastre uma categoria rapidamente sem sair da edição do curso."
66
- createFields={[
67
- {
68
- name: 'name',
69
- label: 'Nome da categoria',
70
- placeholder: 'Ex: Desenvolvimento Web',
71
- required: true,
72
- },
73
- {
74
- name: 'slug',
75
- label: 'Slug',
76
- placeholder: 'desenvolvimento-web',
77
- required: true,
78
- },
79
- ]}
80
- mapSearchToCreateValues={(search) => ({
81
- name: search,
82
- slug: search
83
- .trim()
84
- .toLowerCase()
85
- .normalize('NFD')
86
- .replace(/[\u0300-\u036f]/g, '')
87
- .replace(/[^a-z0-9]+/g, '-')
88
- .replace(/^-+|-+$/g, ''),
89
- })}
90
- onCreate={onCreateCategory}
91
- />
92
- <FormMessage />
93
- </FormItem>
94
- )}
95
- />
50
+ <div className="grid items-start gap-3 lg:grid-cols-2">
51
+ <FormField
52
+ control={form.control}
53
+ name="categorias"
54
+ render={({ field }) => (
55
+ <FormItem className="self-start">
56
+ <FormLabel>{t('form.fields.categories.label')}</FormLabel>
57
+ <CourseMultiEntityPicker
58
+ value={field.value}
59
+ onChange={field.onChange}
60
+ onEditSelected={(option) => onEditCategory(option.value)}
61
+ options={categoryOptions}
62
+ placeholder={t('form.fields.categories.selectPlaceholder')}
63
+ searchPlaceholder={t(
64
+ 'form.fields.categories.searchPlaceholder'
65
+ )}
66
+ entityLabel="categoria"
67
+ emptyStateDescription={t('form.fields.categories.noResults')}
68
+ emptyHint="Nenhuma categoria vinculada ainda."
69
+ createActionLabel="Criar categoria"
70
+ createTitle="Criar categoria"
71
+ createDescription="Cadastre uma categoria rapidamente sem sair da edição do curso."
72
+ createFields={[
73
+ {
74
+ name: 'name',
75
+ label: 'Nome da categoria',
76
+ placeholder: 'Ex: Desenvolvimento Web',
77
+ required: true,
78
+ },
79
+ ]}
80
+ mapSearchToCreateValues={(search) => ({
81
+ name: search,
82
+ })}
83
+ onCreate={onCreateCategory}
84
+ />
85
+ <FormMessage />
86
+ </FormItem>
87
+ )}
88
+ />
96
89
 
97
- <FormField
98
- control={form.control}
99
- name="instrutores"
100
- render={({ field }) => (
101
- <FormItem>
102
- <FormLabel>{t('form.fields.instructors.label')}</FormLabel>
103
- <CourseMultiEntityPicker
104
- value={field.value}
105
- onChange={field.onChange}
106
- options={instructorOptions}
107
- placeholder={t('form.fields.instructors.selectPlaceholder')}
108
- searchPlaceholder={t(
109
- 'form.fields.instructors.searchPlaceholder'
110
- )}
111
- entityLabel="instrutor"
112
- emptyStateDescription={t('form.fields.instructors.noResults')}
113
- emptyHint="Nenhum instrutor vinculado ainda."
114
- createActionLabel="Cadastrar instrutor"
115
- onCreateClick={onCreateInstructor}
116
- variant="instructor"
117
- renderOptionMeta
118
- />
119
- <FormMessage />
120
- </FormItem>
121
- )}
122
- />
90
+ <FormField
91
+ control={form.control}
92
+ name="instrutores"
93
+ render={({ field }) => (
94
+ <FormItem className="self-start">
95
+ <FormLabel>{t('form.fields.instructors.label')}</FormLabel>
96
+ <CourseMultiEntityPicker
97
+ value={field.value}
98
+ onChange={field.onChange}
99
+ onEditSelected={(option) => onEditInstructor(option.value)}
100
+ options={instructorOptions}
101
+ placeholder={t('form.fields.instructors.selectPlaceholder')}
102
+ searchPlaceholder={t(
103
+ 'form.fields.instructors.searchPlaceholder'
104
+ )}
105
+ entityLabel="instrutor"
106
+ emptyStateDescription={t('form.fields.instructors.noResults')}
107
+ emptyHint="Nenhum instrutor vinculado ainda."
108
+ createActionLabel="Cadastrar instrutor"
109
+ onCreateClick={onCreateInstructor}
110
+ variant="instructor"
111
+ renderOptionMeta
112
+ />
113
+ <FormMessage />
114
+ </FormItem>
115
+ )}
116
+ />
117
+ </div>
123
118
 
124
119
  <FormField
125
120
  control={form.control}
@@ -128,10 +123,10 @@ export function CourseRelationsCard({
128
123
  <FormItem>
129
124
  <FormLabel>{t('form.fields.prerequisites.label')}</FormLabel>
130
125
  <FormControl>
131
- <Textarea
132
- {...field}
133
- rows={3}
134
- placeholder={t('form.fields.prerequisites.placeholder')}
126
+ <RichTextEditor
127
+ value={field.value || ''}
128
+ onChange={field.onChange}
129
+ className="w-full max-w-full"
135
130
  />
136
131
  </FormControl>
137
132
  <FormMessage />
@@ -0,0 +1,60 @@
1
+ import { KpiCardsGrid } from '@/components/ui/kpi-cards-grid';
2
+ import { CalendarDays, Percent, Users, Video } from 'lucide-react';
3
+
4
+ interface CourseSummaryCardProps {
5
+ course: {
6
+ totalAlunos?: number;
7
+ conclusaoMedia?: number;
8
+ totalAulas?: number;
9
+ totalSessoes?: number;
10
+ } | null;
11
+ }
12
+
13
+ export function CourseSummaryCard({ course }: CourseSummaryCardProps) {
14
+ return (
15
+ <KpiCardsGrid
16
+ items={[
17
+ {
18
+ key: 'students',
19
+ title: 'Total Alunos',
20
+ value: (course?.totalAlunos ?? 0).toLocaleString('pt-BR'),
21
+ icon: Users,
22
+ layout: 'compact',
23
+ accentClassName: 'from-slate-900/20 via-slate-700/10 to-transparent',
24
+ iconContainerClassName: 'bg-slate-900 text-white',
25
+ },
26
+ {
27
+ key: 'completion',
28
+ title: 'Conclusao Media',
29
+ value: `${course?.conclusaoMedia ?? 0}%`,
30
+ icon: Percent,
31
+ layout: 'compact',
32
+ accentClassName:
33
+ 'from-emerald-500/25 via-green-500/15 to-transparent',
34
+ iconContainerClassName: 'bg-emerald-100 text-emerald-700',
35
+ },
36
+ {
37
+ key: 'lessons',
38
+ title: 'Total de Aulas',
39
+ value: String(course?.totalAulas ?? 0),
40
+ icon: Video,
41
+ layout: 'compact',
42
+ accentClassName: 'from-sky-500/25 via-blue-500/15 to-transparent',
43
+ iconContainerClassName: 'bg-sky-100 text-sky-700',
44
+ },
45
+ {
46
+ key: 'sessions',
47
+ title: 'Sessoes',
48
+ value: String(course?.totalSessoes ?? 0),
49
+ icon: CalendarDays,
50
+ layout: 'compact',
51
+ accentClassName:
52
+ 'from-violet-500/25 via-indigo-500/15 to-transparent',
53
+ iconContainerClassName: 'bg-violet-100 text-violet-700',
54
+ },
55
+ ]}
56
+ columns={4}
57
+ className="mb-3"
58
+ />
59
+ );
60
+ }
@@ -30,6 +30,7 @@ import {
30
30
  import { useTranslations } from 'next-intl';
31
31
  import { useRouter } from 'next/navigation';
32
32
 
33
+ import { CourseAvatar } from '../../_components/course-avatar';
33
34
  import { ConfirmDialog } from './structure/_components/confirm-dialog';
34
35
  import { CourseTreePanel } from './structure/_components/course-tree-panel';
35
36
  import { CourseTreeSkeleton } from './structure/_components/course-tree-skeleton';
@@ -43,7 +44,6 @@ import {
43
44
  import { useStructureStore } from './structure/_components/store';
44
45
  import { TreeDisplaySettingsPopover } from './structure/_components/tree-display-settings-popover';
45
46
  import { useCourseStructureShortcuts } from './structure/_components/use-course-structure-shortcuts';
46
- import { CourseAvatar } from '../../_components/course-avatar';
47
47
  import {
48
48
  useDuplicateLessonMutation,
49
49
  useDuplicateSessionMutation,
@@ -261,8 +261,8 @@ export default function CourseStructurePage({ params }: Props) {
261
261
  <Page>
262
262
  <PageHeader
263
263
  breadcrumbs={[
264
- { label: 'LMS', href: '/lms' },
265
- { label: 'Cursos', href: '/lms/courses' },
264
+ { label: t('breadcrumbs.lms'), href: '/lms' },
265
+ { label: t('breadcrumbs.courses'), href: '/lms/courses' },
266
266
  { label: course.name },
267
267
  ]}
268
268
  title={