v1.0.177: сравнение внутри карточки группы, только одно одновременно

This commit is contained in:
2026-06-24 19:34:00 +04:00
parent c223fc04c0
commit 498bee90d8
+55 -19
View File
@@ -414,19 +414,40 @@ async function loadGroups() {
escHtml(d.filename) + escHtml(d.filename) +
(d.doc_date ? ' <span style="color:var(--muted);">' + escHtml(d.doc_date) + '</span>' : '') + (d.doc_date ? ' <span style="color:var(--muted);">' + escHtml(d.doc_date) + '</span>' : '') +
'</div>'; '</div>';
}).join('') + '</div>'; }).join('') + '</div>' +
card.innerHTML += '<button class="btn btn-primary" style="margin-top:6px;font-size:12px;height:28px;" onclick="runCompareForGroup(' + gi + ')">▶ Сравнить эту группу</button>'; '<button class="btn btn-primary cmp-btn" style="margin-top:6px;font-size:12px;height:28px;" data-gi="' + gi + '">▶ Сравнить эту группу</button>' +
'<div class="cmp-body" id="cmpBody_' + gi + '" style="display:none;margin-top:8px;"></div>';
} }
diffBody.appendChild(card); diffBody.appendChild(card);
}); });
// Один обработчик на все кнопки сравнения
diffBody.querySelectorAll('.cmp-btn').forEach(function(btn) {
btn.addEventListener('click', function() {
var gi = parseInt(this.getAttribute('data-gi'));
runCompareForGroup(gi, this);
});
});
lucide.createIcons(); lucide.createIcons();
} }
window.runCompareForGroup = async function(gi) { // Текущий активный EventSource (только один одновременно)
var _activeCompareES = null;
var _activeCompareTimer = null;
window.runCompareForGroup = async function(gi, btn) {
var group = window._groupsData[gi]; var group = window._groupsData[gi];
if (!group || group.contract_number === '__unresolved__') return; if (!group || group.contract_number === '__unresolved__') return;
var btn = event.target; // Остановить предыдущее сравнение
if (_activeCompareES) { _activeCompareES.close(); _activeCompareES = null; }
if (_activeCompareTimer) { clearInterval(_activeCompareTimer); _activeCompareTimer = null; }
// Свернуть все раскрытые сравнения
document.querySelectorAll('.cmp-body').forEach(function(el) { el.style.display = 'none'; });
document.querySelectorAll('.cmp-btn').forEach(function(b) {
b.disabled = false; b.innerHTML = '▶ Сравнить эту группу';
});
btn.disabled = true; btn.disabled = true;
btn.innerHTML = '<span class="spinner"></span> Применяю...'; btn.innerHTML = '<span class="spinner"></span> Применяю...';
@@ -441,23 +462,26 @@ window.runCompareForGroup = async function(gi) {
} }
var cid = ad.contract_ids[0]; var cid = ad.contract_ids[0];
var cmpBody = document.getElementById('cmpBody_' + gi);
cmpBody.style.display = 'block';
cmpBody.innerHTML = '';
btn.innerHTML = '<span class="spinner"></span> Сравнение...'; btn.innerHTML = '<span class="spinner"></span> Сравнение...';
stepActive('stepCompare'); stepActive('stepCompare');
var compareCard = document.getElementById('compareCard'); var statusEl = document.createElement('div');
var compareBody = document.getElementById('compareBody'); statusEl.style.cssText = 'font-size:11px;color:var(--muted);margin-bottom:4px;';
var compareStatus = document.getElementById('compareStatus'); statusEl.textContent = '⏳ 0.0с';
compareCard.style.display = 'block'; cmpBody.appendChild(statusEl);
compareBody.innerHTML = '';
compareStatus.textContent = '⏳ 0.0с';
var start = Date.now(); var start = Date.now();
var timer = setInterval(function() { _activeCompareTimer = setInterval(function() {
compareStatus.textContent = '⏳ ' + ((Date.now() - start) / 1000).toFixed(1) + 'с'; statusEl.textContent = '⏳ ' + ((Date.now() - start) / 1000).toFixed(1) + 'с';
}, 200); }, 200);
var es = new EventSource(VM_API + '/process-v2?contract_id=' + cid); var es = new EventSource(VM_API + '/process-v2?contract_id=' + cid);
_activeCompareES = es;
var sections = {}; var sections = {};
es.onmessage = function(e) { es.onmessage = function(e) {
var d = JSON.parse(e.data); var d = JSON.parse(e.data);
@@ -469,7 +493,7 @@ window.runCompareForGroup = async function(gi) {
var body = sec.querySelector('.diff-section-body'); var body = sec.querySelector('.diff-section-body');
body.style.display = body.style.display === 'none' ? 'block' : 'none'; body.style.display = body.style.display === 'none' ? 'block' : 'none';
}); });
compareBody.appendChild(sec); cmpBody.appendChild(sec);
sections[d.supplement_id] = sec; sections[d.supplement_id] = sec;
} }
else if (d.type === 'llm_done') { else if (d.type === 'llm_done') {
@@ -497,18 +521,30 @@ window.runCompareForGroup = async function(gi) {
} }
} }
else if (d.type === 'done') { else if (d.type === 'done') {
clearInterval(timer); es.close(); clearInterval(_activeCompareTimer); _activeCompareTimer = null;
compareStatus.textContent = '✓ ' + d.total_time_s + 'с'; es.close(); _activeCompareES = null;
btn.innerHTML = '✓ Готово'; btn.disabled = false; statusEl.textContent = '✓ ' + d.total_time_s + 'с';
statusEl.style.color = 'var(--green)';
btn.innerHTML = '✓ Готово (' + d.total_time_s + 'с)';
btn.style.background = 'var(--green)';
btn.style.color = '#fff';
btn.style.borderColor = 'var(--green)';
btn.style.cursor = 'default';
btn.disabled = false;
stepDone('stepCompare'); stepDone('stepCompare');
} }
else if (d.type === 'error') { else if (d.type === 'error') {
clearInterval(timer); es.close(); clearInterval(_activeCompareTimer); _activeCompareTimer = null;
compareBody.innerHTML += '<div style="color:var(--destructive);">✗ ' + d.message + '</div>'; es.close(); _activeCompareES = null;
cmpBody.innerHTML += '<div style="color:var(--destructive);">✗ ' + d.message + '</div>';
btn.innerHTML = '✗'; btn.disabled = false; btn.innerHTML = '✗'; btn.disabled = false;
} }
}; };
es.onerror = function() { clearInterval(timer); es.close(); btn.innerHTML = '✗ соединение'; btn.disabled = false; }; es.onerror = function() {
clearInterval(_activeCompareTimer); _activeCompareTimer = null;
es.close(); _activeCompareES = null;
btn.innerHTML = '✗ соединение'; btn.disabled = false;
};
}; };
function uploadFile(file, onProgress) { function uploadFile(file, onProgress) {