Skip to content

Commit e9367a0

Browse files
wildleo91claude
andcommitted
fix: side-by-side diff view, reason field naming, sanitization, auto-refresh
Side-by-side diff view: - Replaced JSON blob diff with color-coded side-by-side Before/After tables - Smart column selection: wide CSVs show only changed + key columns (max 8) - Row capping: first 10 edits in detail, rest in compact expandable table - Stats bar with add/remove/edit counts, column change badges Reason field consistency (renamed for clear naming convention): - remove_reason → row_remove_reason (row removal events) - edit_reason → row_edit_reason (row edit events) - column_remove_reason (new, was sharing remove_reason) - All dashboard coalesce chains updated to match Fixes: - Inline multi-edit approval: new submitInlineMultiEditApproval() function (old path crashed on null.length when col/val were undefined) - Counter correction for approval replay drift (diff misclassifies edits as adds) - Usage tracking always increments (was skipped for approval replays) - reset_daily_usage "all" fix (was treated as username, not keyword) - Queue KeyError fix: item.get() for heterogeneous queue entries - Limit cap: editor and admin limits capped at 100 (was 1000/9999) - Reserved _ prefix columns blocked at backend (prevents limit bypass) - original_payload reason fields sanitized before storage - Auto-refresh on ALL approval types (was only create/remove) - Pending approval bar: no more duplicated reason text - Approval description uses analyst's reason (not auto-generated text) - Backend stores comment field in approval queue entries Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent 9fa8b07 commit e9367a0

6 files changed

Lines changed: 610 additions & 122 deletions

File tree

