@hed-hog/lms 0.0.270 → 0.0.275

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 (2) hide show
  1. package/README.md +602 -0
  2. package/package.json +8 -8
package/README.md ADDED
@@ -0,0 +1,602 @@
1
+ ```markdown
2
+ # @hed-hog/lms
3
+
4
+ ## 1. Visão geral do módulo
5
+
6
+ O módulo `@hed-hog/lms` é responsável pela gestão do sistema de Learning Management System (LMS) dentro do monorepo HedHog. Ele oferece funcionalidades para gerenciamento de cursos, aulas, avaliações, certificados, matrículas, instrutores, trilhas de aprendizagem e demais componentes relacionados ao ambiente educacional digital.
7
+
8
+ ## 2. Escopo e responsabilidades
9
+
10
+ - Gerenciamento de cursos, módulos, aulas e suas respectivas estruturas.
11
+ - Controle de matrículas em cursos e trilhas de aprendizagem.
12
+ - Administração de avaliações, tentativas e respostas.
13
+ - Emissão e verificação de certificados.
14
+ - Gestão de instrutores e suas atribuições.
15
+ - Controle de presenças em aulas presenciais ou online.
16
+ - Organização de trilhas de aprendizagem e seus passos.
17
+ - Suporte a imagens e arquivos relacionados a cursos, exames e trilhas.
18
+ - Avaliações e feedbacks sobre tópicos específicos do LMS.
19
+
20
+ ## 3. Endpoints
21
+
22
+ > **Nota:** O código fonte fornecido não expõe endpoints REST ou GraphQL diretamente. Este módulo é consumido via serviços internos ou APIs do HedHog que integram com o LMS.
23
+
24
+ ## 4. Regras de autenticação e autorização
25
+
26
+ - Existe o papel (`role`) `admin-lms` com permissão total para gestão do LMS.
27
+ - Autenticação e autorização são gerenciadas externamente, utilizando o papel `admin-lms` para operações administrativas.
28
+ - Regras específicas de acesso devem ser implementadas conforme a integração com o sistema de autenticação do HedHog.
29
+
30
+ ## 5. Estruturas de request/response
31
+
32
+ - Não aplicável diretamente, pois o módulo não expõe endpoints REST no código fornecido.
33
+ - Operações são realizadas via serviços internos ou APIs que consomem este módulo.
34
+
35
+ ## 6. Erros comuns
36
+
37
+ - **Violação de integridade referencial:** ao inserir ou atualizar registros com chaves estrangeiras inválidas.
38
+ - **Duplicidade de registros únicos:** como códigos únicos de certificado, slugs de cursos ou templates.
39
+ - **Status inválidos:** ao definir valores fora dos enums para status de cursos, exames, matrículas, etc.
40
+ - **Campos obrigatórios ausentes:** como títulos, slugs e chaves primárias.
41
+
42
+ ## 7. Banco de dados (tabelas YAML)
43
+
44
+ ### certificate
45
+
46
+ - **Finalidade:** Armazena certificados emitidos para estudantes em cursos, exames, grupos de aulas ou trilhas de aprendizagem.
47
+ - **Colunas:**
48
+ - `id` (PK)
49
+ - `verification_code` (varchar 50, único): código para verificação do certificado.
50
+ - `student_id` (FK para `person.id`, onDelete CASCADE): estudante que recebeu o certificado.
51
+ - `course_enrollment_id` (FK opcional para `course_enrollment.id`, onDelete SET NULL)
52
+ - `course_id` (FK opcional para `course.id`, onDelete SET NULL)
53
+ - `exam_id` (FK opcional para `exam.id`, onDelete SET NULL)
54
+ - `course_class_group_id` (FK opcional para `course_class_group.id`, onDelete SET NULL)
55
+ - `learning_path_id` (FK opcional para `learning_path.id`, onDelete SET NULL)
56
+ - `certificate_template_id` (FK para `certificate_template.id`)
57
+ - `certificate_type` (enum: `course`, `exam`, `course_class_group`, `learning_path`)
58
+ - `student_name` (varchar 255)
59
+ - `course_name` (varchar 255)
60
+ - `workload_hours` (int)
61
+ - `issued_at` (datetime)
62
+ - `completed_at` (datetime)
63
+ - `final_score` (int, nullable)
64
+ - `verification_url` (varchar 500, nullable)
65
+ - `pdf_url` (varchar 500, nullable)
66
+ - `created_at`, `updated_at`
67
+ - **Índices:** único em `verification_code`.
68
+
69
+ ### certificate_template
70
+
71
+ - **Finalidade:** Modelos de certificados para emissão.
72
+ - **Colunas:**
73
+ - `id` (PK)
74
+ - `name` (varchar 255)
75
+ - `slug` (varchar 255, único)
76
+ - `description` (text, nullable)
77
+ - `template_content` (text)
78
+ - `status` (enum: `draft`, `active`, `inactive`, default `draft`)
79
+ - `created_at`, `updated_at`
80
+ - **Índices:** único em `slug`.
81
+
82
+ ### course
83
+
84
+ - **Finalidade:** Cursos disponíveis no LMS.
85
+ - **Colunas:**
86
+ - `id` (PK)
87
+ - `title` (varchar 255)
88
+ - `slug` (varchar 255, único)
89
+ - `description` (text, nullable)
90
+ - `short_description` (varchar 500, nullable)
91
+ - `level` (enum: `beginner`, `intermediate`, `advanced`, default `beginner`)
92
+ - `duration_hours` (int, default 0)
93
+ - `status` (enum: `draft`, `published`, `archived`, default `draft`)
94
+ - `primary_color`, `primary_contrast_color`, `secondary_color`, `secondary_contrast_color` (varchar 9, nullable)
95
+ - `certificate_workload` (int, nullable)
96
+ - `certificate_template_id` (FK opcional para `certificate_template.id`, onDelete SET NULL)
97
+ - `requirements`, `objectives`, `target_audience` (text, nullable)
98
+ - `created_at`, `updated_at`
99
+ - **Índices:** único em `slug`.
100
+
101
+ ### course_category
102
+
103
+ - **Finalidade:** Associação entre cursos e categorias.
104
+ - **Colunas:**
105
+ - `id` (PK)
106
+ - `course_id` (FK para `course.id`, onDelete CASCADE)
107
+ - `category_id` (FK para `category.id`, onDelete CASCADE)
108
+ - `created_at`, `updated_at`
109
+ - **Índices:** único em combinação `course_id` + `category_id`.
110
+
111
+ ### course_class_attendance
112
+
113
+ - **Finalidade:** Registro de presença dos estudantes em sessões de aula.
114
+ - **Colunas:**
115
+ - `id` (PK)
116
+ - `course_class_session_id` (FK para `course_class_session.id`, onDelete CASCADE)
117
+ - `student_id` (FK para `person.id`, onDelete CASCADE)
118
+ - `present` (boolean, default false)
119
+ - `justification` (text, nullable)
120
+ - `recorded_by_id` (FK opcional para `person.id`, onDelete SET NULL)
121
+ - `created_at`, `updated_at`
122
+ - **Índices:** único em combinação `course_class_session_id` + `student_id`.
123
+
124
+ ### course_class_group
125
+
126
+ - **Finalidade:** Grupos de aulas de um curso.
127
+ - **Colunas:**
128
+ - `id` (PK)
129
+ - `course_id` (FK para `course.id`, onDelete CASCADE)
130
+ - `title` (varchar 255)
131
+ - `code` (varchar 50, único)
132
+ - `description` (text, nullable)
133
+ - `delivery_mode` (enum: `presential`, `online`, `hybrid`)
134
+ - `status` (enum: `open`, `ongoing`, `completed`, `cancelled`, default `open`)
135
+ - `start_date` (datetime)
136
+ - `end_date` (datetime, nullable)
137
+ - `start_time` (varchar 5, nullable)
138
+ - `end_time` (varchar 5, nullable)
139
+ - `week_days` (text, nullable)
140
+ - `capacity` (int, default 30)
141
+ - `location` (text, nullable)
142
+ - `virtual_room_url` (varchar 500, nullable)
143
+ - `created_at`, `updated_at`
144
+ - **Índices:** único em `code`.
145
+
146
+ ### course_class_session
147
+
148
+ - **Finalidade:** Sessões específicas dentro de um grupo de aula.
149
+ - **Colunas:**
150
+ - `id` (PK)
151
+ - `course_class_group_id` (FK para `course_class_group.id`, onDelete CASCADE)
152
+ - `title` (varchar 255)
153
+ - `description` (text, nullable)
154
+ - `session_date` (datetime)
155
+ - `start_time` (varchar 5)
156
+ - `end_time` (varchar 5)
157
+ - `location` (text, nullable)
158
+ - `meeting_url` (varchar 500, nullable)
159
+ - `status` (enum: `scheduled`, `completed`, `cancelled`, default `scheduled`)
160
+ - `created_at`, `updated_at`
161
+ - **Índices:** combinação `course_class_group_id` + `session_date`.
162
+
163
+ ### course_class_session_instructor
164
+
165
+ - **Finalidade:** Instrutores vinculados a sessões de aula.
166
+ - **Colunas:**
167
+ - `id` (PK)
168
+ - `course_class_session_id` (FK para `course_class_session.id`, onDelete CASCADE)
169
+ - `instructor_id` (FK para `instructor.id`, onDelete CASCADE)
170
+ - `role` (enum: `lead`, `assistant`, default `assistant`)
171
+ - `created_at`, `updated_at`
172
+ - **Índices:** único em combinação `course_class_session_id` + `instructor_id`.
173
+
174
+ ### course_enrollment
175
+
176
+ - **Finalidade:** Matrículas de pessoas em cursos ou grupos de aula.
177
+ - **Colunas:**
178
+ - `id` (PK)
179
+ - `person_id` (FK para `person.id`, onDelete CASCADE)
180
+ - `course_class_group_id` (FK opcional para `course_class_group.id`, onDelete SET NULL)
181
+ - `course_id` (FK para `course.id`, onDelete CASCADE)
182
+ - `status` (enum: `pending`, `active`, `completed`, `cancelled`, `paused`, default `active`)
183
+ - `enrolled_at` (datetime)
184
+ - `completed_at` (datetime, nullable)
185
+ - `progress_percent` (int, default 0)
186
+ - `final_score` (int, nullable)
187
+ - `created_at`, `updated_at`
188
+ - **Índices:** único em combinação `person_id` + `course_class_group_id`.
189
+
190
+ ### course_image
191
+
192
+ - **Finalidade:** Imagens associadas a cursos.
193
+ - **Colunas:**
194
+ - `id` (PK)
195
+ - `course_id` (FK para `course.id`, onDelete CASCADE)
196
+ - `file_id` (FK para `file.id`, onDelete CASCADE)
197
+ - `image_type_id` (FK para `image_type.id`, onDelete CASCADE)
198
+ - `order` (int)
199
+ - `is_primary` (boolean, default false)
200
+ - `created_at`, `updated_at`
201
+ - **Índices:** único em combinação `course_id` + `image_type_id` + `order`.
202
+
203
+ ### course_lesson
204
+
205
+ - **Finalidade:** Aulas dentro de módulos de curso.
206
+ - **Colunas:**
207
+ - `id` (PK)
208
+ - `course_module_id` (FK para `course_module.id`, onDelete CASCADE)
209
+ - `title` (varchar 255)
210
+ - `description` (text, nullable)
211
+ - `type` (enum: `video`, `text`, `quiz`, default `video`)
212
+ - `content` (text, nullable)
213
+ - `duration_seconds` (int, default 0)
214
+ - `order` (int)
215
+ - `is_released` (boolean, default true)
216
+ - `created_at`, `updated_at`
217
+ - **Índices:** único em combinação `course_module_id` + `order`.
218
+
219
+ ### course_lesson_file
220
+
221
+ - **Finalidade:** Arquivos vinculados a aulas.
222
+ - **Colunas:**
223
+ - `id` (PK)
224
+ - `course_lesson_id` (FK para `course_lesson.id`, onDelete CASCADE)
225
+ - `file_id` (FK opcional para `file.id`, onDelete SET NULL)
226
+ - `title` (varchar 255)
227
+ - `created_at`, `updated_at`
228
+ - **Índices:** em `course_lesson_id`.
229
+
230
+ ### course_lesson_instructor
231
+
232
+ - **Finalidade:** Instrutores vinculados a aulas.
233
+ - **Colunas:**
234
+ - `id` (PK)
235
+ - `course_lesson_id` (FK para `course_lesson.id`, onDelete CASCADE)
236
+ - `instructor_id` (FK para `instructor.id`, onDelete CASCADE)
237
+ - `role` (enum: `lead`, `assistant`, default `assistant`)
238
+ - `created_at`, `updated_at`
239
+ - **Índices:** único em combinação `course_lesson_id` + `instructor_id`.
240
+
241
+ ### course_lesson_progress
242
+
243
+ - **Finalidade:** Progresso dos estudantes em aulas.
244
+ - **Colunas:**
245
+ - `id` (PK)
246
+ - `course_enrollment_id` (FK para `course_enrollment.id`, onDelete CASCADE)
247
+ - `course_lesson_id` (FK para `course_lesson.id`, onDelete CASCADE)
248
+ - `status` (enum: `not_started`, `in_progress`, `completed`, default `not_started`)
249
+ - `progress_percent` (int, default 0)
250
+ - `video_progress_seconds` (int, default 0)
251
+ - `started_at` (datetime, nullable)
252
+ - `completed_at` (datetime, nullable)
253
+ - `time_spent_seconds` (int, default 0)
254
+ - `created_at`, `updated_at`
255
+ - **Índices:** único em combinação `course_enrollment_id` + `course_lesson_id`.
256
+
257
+ ### course_lesson_question
258
+
259
+ - **Finalidade:** Questões associadas a aulas do tipo quiz.
260
+ - **Colunas:**
261
+ - `id` (PK)
262
+ - `course_lesson_id` (FK para `course_lesson.id`, onDelete CASCADE)
263
+ - `question_id` (FK para `question.id`, onDelete CASCADE)
264
+ - `order` (int)
265
+ - `created_at`, `updated_at`
266
+ - **Índices:** únicos em combinações `course_lesson_id` + `question_id` e `course_lesson_id` + `order`.
267
+
268
+ ### course_module
269
+
270
+ - **Finalidade:** Módulos dentro de cursos.
271
+ - **Colunas:**
272
+ - `id` (PK)
273
+ - `course_id` (FK para `course.id`, onDelete CASCADE)
274
+ - `title` (varchar 255)
275
+ - `description` (text, nullable)
276
+ - `order` (int)
277
+ - `duration_minutes` (int, default 0)
278
+ - `created_at`, `updated_at`
279
+ - **Índices:** único em combinação `course_id` + `order`.
280
+
281
+ ### course_prerequisite
282
+
283
+ - **Finalidade:** Pré-requisitos para cursos.
284
+ - **Colunas:**
285
+ - `id` (PK)
286
+ - `course_id` (FK para `course.id`, onDelete CASCADE)
287
+ - `prerequisite_type` (enum: `course`, `learning_path`, `exam`, default `course`)
288
+ - `prerequisite_course_id` (FK opcional para `course.id`, onDelete CASCADE)
289
+ - `prerequisite_learning_path_id` (FK opcional para `learning_path.id`, onDelete CASCADE)
290
+ - `prerequisite_exam_id` (FK opcional para `exam.id`, onDelete CASCADE)
291
+ - `created_at`, `updated_at`
292
+ - **Índices:** únicos para combinações de curso e pré-requisitos.
293
+
294
+ ### evaluation_rating
295
+
296
+ - **Finalidade:** Avaliações e notas dadas a tópicos de avaliação.
297
+ - **Colunas:**
298
+ - `id` (PK)
299
+ - `evaluation_topic_id` (FK para `evaluation_topic.id`, onDelete CASCADE)
300
+ - `evaluator_id` (FK opcional para `person.id`, onDelete SET NULL)
301
+ - `score` (decimal 2,1)
302
+ - `comment` (text, nullable)
303
+ - `created_at`, `updated_at`
304
+ - **Índices:** único em combinação `evaluation_topic_id` + `evaluator_id`.
305
+
306
+ ### evaluation_topic
307
+
308
+ - **Finalidade:** Tópicos para avaliação dentro do LMS.
309
+ - **Colunas:**
310
+ - `id` (PK)
311
+ - `name` (varchar 255)
312
+ - `description` (text, nullable)
313
+ - `target_type` (enum: `course`, `course_lesson`, `course_class_session`, `question`, `exam`)
314
+ - `course_id` (FK opcional para `course.id`, onDelete SET NULL)
315
+ - `course_lesson_id` (FK opcional para `course_lesson.id`, onDelete SET NULL)
316
+ - `course_class_session_id` (FK opcional para `course_class_session.id`, onDelete SET NULL)
317
+ - `question_id` (FK opcional para `question.id`, onDelete SET NULL)
318
+ - `exam_id` (FK opcional para `exam.id`, onDelete SET NULL)
319
+ - `order` (int)
320
+ - `is_active` (boolean, default true)
321
+ - `created_at`, `updated_at`
322
+ - **Índices:** únicos para combinações de alvo e ordem.
323
+
324
+ ### exam
325
+
326
+ - **Finalidade:** Exames vinculados a cursos ou grupos de aula.
327
+ - **Colunas:**
328
+ - `id` (PK)
329
+ - `course_id` (FK opcional para `course.id`, onDelete SET NULL)
330
+ - `course_class_group_id` (FK opcional para `course_class_group.id`, onDelete SET NULL)
331
+ - `title` (varchar 255)
332
+ - `description` (text, nullable)
333
+ - `instructions` (text, nullable)
334
+ - `exam_type` (enum: `quiz`, `test`, `assignment`, `project`)
335
+ - `status` (enum: `draft`, `published`, `closed`, `archived`, default `draft`)
336
+ - `primary_color`, `primary_contrast_color`, `secondary_color`, `secondary_contrast_color` (varchar 9, nullable)
337
+ - `starts_at` (datetime, nullable)
338
+ - `ends_at` (datetime, nullable)
339
+ - `time_limit_minutes` (int, nullable)
340
+ - `attempts_allowed` (int, default 1)
341
+ - `min_score` (int, default 60)
342
+ - `max_score` (int, default 100)
343
+ - `shuffle_questions` (boolean, default false)
344
+ - `shuffle_options` (boolean, default false)
345
+ - `show_result` (boolean, default true)
346
+ - `show_answer_key` (boolean, default false)
347
+ - `show_explanation_after_answer` (boolean, default false)
348
+ - `require_all_questions_answered_to_finish` (boolean, default false)
349
+ - `created_at`, `updated_at`
350
+ - **Índices:** em `course_id`, `course_class_group_id` e `status`.
351
+
352
+ ### exam_answer
353
+
354
+ - **Finalidade:** Respostas dadas em tentativas de exame.
355
+ - **Colunas:**
356
+ - `id` (PK)
357
+ - `exam_attempt_id` (FK para `exam_attempt.id`, onDelete CASCADE)
358
+ - `question_id` (FK para `question.id`, onDelete CASCADE)
359
+ - `exam_option_id` (FK opcional para `exam_option.id`, onDelete SET NULL)
360
+ - `answer_text` (text, nullable)
361
+ - `is_correct` (boolean, nullable)
362
+ - `points_awarded` (int, default 0)
363
+ - `teacher_feedback` (text, nullable)
364
+ - `created_at`, `updated_at`
365
+ - **Índices:** único em combinação `exam_attempt_id` + `question_id`.
366
+
367
+ ### exam_attempt
368
+
369
+ - **Finalidade:** Tentativas de realização de exames por estudantes.
370
+ - **Colunas:**
371
+ - `id` (PK)
372
+ - `exam_id` (FK para `exam.id`, onDelete CASCADE)
373
+ - `student_id` (FK para `person.id`, onDelete CASCADE)
374
+ - `course_enrollment_id` (FK opcional para `course_enrollment.id`, onDelete SET NULL)
375
+ - `attempt_number` (int, default 1)
376
+ - `started_at` (datetime)
377
+ - `finished_at` (datetime, nullable)
378
+ - `duration_seconds` (int, nullable)
379
+ - `score` (int, nullable)
380
+ - `status` (enum: `in_progress`, `completed`, `abandoned`, `voided`, default `in_progress`)
381
+ - `ip_address` (varchar 45, nullable)
382
+ - `created_at`, `updated_at`
383
+ - **Índices:** único em combinação `exam_id` + `student_id` + `attempt_number`.
384
+
385
+ ### exam_image
386
+
387
+ - **Finalidade:** Imagens associadas a exames.
388
+ - **Colunas:**
389
+ - `id` (PK)
390
+ - `exam_id` (FK para `exam.id`, onDelete CASCADE)
391
+ - `file_id` (FK para `file.id`, onDelete CASCADE)
392
+ - `image_type_id` (FK para `image_type.id`, onDelete CASCADE)
393
+ - `order` (int)
394
+ - `is_primary` (boolean, default false)
395
+ - `created_at`, `updated_at`
396
+ - **Índices:** único em combinação `exam_id` + `image_type_id` + `order`.
397
+
398
+ ### exam_option
399
+
400
+ - **Finalidade:** Opções de resposta para questões de exame.
401
+ - **Colunas:**
402
+ - `id` (PK)
403
+ - `question_id` (FK para `question.id`, onDelete CASCADE)
404
+ - `option_text` (text)
405
+ - `is_correct` (boolean, default false)
406
+ - `position` (int, default 0)
407
+ - `feedback` (text, nullable)
408
+ - `created_at`, `updated_at`
409
+ - **Índices:** único em combinação `question_id` + `position`.
410
+
411
+ ### exam_question
412
+
413
+ - **Finalidade:** Questões associadas a exames.
414
+ - **Colunas:**
415
+ - `id` (PK)
416
+ - `exam_id` (FK para `exam.id`, onDelete CASCADE)
417
+ - `question_id` (FK para `question.id`, onDelete CASCADE)
418
+ - `order` (int)
419
+ - `created_at`, `updated_at`
420
+ - **Índices:** únicos em combinações `exam_id` + `question_id` e `exam_id` + `order`.
421
+
422
+ ### image_type
423
+
424
+ - **Finalidade:** Tipos de imagens aplicáveis a cursos, exames e trilhas.
425
+ - **Colunas:**
426
+ - `id` (PK)
427
+ - `name` (varchar 100)
428
+ - `slug` (varchar 100, único)
429
+ - `applies_to_course` (boolean, default false)
430
+ - `applies_to_exam` (boolean, default false)
431
+ - `applies_to_learning_path` (boolean, default false)
432
+ - `status` (enum: `active`, `inactive`, default `active`)
433
+ - `created_at`, `updated_at`
434
+ - **Índices:** único em `slug`.
435
+
436
+ ### instructor
437
+
438
+ - **Finalidade:** Instrutores cadastrados no LMS.
439
+ - **Colunas:**
440
+ - `id` (PK)
441
+ - `person_id` (FK único para `person.id`, onDelete CASCADE)
442
+ - `status` (enum: `active`, `inactive`, default `active`)
443
+ - `can_teach_courses` (boolean, default true)
444
+ - `created_at`, `updated_at`
445
+ - **Índices:** único em `person_id`.
446
+
447
+ ### learning_path
448
+
449
+ - **Finalidade:** Trilhas de aprendizagem compostas por cursos e exames.
450
+ - **Colunas:**
451
+ - `id` (PK)
452
+ - `title` (varchar 255)
453
+ - `slug` (varchar 255, único)
454
+ - `description` (text, nullable)
455
+ - `short_description` (varchar 500, nullable)
456
+ - `level` (enum: `beginner`, `intermediate`, `advanced`, default `beginner`)
457
+ - `duration_hours` (int, default 0)
458
+ - `status` (enum: `draft`, `active`, `archived`, default `draft`)
459
+ - `primary_color`, `primary_contrast_color`, `secondary_color`, `secondary_contrast_color` (varchar 9, nullable)
460
+ - `created_at`, `updated_at`
461
+ - **Índices:** único em `slug`.
462
+
463
+ ### learning_path_enrollment
464
+
465
+ - **Finalidade:** Matrículas em trilhas de aprendizagem.
466
+ - **Colunas:**
467
+ - `id` (PK)
468
+ - `learning_path_id` (FK para `learning_path.id`, onDelete CASCADE)
469
+ - `person_id` (FK para `person.id`, onDelete CASCADE)
470
+ - `status` (enum: `active`, `completed`, `cancelled`, default `active`)
471
+ - `progress_percent` (int, default 0)
472
+ - `enrolled_at` (datetime)
473
+ - `completed_at` (datetime, nullable)
474
+ - `created_at`, `updated_at`
475
+ - **Índices:** único em combinação `learning_path_id` + `person_id`.
476
+
477
+ ### learning_path_image
478
+
479
+ - **Finalidade:** Imagens associadas a trilhas de aprendizagem.
480
+ - **Colunas:**
481
+ - `id` (PK)
482
+ - `learning_path_id` (FK para `learning_path.id`, onDelete CASCADE)
483
+ - `file_id` (FK para `file.id`, onDelete CASCADE)
484
+ - `image_type_id` (FK para `image_type.id`, onDelete CASCADE)
485
+ - `order` (int)
486
+ - `is_primary` (boolean, default false)
487
+ - `created_at`, `updated_at`
488
+ - **Índices:** único em combinação `learning_path_id` + `image_type_id` + `order`.
489
+
490
+ ### learning_path_step
491
+
492
+ - **Finalidade:** Passos dentro de uma trilha, podendo ser cursos ou exames.
493
+ - **Colunas:**
494
+ - `id` (PK)
495
+ - `learning_path_id` (FK para `learning_path.id`, onDelete CASCADE)
496
+ - `step_type` (enum: `course`, `exam`)
497
+ - `course_id` (FK opcional para `course.id`, onDelete CASCADE)
498
+ - `exam_id` (FK opcional para `exam.id`, onDelete CASCADE)
499
+ - `order` (int)
500
+ - `is_required` (boolean, default true)
501
+ - `created_at`, `updated_at`
502
+ - **Índices:** únicos para combinações de trilha e ordem, curso ou exame.
503
+
504
+ ### question
505
+
506
+ - **Finalidade:** Questões para avaliações e quizzes.
507
+ - **Colunas:**
508
+ - `id` (PK)
509
+ - `question_type` (enum: `multiple_choice`, `true_false`, `essay`, `fill_blank`, `matching`)
510
+ - `statement` (text)
511
+ - `explanation` (text, nullable)
512
+ - `points` (int, default 1)
513
+ - `created_at`, `updated_at`
514
+
515
+ ## 8. Regras de negócio relevantes
516
+
517
+ - Certificados são vinculados a estudantes e podem estar associados a diferentes tipos de atividades (curso, exame, grupo de aula, trilha).
518
+ - Cursos, exames e trilhas possuem status que controlam sua visibilidade e disponibilidade.
519
+ - Matrículas e inscrições possuem status que refletem o progresso e situação do aluno.
520
+ - Avaliações e tentativas de exame são controladas para permitir múltiplas tentativas e registrar resultados detalhados.
521
+ - Instrutores podem ter papéis distintos (líder ou assistente) em aulas e sessões.
522
+ - Trilhas de aprendizagem são compostas por passos ordenados que podem ser cursos ou exames, podendo ser obrigatórios ou opcionais.
523
+ - Progresso em aulas e cursos é monitorado para permitir acompanhamento detalhado do aluno.
524
+ - Imagens e arquivos são organizados por tipo e podem ser marcados como primários para exibição.
525
+
526
+ ## 9. Guia rápido de uso (exemplos)
527
+
528
+ > Como o módulo não expõe endpoints diretamente, o uso típico envolve integração via serviços internos ou APIs do HedHog.
529
+
530
+ ### Exemplo: Criar um novo curso
531
+
532
+ ```ts
533
+ const novoCurso = await prisma.course.create({
534
+ data: {
535
+ title: 'Introdução ao HedHog LMS',
536
+ slug: 'introducao-hedhog-lms',
537
+ description: 'Curso básico para entender o LMS HedHog',
538
+ level: 'beginner',
539
+ duration_hours: 10,
540
+ status: 'draft',
541
+ },
542
+ });
543
+ ```
544
+
545
+ ### Exemplo: Matricular um estudante em um curso
546
+
547
+ ```ts
548
+ const matricula = await prisma.course_enrollment.create({
549
+ data: {
550
+ person_id: estudanteId,
551
+ course_id: cursoId,
552
+ status: 'active',
553
+ enrolled_at: new Date(),
554
+ },
555
+ });
556
+ ```
557
+
558
+ ### Exemplo: Registrar presença em uma sessão de aula
559
+
560
+ ```ts
561
+ const presenca = await prisma.course_class_attendance.upsert({
562
+ where: {
563
+ course_class_session_id_student_id: {
564
+ course_class_session_id: sessaoId,
565
+ student_id: estudanteId,
566
+ },
567
+ },
568
+ update: { present: true },
569
+ create: {
570
+ course_class_session_id: sessaoId,
571
+ student_id: estudanteId,
572
+ present: true,
573
+ },
574
+ });
575
+ ```
576
+
577
+ ### Exemplo: Emitir um certificado
578
+
579
+ ```ts
580
+ const certificado = await prisma.certificate.create({
581
+ data: {
582
+ verification_code: gerarCodigoUnico(),
583
+ student_id: estudanteId,
584
+ course_id: cursoId,
585
+ certificate_template_id: templateId,
586
+ certificate_type: 'course',
587
+ student_name: nomeEstudante,
588
+ course_name: nomeCurso,
589
+ workload_hours: cargaHoraria,
590
+ issued_at: new Date(),
591
+ completed_at: dataConclusao,
592
+ final_score: notaFinal,
593
+ verification_url: urlVerificacao,
594
+ pdf_url: urlPdf,
595
+ },
596
+ });
597
+ ```
598
+
599
+ ---
600
+
601
+ Para mais detalhes sobre integração e uso, consulte a documentação geral do HedHog e os serviços que consomem o módulo `@hed-hog/lms`.
602
+ ```
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@hed-hog/lms",
3
- "version": "0.0.270",
3
+ "version": "0.0.275",
4
4
  "main": "dist/index.js",
