// documents.js - Работа с документами для согласования let documentTypes = []; async function loadDocumentTypes() { try { const response = await fetch('/api/document-types'); documentTypes = await response.json(); populateDocumentTypeSelect(); } catch (error) { console.error('Ошибка загрузки типов документов:', error); } } function populateDocumentTypeSelect() { const select = document.getElementById('document-type'); if (!select) return; select.innerHTML = ''; documentTypes.forEach(type => { const option = document.createElement('option'); option.value = type.id; option.textContent = type.name; select.appendChild(option); }); } function initializeDocumentForm() { const form = document.getElementById('create-document-form'); if (form) { form.addEventListener('submit', createDocumentTask); } // Инициализация даты по умолчанию const today = new Date(); const todayStr = today.toISOString().split('T')[0]; const dateInput = document.getElementById('document-date'); if (dateInput) { dateInput.value = todayStr; } loadDocumentTypes(); } async function createDocumentTask(event) { event.preventDefault(); if (!currentUser) { alert('Требуется аутентификация'); return; } const formData = new FormData(); // Основные данные задачи formData.append('title', document.getElementById('document-title').value); formData.append('description', document.getElementById('document-description').value); // Даты const dueDateInput = document.getElementById('due-date'); if (dueDateInput.value) { formData.append('dueDate', dueDateInput.value); } // Данные документа formData.append('documentTypeId', document.getElementById('document-type').value); formData.append('documentNumber', document.getElementById('document-number').value); formData.append('documentDate', document.getElementById('document-date').value); formData.append('pagesCount', document.getElementById('pages-count').value); formData.append('urgencyLevel', document.getElementById('urgency-level').value); formData.append('comment', document.getElementById('document-comment').value); // Загружаем файлы const filesInput = document.getElementById('document-files'); if (filesInput.files) { for (let i = 0; i < filesInput.files.length; i++) { formData.append('files', filesInput.files[i]); } } try { const response = await fetch('/api/documents', { method: 'POST', body: formData }); if (response.ok) { alert('Задача на согласование документа создана!'); document.getElementById('create-document-form').reset(); document.getElementById('document-file-list').innerHTML = ''; // Сброс даты const today = new Date(); const todayStr = today.toISOString().split('T')[0]; const dateInput = document.getElementById('document-date'); if (dateInput) { dateInput.value = todayStr; } // Перенаправление на список документов showDocumentSection('my-documents'); } else { const error = await response.json(); alert(error.error || 'Ошибка создания задачи'); } } catch (error) { console.error('Ошибка:', error); alert('Ошибка создания задачи'); } } function updateDocumentFileList() { const fileInput = document.getElementById('document-files'); const fileList = document.getElementById('document-file-list'); const files = fileInput.files; if (files.length === 0) { fileList.innerHTML = ''; return; } let html = ''; html += `

Общий размер: ${(totalSize / 1024 / 1024).toFixed(2)} MB / 300 MB

`; fileList.innerHTML = html; } // Функции для работы с документами async function loadMyDocuments() { try { const response = await fetch('/api/documents/my'); const documents = await response.json(); renderMyDocuments(documents); } catch (error) { console.error('Ошибка загрузки документов:', error); } } async function loadSecretaryDocuments() { try { const response = await fetch('/api/documents/secretary'); const documents = await response.json(); renderSecretaryDocuments(documents); } catch (error) { console.error('Ошибка загрузки документов секретаря:', error); } } function renderMyDocuments(documents) { const container = document.getElementById('my-documents-list'); if (!container) return; if (documents.length === 0) { container.innerHTML = '
У вас нет документов на согласование
'; return; } container.innerHTML = documents.map(doc => `
Документ №${doc.document_number || doc.id} ${doc.title} ${getDocumentStatusText(doc.status)} ${doc.urgency_level === 'urgent' ? 'Срочно' : ''} ${doc.urgency_level === 'very_urgent' ? 'Очень срочно' : ''}
Создан: ${formatDateTime(doc.created_at)} ${doc.due_date ? `Срок: ${formatDateTime(doc.due_date)}` : ''}

Тип: ${doc.document_type_name || 'Не указан'}

Дата документа: ${doc.document_date ? formatDate(doc.document_date) : 'Не указана'}

Количество страниц: ${doc.pages_count || 'Не указано'}

${doc.comment ? `

Комментарий: ${doc.comment}

` : ''}
${doc.files && doc.files.length > 0 ? ` Файлы:
${doc.files.map(file => renderFileIcon(file)).join('')}
` : 'Файлы: нет файлов'}
${doc.refusal_reason ? `
Причина отказа: ${doc.refusal_reason}
` : ''}
${doc.status === 'assigned' || doc.status === 'in_progress' ? ` ` : ''} ${doc.status === 'refused' ? ` ` : ''} ${doc.status === 'approved' || doc.status === 'received' || doc.status === 'signed' ? ` ` : ''}
`).join(''); } function renderSecretaryDocuments(documents) { const container = document.getElementById('secretary-documents-list'); if (!container) return; if (documents.length === 0) { container.innerHTML = '
Нет документов для согласования
'; return; } container.innerHTML = documents.map(doc => `
Документ №${doc.document_number || doc.id} ${doc.title} ${getDocumentStatusText(doc.status)} ${doc.urgency_level === 'urgent' ? 'Срочно' : ''} ${doc.urgency_level === 'very_urgent' ? 'Очень срочно' : ''}
От: ${doc.creator_name} Создан: ${formatDateTime(doc.created_at)} ${doc.due_date ? `Срок: ${formatDateTime(doc.due_date)}` : ''}