appserver/static/control_panel.js

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -367,7 +367,7 @@ require([
367367
var csvDisplay = isRuleOp ? "N/A" : item.csv_file;
368368
var ruleDisplay = item.detection_rule || "";
369369
// Combine description with payload-extracted reason for full context
370-
var analystReason = item.description || extractRequestReason(item) || "";
370+
var analystReason = item.comment || item.description || extractRequestReason(item) || "";
371371
html += '<tr>' +
372372
'<td style="font-size:11px;word-break:break-all">' + _.escape(item.request_id) + '</td>' +
373373
'<td>' + _.escape(tsStr) + '</td>' +
@@ -428,7 +428,7 @@ require([
428428
var isRuleOp = item.csv_file === "__rule_operation__";
429429
var csvDisplay = isRuleOp ? "N/A" : item.csv_file;
430430
var ruleDisplay = item.detection_rule || "";
431-
var analystReason = item.description || extractRequestReason(item) || "";
431+
var analystReason = item.comment || item.description || extractRequestReason(item) || "";
432432
var adminResponse = item.rejection_reason || item.cancellation_reason ||
433433
item.admin_comment || "";
434434
html += '<tr>' +
@@ -1898,7 +1898,7 @@ require([
18981898
'<td style="color:var(--wl-muted,#888)">' + def + '</td>' +
18991899
'<td><input type="number" class="wl-admin-limit-input" ' +
19001900
'data-key="' + f.key + '" value="' + cur + '" ' +
1901-
'min="0" max="9999" style="width:80px;padding:4px 8px;' +
1901+
'min="0" max="100" style="width:80px;padding:4px 8px;' +
19021902
'background:var(--wl-bg-main,#1a1c1e);color:var(--wl-text,#e0e0e0);' +
19031903
'border:1px solid var(--wl-border,#444);border-radius:4px"></td>' +
19041904
'</tr>';

appserver/static/whitelist_manager.css

Lines changed: 122 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -641,50 +641,146 @@ body.wl-resizing * {
641641
margin-bottom: 14px;
642642
}
643643

644-
.wl-diff-added h5 {
645-
color: var(--wl-diff-add);
646-
margin: 0 0 4px;
644+
.wl-diff-section h5 {
645+
margin: 0 0 8px;
646+
font-size: 13px;
647647
}
648648

649-
.wl-diff-added li {
650-
color: var(--wl-diff-add);
651-
font-family: "Courier New", monospace;
649+
/* ── Side-by-side diff table ─────────────────────────────────────── */
650+
651+
.wl-diff-sbs {
652+
display: grid;
653+
grid-template-columns: 1fr 1fr;
654+
gap: 12px;
655+
margin-bottom: 14px;
656+
}
657+
658+
.wl-diff-pane {
659+
border: 1px solid var(--wl-border, #444);
660+
border-radius: 4px;
661+
overflow: hidden;
662+
}
663+
664+
.wl-diff-pane-header {
665+
padding: 6px 12px;
666+
font-weight: bold;
652667
font-size: 12px;
653-
word-break: break-all;
668+
text-transform: uppercase;
669+
letter-spacing: 0.5px;
654670
}
655671

656-
.wl-diff-removed h5 {
672+
.wl-diff-pane-before .wl-diff-pane-header {
673+
background: rgba(198, 40, 40, 0.15);
657674
color: var(--wl-diff-rm);
658-
margin: 0 0 4px;
675+
border-bottom: 2px solid var(--wl-diff-rm);
659676
}
660677

661-
.wl-diff-removed li {
662-
color: var(--wl-diff-rm);
663-
font-family: "Courier New", monospace;
678+
.wl-diff-pane-after .wl-diff-pane-header {
679+
background: rgba(46, 125, 50, 0.15);
680+
color: var(--wl-diff-add);
681+
border-bottom: 2px solid var(--wl-diff-add);
682+
}
683+
684+
.wl-diff-pane table {
685+
width: 100%;
686+
border-collapse: collapse;
664687
font-size: 12px;
665-
word-break: break-all;
688+
font-family: "Courier New", Consolas, monospace;
666689
}
667690

668-
.wl-diff-pre {
669-
background: #1e1e1e;
670-
color: #d4d4d4;
671-
padding: 12px 14px;
672-
border-radius: 4px;
691+
.wl-diff-pane th {
692+
padding: 4px 8px;
693+
text-align: left;
694+
font-weight: bold;
695+
border-bottom: 1px solid var(--wl-border, #444);
696+
background: var(--wl-bg-row, #23272b);
697+
color: var(--wl-muted, #888);
698+
font-size: 11px;
699+
}
700+
701+
.wl-diff-pane td {
702+
padding: 4px 8px;
703+
border-bottom: 1px solid var(--wl-border-section, #333);
704+
word-break: break-word;
705+
max-width: 300px;
706+
}
707+
708+
.wl-diff-cell-changed {
709+
font-weight: bold;
710+
}
711+
712+
.wl-diff-pane-before .wl-diff-cell-changed {
713+
background: rgba(198, 40, 40, 0.12);
714+
color: var(--wl-diff-rm);
715+
}
716+
717+
.wl-diff-pane-after .wl-diff-cell-changed {
718+
background: rgba(46, 125, 50, 0.12);
719+
color: var(--wl-diff-add);
720+
}
721+
722+
/* ── Row-level additions/removals ──────────────────────────────── */
723+
724+
.wl-diff-row-list {
725+
padding: 0;
726+
margin: 0;
727+
list-style: none;
728+
}
729+
730+
.wl-diff-row-list li {
731+
padding: 4px 10px;
732+
font-family: "Courier New", Consolas, monospace;
673733
font-size: 12px;
674-
overflow-x: auto;
675-
line-height: 1.6;
734+
border-bottom: 1px solid var(--wl-border-section, #333);
735+
}
736+
737+
.wl-diff-row-add {
738+
background: rgba(46, 125, 50, 0.08);
739+
color: var(--wl-diff-add);
740+
}
741+
742+
.wl-diff-row-add::before {
743+
content: "+ ";
744+
font-weight: bold;
676745
}
677746

678-
.wl-diff-line-add {
679-
color: #4ec94e;
747+
.wl-diff-row-rm {
748+
background: rgba(198, 40, 40, 0.08);
749+
color: var(--wl-diff-rm);
680750
}
681751

682-
.wl-diff-line-rm {
683-
color: #f44336;
752+
.wl-diff-row-rm::before {
753+
content: "- ";
754+
font-weight: bold;
755+
}
756+
757+
/* ── Column changes ──────────────────────────────────────────────── */
758+
759+
.wl-diff-col-badge {
760+
display: inline-block;
761+
padding: 2px 8px;
762+
border-radius: 3px;
763+
font-size: 11px;
764+
margin: 2px 4px 2px 0;
765+
}
766+
767+
.wl-diff-col-add {
768+
background: rgba(46, 125, 50, 0.15);
769+
color: var(--wl-diff-add);
770+
border: 1px solid var(--wl-diff-add);
771+
}
772+
773+
.wl-diff-col-rm {
774+
background: rgba(198, 40, 40, 0.15);
775+
color: var(--wl-diff-rm);
776+
border: 1px solid var(--wl-diff-rm);
684777
}
685778

686-
.wl-diff-line-info {
687-
color: #64b5f6;
779+
/* ── Responsive: stack on narrow screens ─────────────────────────── */
780+
@media (max-width: 900px) {
781+
.wl-diff-sbs {
782+
grid-template-columns: 1fr;
783+
}
688784
}
689785

690786
/* ── Date/Time Picker ──────────────────────────────────────────────── */

0 commit comments

Comments
 (0)