5
5
  "types": "dist/index.d.ts",
6
6
  "dependencies": {
@@ -9,15 +9,15 @@
9
9
  "@nestjs/core": "^11",
10
10
  "@nestjs/jwt": "^11",
11
11
  "@nestjs/mapped-types": "*",
12
- "@hed-hog/api-pagination": "0.0.6",
13
- "@hed-hog/core": "0.0.270",
12
+ "@hed-hog/core": "0.0.275",
14
13
  "@hed-hog/api": "0.0.4",
15
- "@hed-hog/api-locale": "0.0.13",
14
+ "@hed-hog/finance": "0.0.275",
16
15
  "@hed-hog/api-types": "0.0.1",
17
- "@hed-hog/finance": "0.0.270",
18
- "@hed-hog/contact": "0.0.270",
19
- "@hed-hog/category": "0.0.270",
20
- "@hed-hog/api-prisma": "0.0.5"
16
+ "@hed-hog/api-pagination": "0.0.6",
17
+ "@hed-hog/contact": "0.0.275",
18
+ "@hed-hog/api-prisma": "0.0.5",
19
+ "@hed-hog/api-locale": "0.0.13",
20
+ "@hed-hog/category": "0.0.275"
21
21
  },
22
22
  "exports": {
23
23
  ".": {