Redesign #13
@@ -166,6 +166,7 @@ public class AcademicCalendarController {
|
||||
}
|
||||
try {
|
||||
replaceCalendarSubjects(calendar, rows == null ? List.of() : rows);
|
||||
scheduleGeneratorService.clearCache();
|
||||
return ResponseEntity.ok(calendarSubjectRepository.findByCalendarIdWithSubject(id).stream()
|
||||
.map(this::toCalendarSubjectDto)
|
||||
.toList());
|
||||
@@ -284,6 +285,7 @@ public class AcademicCalendarController {
|
||||
}
|
||||
|
||||
calendarSubjectRepository.deleteByAcademicCalendar_Id(calendar.getId());
|
||||
calendarSubjectRepository.flush();
|
||||
List<AcademicCalendarSubject> entities = rows.stream()
|
||||
.map(row -> {
|
||||
AcademicCalendarSubject calendarSubject = new AcademicCalendarSubject();
|
||||
|
||||
@@ -435,7 +435,7 @@ GET /api/schedule?groupId=1&startDate=2026-04-27&endDate=2026-05-03
|
||||
]
|
||||
```
|
||||
|
||||
`semesterNumber` — номер учебного семестра внутри графика: для 4 курсов доступны значения `1..8`. API принимает только существующие неархивные дисциплины из `/api/subjects`, не допускает дубли одной дисциплины в одном семестре и возвращает сохранённые записи с `subjectName`, `subjectCode` и `departmentId`.
|
||||
`semesterNumber` — номер учебного семестра внутри графика: для 4 курсов доступны значения `1..8`. API принимает только существующие неархивные дисциплины из `/api/subjects`, не допускает дубли одной дисциплины в одном семестре и возвращает сохранённые записи с `subjectName`, `subjectCode` и `departmentId`. `PUT /subjects` выполняет атомарную полную замену списка: перед вставкой нового набора старые привязки этого графика удаляются и синхронизируются с БД.
|
||||
|
||||
### `POST /api/admin/schedule-rules`
|
||||
|
||||
|
||||
@@ -139,7 +139,7 @@ frontend/
|
||||
|
||||
### Особенности админских вкладок
|
||||
|
||||
- Вкладка `groups` загружает кафедры, специальности, профили, учебные годы и календарные графики. Список групп открывается через `/api/groups?includeArchived=true`, поэтому в таблице видны активные, будущие, завершившие обучение и архивные группы со статусом. Группа создаётся через `/api/groups` с `specialtyId` и `specialtyProfileId`, блок подгрупп использует `/api/subgroups` и `/api/groups/{id}/subgroups`, а блок назначений использует `/api/groups/{id}/calendar-assignments`. После назначения графика в таблице назначений сразу выводятся дисциплины графика, сгруппированные по номерам семестров. В селекты подгрупп и назначений попадают только группы с `active=true`.
|
||||
- Вкладка `groups` загружает кафедры, специальности, профили, учебные годы и календарные графики. Список групп открывается через `/api/groups?includeArchived=true`, поэтому в таблице видны активные, будущие, завершившие обучение и архивные группы со статусом. Группа создаётся через `/api/groups` с `specialtyId` и `specialtyProfileId`, а модалка редактирования использует широкую сетку полей без внутреннего пустого скролла. Блок подгрупп использует `/api/subgroups` и `/api/groups/{id}/subgroups`, а блок назначений использует `/api/groups/{id}/calendar-assignments`. После назначения графика в таблице назначений сразу выводятся дисциплины графика, сгруппированные по номерам семестров. В селекты подгрупп и назначений попадают только группы с `active=true`.
|
||||
- Вкладка `teacher-requests` показывает pending-заявки кафедр на создание преподавателей. Администратор может скорректировать кафедру, логин, ФИО и должность, задать пароль минимум 8 символов, затем одобрить заявку через `/api/teacher-requests/{id}/approve` или отклонить её через `/api/teacher-requests/{id}/reject`. Для роли `ADMIN` счётчик pending-заявок выводится в пункте меню «Заявки» и рядом с заголовком страницы, чтобы очередь была видна без открытия вкладки.
|
||||
- Вкладка `department-workspace` в блоке преподавателей объединяет данные `/api/department/teachers` и `/api/workload/teachers`: каждый преподаватель показывается одной карточкой с должностью и нагрузкой за выбранный период, преподаватели без занятий получают нулевую нагрузку, а преподаватели из расписания добавляются без дублей. Если дата начала периода выбрана позже даты окончания, поле окончания очищается, а расчёт нагрузки ждёт корректный период.
|
||||
- Вкладка `department-workspace` позволяет кафедре добавить существующего активного преподавателя на свою кафедру через `/api/department/teachers/{teacherId}/assignments`, отправить заявку на нового преподавателя через `/api/department/teacher-requests` и видеть статусы собственных заявок в таблице.
|
||||
|
||||
@@ -74,6 +74,59 @@
|
||||
color: var(--error);
|
||||
}
|
||||
|
||||
#modal-edit-group .edit-group-modal {
|
||||
width: min(980px, calc(100vw - 2rem));
|
||||
max-height: none;
|
||||
overflow: visible;
|
||||
}
|
||||
|
||||
#modal-edit-group #edit-group-form {
|
||||
display: grid;
|
||||
gap: 1rem;
|
||||
margin-top: 1rem;
|
||||
}
|
||||
|
||||
#modal-edit-group .edit-group-form-row {
|
||||
display: grid;
|
||||
gap: 1rem;
|
||||
align-items: end;
|
||||
}
|
||||
|
||||
#modal-edit-group .edit-group-form-row-main {
|
||||
grid-template-columns: repeat(3, minmax(0, 1fr));
|
||||
}
|
||||
|
||||
#modal-edit-group .edit-group-form-row-details {
|
||||
grid-template-columns: repeat(5, minmax(0, 1fr));
|
||||
}
|
||||
|
||||
#modal-edit-group .form-group {
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
#modal-edit-group .edit-group-submit {
|
||||
display: flex;
|
||||
align-items: flex-end;
|
||||
}
|
||||
|
||||
#modal-edit-group .edit-group-submit .btn {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
@media (max-width: 980px) {
|
||||
#modal-edit-group .edit-group-form-row-main,
|
||||
#modal-edit-group .edit-group-form-row-details {
|
||||
grid-template-columns: repeat(2, minmax(0, 1fr));
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 560px) {
|
||||
#modal-edit-group .edit-group-form-row-main,
|
||||
#modal-edit-group .edit-group-form-row-details {
|
||||
grid-template-columns: 1fr;
|
||||
}
|
||||
}
|
||||
|
||||
#schedule-conflict-modal {
|
||||
padding: 0.35rem;
|
||||
overflow-x: hidden;
|
||||
|
||||
@@ -98,12 +98,12 @@
|
||||
|
||||
<!-- Модальное окно редактирования группы -->
|
||||
<div class="modal-overlay" id="modal-edit-group">
|
||||
<div class="modal-content card">
|
||||
<div class="modal-content card edit-group-modal">
|
||||
<h2>Редактировать группу</h2>
|
||||
<button class="modal-close" id="modal-edit-group-close">×</button>
|
||||
<form id="edit-group-form">
|
||||
<input type="hidden" id="edit-group-id">
|
||||
<div class="form-row" style="margin-top: 1rem;">
|
||||
<div class="form-row edit-group-form-row edit-group-form-row-main">
|
||||
<div class="form-group">
|
||||
<label for="edit-group-name">Название группы</label>
|
||||
<input type="text" id="edit-group-name" required>
|
||||
@@ -119,7 +119,7 @@
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<div class="form-row" style="margin-top: 1rem;">
|
||||
<div class="form-row edit-group-form-row edit-group-form-row-details">
|
||||
<div class="form-group">
|
||||
<label for="edit-group-department">Кафедра</label>
|
||||
<select id="edit-group-department">
|
||||
@@ -142,8 +142,8 @@
|
||||
<option value="">Выберите специальность</option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="form-group" style="display: flex; align-items: flex-end;">
|
||||
<button type="submit" class="btn btn-md btn-primary" style="width: 100%;">Сохранить</button>
|
||||
<div class="form-group edit-group-submit">
|
||||
<button type="submit" class="btn btn-md btn-primary">Сохранить</button>
|
||||
</div>
|
||||
</div>
|
||||
<div class="form-alert" id="edit-group-alert" role="alert"></div>
|
||||
|
||||
Reference in New Issue
Block a user