'use strict'; /* admin → exams (exam-prep modules) section. * Список ВСЕХ экзамен-треков (вкл. выключенные) + тумблер enabled. * Источник: GET /api/exam-prep/admin/tracks; переключение: PATCH /api/exam-prep/admin/track. * Влияет на видимость модуля в /exam-prep и в каталоге прав доступа (Экзамены). */ (function () { 'use strict'; let inited = false; let _tracks = []; const SUBJ = { math: 'Математика', physics: 'Физика', phys: 'Физика', chemistry: 'Химия', chem: 'Химия', biology: 'Биология', bio: 'Биология' }; function esc(s) { return String(s == null ? '' : s).replace(/[&<>"']/g, c => ({ '&': '&', '<': '<', '>': '>', '"': '"', "'": ''' }[c])); } async function load() { try { const data = await LS.api('/api/exam-prep/admin/tracks'); _tracks = Array.isArray(data.tracks) ? data.tracks : []; _render(); } catch (e) { LS.toast('Ошибка загрузки экзамен-модулей: ' + e.message, 'error'); } } function _render() { const grid = document.getElementById('exams-grid'); if (!grid) return; if (!_tracks.length) { grid.innerHTML = '

Нет экзамен-модулей.

'; return; } grid.innerHTML = _tracks.map(t => { const subj = SUBJ[t.subject_slug] || t.subject_slug || ''; const meta = [subj, t.grade ? (t.grade + ' кл.') : '', (t.task_count || 0) + ' заданий'] .filter(Boolean).join(' · '); return `
${esc(t.title)}
${esc(t.exam_key)}${meta ? ' · ' + esc(meta) : ''}
Открыть
`; }).join(''); if (window.lucide) lucide.createIcons(); } async function examToggle(examKey, enabled) { try { await LS.api('/api/exam-prep/admin/track', { method: 'PATCH', body: JSON.stringify({ exam_key: examKey, enabled }), }); const t = _tracks.find(x => x.exam_key === examKey); if (t) t.enabled = enabled ? 1 : 0; const card = document.getElementById('examcard-' + examKey); if (card) card.classList.toggle('enabled', !!enabled); LS.toast(enabled ? `«${examKey}» включён` : `«${examKey}» выключен`, enabled ? 'success' : 'warning'); } catch (e) { LS.toast('Ошибка: ' + e.message, 'error'); } } window.examToggle = examToggle; window.AdminSections = window.AdminSections || {}; window.AdminSections.exams = { init: async () => { if (inited) return; inited = true; await load(); }, reload: load, }; })();