Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
50 changes: 49 additions & 1 deletion web-static/dashboard.html
Original file line number Diff line number Diff line change
Expand Up @@ -1248,7 +1248,26 @@
max-width: 100%;
}
}


/* Narrow phones (<=480px): the header info boxes carry INLINE
min-width (280px / 220px) which the wider breakpoints cannot
override, and the monospace config lines (stratum URL, the
<ADDR>,<DOGE_ADDR>.WORKER username) are unbreakable tokens.
Together they force horizontal overflow that clips the view on
a phone. Neutralize the inline mins and let long tokens wrap.
Static drop-in; serves the operator-flagged D-WEB.4 mobile clip. */
@media (max-width: 480px) {
#miner-info, #network-info {
min-width: 0 !important;
flex: 1 1 100% !important;
}
.miner-info [style*="monospace"],
.miner-info [style*="monospace"] span {
overflow-wrap: anywhere;
word-break: break-word;
}
}

/* Two-column layout for sections */
.two-col {
display: grid;
Expand Down Expand Up @@ -1790,6 +1809,12 @@ <h3><span class="icon">🔀</span> Share-Version Crossing</h3>
<div class="stat-sub">Vote: <span id="v36_vote_pct">-</span> &nbsp;·&nbsp; Work-weighted: <span id="v36_ww_pct">-</span></div>
<div class="stat-detail"><span id="v36_share_label">-</span> &rarr; <span id="v36_target_label">-</span> <span id="v36_msg" style="opacity:0.7;"></span></div>
</div>
<!-- Per-node topology: THIS node's REAL coin set from /api/node_topology (charter #2, config-driven/auto-detected -- never a baked-in coin list) -->
<div class="stat-card" id="node_topology_card" style="display:none;">
<h3><span class="icon">🧭</span> Node Topology <span id="node_topology_symbol" style="font-size:0.6em;opacity:0.6;"></span></h3>
<div id="node_topology_coins" class="stat-sub" style="line-height:1.6;"></div>
<div class="stat-detail" id="node_topology_note" style="opacity:0.6;"></div>
</div>
</div>

<!-- Right Column: Top stats row + Graph -->
Expand Down Expand Up @@ -2888,6 +2913,7 @@ <h4>Legend</h4>
d3.json('../merged_stats', function(d) { _ms = d || {}; _tryRenderStats(); });
d3.json('../best_share', function(d) { _bs = d || {}; _tryRenderStats(); });
d3.json('../v36_status', function(d) { if (d) renderV36Status(d); });
d3.json('../api/node_topology', function(d) { if (d) renderNodeTopology(d); });
}

// V36 crossing widget: maps /v36_status ratchet state to an at-a-glance label.
Expand All @@ -2914,6 +2940,28 @@ <h4>Legend</h4>
d3.select('#v36_msg').text(v.message ? '\u00b7 ' + v.message : '');
}

// Per-node topology: renders THIS node's real coin set (primary + embedded/aux),
// peer counts and embedded/RPC flags, straight from /api/node_topology.
// Config-driven/auto-detected -- never a baked-in coin list (charter #2).
function renderNodeTopology(t) {
var card = document.getElementById('node_topology_card');
if (!card || !t || !Array.isArray(t.coins) || !t.coins.length) return;
var rows = t.coins.map(function(c) {
var tags = [];
if (c.primary) tags.push('primary');
if (c.embedded) tags.push('embedded');
if (c.has_rpc) tags.push('rpc');
var tagStr = tags.length ? ' <span style="opacity:0.6;">[' + tags.join(', ') + ']</span>' : '';
var peers = (c.peers != null ? c.peers : 0);
return '<div><strong>' + c.coin + '</strong>' + tagStr +
' &nbsp;&middot;&nbsp; ' + peers + ' peer' + (peers === 1 ? '' : 's') + '</div>';
}).join('');
document.getElementById('node_topology_coins').innerHTML = rows;
d3.select('#node_topology_symbol').text(t.node_symbol ? '(' + t.node_symbol + ')' : '');
d3.select('#node_topology_note').text(t.auto_detected ? 'auto-detected' : '');
card.style.display = '';
}

function renderBestShare(bs) {
if (!bs || !bs.round) return;
d3.select('#best_share_round_pct_fancy').html(format_pct_fancy(bs.round.pct_of_block));
Expand Down
Loading