viberadar 0.3.201 → 0.3.203
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.
- package/dist/ui/dashboard.html +39 -22
- package/package.json +1 -1
package/dist/ui/dashboard.html
CHANGED
|
@@ -4707,9 +4707,10 @@ function renderObsGlobalDetail(c, filterFeatureKey) {
|
|
|
4707
4707
|
}).join('') || '<div class="obs-sub">Шумных паттернов не обнаружено</div>';
|
|
4708
4708
|
|
|
4709
4709
|
// ── Missing critical logs (V2: grouped by risk tier with failure points) ──
|
|
4710
|
-
const v2Data = missingV2.filter(m => m.failurePoints.length > 0);
|
|
4711
|
-
window.__obsMissingV2 = v2Data;
|
|
4712
|
-
|
|
4710
|
+
const v2Data = missingV2.filter(m => m.failurePoints.length > 0);
|
|
4711
|
+
window.__obsMissingV2 = v2Data;
|
|
4712
|
+
window.__obsMissingGroupMeta = {};
|
|
4713
|
+
const fpTypeLabels = {
|
|
4713
4714
|
'empty-catch':'пустой catch','catch-no-log':'catch без лога','promise-catch-no-log':'.catch без лога',
|
|
4714
4715
|
'http-no-error-handling':'HTTP без обработки','db-no-error-handling':'DB без обработки',
|
|
4715
4716
|
'throw-no-log':'throw без лога','error-check-no-log':'if(err) без лога',
|
|
@@ -4719,11 +4720,19 @@ function renderObsGlobalDetail(c, filterFeatureKey) {
|
|
|
4719
4720
|
const tierLabels = { critical:'Критичные', important:'Важные', normal:'Обычные' };
|
|
4720
4721
|
const tiers = ['critical','important','normal'];
|
|
4721
4722
|
const tierSections = tiers.map(tier => {
|
|
4722
|
-
const items = v2Data.filter(m => m.riskTier === tier);
|
|
4723
|
-
if (!items.length) return '';
|
|
4724
|
-
const groupId = 'missing-' + tier;
|
|
4725
|
-
const
|
|
4726
|
-
|
|
4723
|
+
const items = v2Data.filter(m => m.riskTier === tier);
|
|
4724
|
+
if (!items.length) return '';
|
|
4725
|
+
const groupId = 'missing-' + tier;
|
|
4726
|
+
const groupIndices = items
|
|
4727
|
+
.map(m => (o.missingCriticalLogsV2 || []).indexOf(m))
|
|
4728
|
+
.filter(idx => idx >= 0);
|
|
4729
|
+
window.__obsMissingGroupMeta[groupId] = {
|
|
4730
|
+
missingLogIndices: groupIndices,
|
|
4731
|
+
recommendationType: 'add event',
|
|
4732
|
+
};
|
|
4733
|
+
const expandBtn = hasAgent ? `<button class="obs-expand-btn" onclick="event.stopPropagation();toggleObsDetail('${groupId}')">▼</button>` : '';
|
|
4734
|
+
const copyGroupBtn = `<button class="obs-copy-btn" title="Скопировать prompt для всей группы" onclick="event.stopPropagation();obsCopyPrompt('obs-fix-selected',window.__obsMissingGroupMeta['${groupId}'])">📋 Промпт</button>`;
|
|
4735
|
+
const totalFPs = items.reduce((s,m) => s + m.failurePoints.length, 0);
|
|
4727
4736
|
const detailItems = items.map(m => {
|
|
4728
4737
|
const globalIdx = (o.missingCriticalLogsV2 || []).indexOf(m); // index in full unfiltered array — must match server's missingCriticalLogsV2
|
|
4729
4738
|
const fpCount = m.failurePoints.length;
|
|
@@ -4753,10 +4762,11 @@ function renderObsGlobalDetail(c, filterFeatureKey) {
|
|
|
4753
4762
|
const _blTier = _bl?.tiers?.[tier];
|
|
4754
4763
|
return `<div class="obs-tier-group">
|
|
4755
4764
|
<div class="obs-tier-group-header">
|
|
4756
|
-
<span class="obs-tier-badge obs-tier-${tier}">${tierLabels[tier]}</span>
|
|
4757
|
-
<span>${items.length}${_d(items.length, _blTier?.modules)} модулей, ${totalFPs}${_d(totalFPs, _blTier?.fps)} точек отказа</span>
|
|
4758
|
-
${
|
|
4759
|
-
|
|
4765
|
+
<span class="obs-tier-badge obs-tier-${tier}">${tierLabels[tier]}</span>
|
|
4766
|
+
<span>${items.length}${_d(items.length, _blTier?.modules)} модулей, ${totalFPs}${_d(totalFPs, _blTier?.fps)} точек отказа</span>
|
|
4767
|
+
${copyGroupBtn}
|
|
4768
|
+
${expandBtn}
|
|
4769
|
+
</div>
|
|
4760
4770
|
${detail}
|
|
4761
4771
|
</div>`;
|
|
4762
4772
|
}).join('');
|
|
@@ -4765,12 +4775,18 @@ function renderObsGlobalDetail(c, filterFeatureKey) {
|
|
|
4765
4775
|
missingSection = '<div class="obs-sub" style="color:var(--green)">Критичные сценарии покрыты</div>';
|
|
4766
4776
|
}
|
|
4767
4777
|
|
|
4768
|
-
const fieldGaps = fieldGapsData;
|
|
4769
|
-
|
|
4770
|
-
const
|
|
4771
|
-
|
|
4772
|
-
const
|
|
4773
|
-
const
|
|
4778
|
+
const fieldGaps = fieldGapsData;
|
|
4779
|
+
window.__obsFieldGroupMeta = {};
|
|
4780
|
+
const fieldGapEntries = Object.entries(fieldGaps).filter(([,v]) => v > 0).sort((a,b) => b[1] - a[1]);
|
|
4781
|
+
const fieldGapRows = fieldGapEntries.map(([name, count]) => {
|
|
4782
|
+
const groupId = 'field-' + name.replace(/[^a-z0-9]/gi, '_');
|
|
4783
|
+
const affectedItems = catalog.filter(c => (c.missingFields||[]).includes(name));
|
|
4784
|
+
window.__obsFieldGroupMeta[groupId] = {
|
|
4785
|
+
fieldName: name,
|
|
4786
|
+
catalogPaths: affectedItems.map(c => c.modulePath),
|
|
4787
|
+
};
|
|
4788
|
+
const expandBtn = hasAgent ? `<button class="obs-expand-btn" onclick="event.stopPropagation();toggleObsDetail('${groupId}')">▼</button>` : '';
|
|
4789
|
+
const copyFieldBtn = `<button class="obs-copy-btn" title="Скопировать prompt для всех модулей с этим полем" onclick="event.stopPropagation();obsCopyPrompt('obs-fix-selected',window.__obsFieldGroupMeta['${groupId}'])">📋 Промпт</button>`;
|
|
4774
4790
|
const detailItems = affectedItems.map(ci => {
|
|
4775
4791
|
const catIdx = catalog.indexOf(ci);
|
|
4776
4792
|
const otherMissing = (ci.missingFields||[]).filter(f => f !== name);
|
|
@@ -4789,10 +4805,11 @@ function renderObsGlobalDetail(c, filterFeatureKey) {
|
|
|
4789
4805
|
</div>` : '';
|
|
4790
4806
|
return `<div>
|
|
4791
4807
|
<div class="obs-list-item">
|
|
4792
|
-
<span><code>${escapeHtml(name)}</code></span>
|
|
4793
|
-
<strong style="color:${count > 20 ? 'var(--red)' : count > 5 ? 'var(--yellow)' : 'var(--muted)'}">${count} пропусков в ${affectedItems.length} модул${affectedItems.length === 1 ? 'е' : affectedItems.length < 5 ? 'ях' : 'ях'}</strong>
|
|
4794
|
-
${
|
|
4795
|
-
|
|
4808
|
+
<span><code>${escapeHtml(name)}</code></span>
|
|
4809
|
+
<strong style="color:${count > 20 ? 'var(--red)' : count > 5 ? 'var(--yellow)' : 'var(--muted)'}">${count} пропусков в ${affectedItems.length} модул${affectedItems.length === 1 ? 'е' : affectedItems.length < 5 ? 'ях' : 'ях'}</strong>
|
|
4810
|
+
${copyFieldBtn}
|
|
4811
|
+
${expandBtn}
|
|
4812
|
+
</div>
|
|
4796
4813
|
${detail}
|
|
4797
4814
|
</div>`;
|
|
4798
4815
|
}).join('') || '<div class="obs-sub" style="color:var(--green)">Все обязательные поля на месте</div>';
|