Тип: ${doc.document_type_name || 'Не указан'}

Номер: ${doc.document_number || 'Не указан'}

Дата документа: ${doc.document_date ? formatDate(doc.document_date) : 'Не указана'}

Количество страниц: ${doc.pages_count || 'Не указано'}

${doc.comment ? `

Комментарий автора: ${doc.comment}

` : ''}
${doc.files && doc.files.length > 0 ? ` Файлы:
${doc.files.map(file => renderFileIcon(file)).join('')}
` : 'Файлы: нет файлов'}
${doc.status === 'assigned' ? ` ` : ''} ${doc.status === 'in_progress' ? `
` : ''} ${doc.status === 'approved' ? `
` : ''} ${doc.status === 'received' ? `
` : ''} ${doc.status === 'refused' ? `

Причина отказа: ${doc.refusal_reason}

` : ''}
`).join(''); } function getDocumentStatusClass(status) { switch(status) { case 'assigned': return 'status-assigned'; case 'in_progress': return 'status-in-progress'; case 'approved': return 'status-approved'; case 'received': return 'status-received'; case 'signed': return 'status-signed'; case 'refused': return 'status-refused'; case 'cancelled': return 'status-cancelled'; default: return 'status-assigned'; } } function getDocumentStatusText(status) { switch(status) { case 'assigned': return 'Назначена'; case 'in_progress': return 'В работе'; case 'approved': return 'Согласован'; case 'received': return 'Получен'; case 'signed': return 'Подписан'; case 'refused': return 'Отказано'; case 'cancelled': return 'Отозвано'; default: return status; } } function formatDate(dateString) { if (!dateString) return ''; return new Date(dateString).toLocaleDateString('ru-RU'); } // Модальные окна для секретаря function showApproveModal(documentId) { currentDocumentId = documentId; document.getElementById('approve-document-modal').style.display = 'block'; } function closeApproveModal() { document.getElementById('approve-document-modal').style.display = 'none'; document.getElementById('approve-comment').value = ''; } function showReceiveModal(documentId) { currentDocumentId = documentId; document.getElementById('receive-document-modal').style.display = 'block'; } function closeReceiveModal() { document.getElementById('receive-document-modal').style.display = 'none'; document.getElementById('receive-comment').value = ''; } function showRefuseModal(documentId) { currentDocumentId = documentId; document.getElementById('refuse-document-modal').style.display = 'block'; } function closeRefuseModal() { document.getElementById('refuse-document-modal').style.display = 'none'; document.getElementById('refuse-reason').value = ''; } let currentDocumentId = null; // Функции для работы с API async function updateDocumentStatus(documentId, status, comment = '', refusalReason = '') { try { const response = await fetch(`/api/documents/${documentId}/status`, { method: 'PUT', headers: { 'Content-Type': 'application/json', }, body: JSON.stringify({ status: status, comment: comment, refusalReason: refusalReason }) }); if (response.ok) { alert('Статус документа обновлен!'); // Закрываем модальные окна closeApproveModal(); closeReceiveModal(); closeRefuseModal(); // Обновляем список документов if (isSecretary()) { loadSecretaryDocuments(); } loadMyDocuments(); } else { const error = await response.json(); alert(error.error || 'Ошибка обновления статуса'); } } catch (error) { console.error('Ошибка:', error); alert('Ошибка обновления статуса'); } } async function cancelDocument(documentId) { if (!confirm('Вы уверены, что хотите отозвать документ?')) { return; } try { const response = await fetch(`/api/documents/${documentId}/cancel`, { method: 'POST' }); if (response.ok) { alert('Документ отозван!'); loadMyDocuments(); } else { const error = await response.json(); alert(error.error || 'Ошибка отзыва документа'); } } catch (error) { console.error('Ошибка:', error); alert('Ошибка отзыва документа'); } } async function reworkDocument(documentId) { // Здесь можно открыть форму для повторной отправки alert('Функция исправления и повторной отправки будет реализована в следующей версии'); } async function downloadDocumentPackage(documentId) { try { const response = await fetch(`/api/documents/${documentId}/package`); if (response.ok) { const blob = await response.blob(); const url = window.URL.createObjectURL(blob); const a = document.createElement('a'); a.href = url; a.download = `document_${documentId}_package.zip`; document.body.appendChild(a); a.click(); window.URL.revokeObjectURL(url); document.body.removeChild(a); } else { const error = await response.json(); alert(error.error || 'Ошибка скачивания пакета документов'); } } catch (error) { console.error('Ошибка:', error); alert('Ошибка скачивания пакета документов'); } } function isSecretary() { return currentUser && currentUser.groups && currentUser.groups.includes('Секретарь'); } function showDocumentSection(sectionName) { // Скрываем все секции document.querySelectorAll('.document-section').forEach(section => { section.style.display = 'none'; }); // Показываем выбранную секцию const targetSection = document.getElementById(`${sectionName}-section`); if (targetSection) { targetSection.style.display = 'block'; } // Загружаем данные для секции if (sectionName === 'my-documents') { loadMyDocuments(); } else if (sectionName === 'secretary-documents' && isSecretary()) { loadSecretaryDocuments(); } } // Инициализация при загрузке страницы document.addEventListener('DOMContentLoaded', function() { if (window.location.pathname === '/doc') { initializeDocumentForm(); // Показываем соответствующие секции if (isSecretary()) { document.getElementById('secretary-tab').style.display = 'block'; } // По умолчанию показываем создание документа showDocumentSection('create-document'); } });