fix htmx refactor route mismatches and remaining TODO items
- wireguard: POST /peers with JSON encoding (was /add-peer) - rules: delete by rule_id in URL path (was JSON body); pass rule objects with id from server; add hx-disable to initial render - nat: port forward delete uses URL path params to match blueprint - nat: masquerade toggle uses native hx-post/hx-vals (was inline fetch) - app.js renderers updated to use URL path deletes for rules and forwards - remove TODO.md
This commit is contained in:
+69
-36
@@ -13,9 +13,7 @@
|
||||
<input type="checkbox" id="auto-refresh-toggle" onchange="toggleAutoRefresh()">
|
||||
<span class="slider"></span>
|
||||
</label>
|
||||
<span class="htmx-indicator text-sm" style="color:var(--accent);">
|
||||
<span id="refresh-indicator" style="display:none;">Refreshing...</span>
|
||||
</span>
|
||||
<span class="htmx-indicator text-sm" style="color:var(--accent);">Refreshing...</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -24,15 +22,16 @@
|
||||
<button class="tab" data-tab="nginx-access" onclick="switchTab('nginx-access')">Nginx Access</button>
|
||||
<button class="tab" data-tab="nginx-error" onclick="switchTab('nginx-error')">Nginx Error</button>
|
||||
<button class="tab" data-tab="dnsmasq" onclick="switchTab('dnsmasq')">Dnsmasq</button>
|
||||
<button class="tab" data-tab="app" onclick="switchTab('app')">App</button>
|
||||
</div>
|
||||
|
||||
<div id="tab-journal" class="tab-content active">
|
||||
<div class="card" style="padding:0;overflow:hidden;">
|
||||
<div class="log-viewer" id="log-journal"
|
||||
hx-get="/api/logs/journal"
|
||||
hx-trigger="every {{ (refresh_interval | default(15)) }}s"
|
||||
hx-swap="innerHTML"
|
||||
hx-indicator="#refresh-indicator">
|
||||
hx-get="/api/logs/journal"
|
||||
hx-trigger="none"
|
||||
hx-swap="innerHTML"
|
||||
hx-indicator=".page-header .htmx-indicator">
|
||||
Loading journal entries...
|
||||
</div>
|
||||
</div>
|
||||
@@ -41,10 +40,10 @@
|
||||
<div id="tab-nginx-access" class="tab-content">
|
||||
<div class="card" style="padding:0;overflow:hidden;">
|
||||
<div class="log-viewer" id="log-nginx-access"
|
||||
hx-get="/api/logs/nginx/access"
|
||||
hx-trigger="every {{ (refresh_interval | default(15)) }}s"
|
||||
hx-swap="innerHTML"
|
||||
hx-indicator="#refresh-indicator">
|
||||
hx-get="/api/logs/nginx/access"
|
||||
hx-trigger="none"
|
||||
hx-swap="innerHTML"
|
||||
hx-indicator=".page-header .htmx-indicator">
|
||||
Loading Nginx access log...
|
||||
</div>
|
||||
</div>
|
||||
@@ -53,10 +52,10 @@
|
||||
<div id="tab-nginx-error" class="tab-content">
|
||||
<div class="card" style="padding:0;overflow:hidden;">
|
||||
<div class="log-viewer" id="log-nginx-error"
|
||||
hx-get="/api/logs/nginx/error"
|
||||
hx-trigger="every {{ (refresh_interval | default(15)) }}s"
|
||||
hx-swap="innerHTML"
|
||||
hx-indicator="#refresh-indicator">
|
||||
hx-get="/api/logs/nginx/error"
|
||||
hx-trigger="none"
|
||||
hx-swap="innerHTML"
|
||||
hx-indicator=".page-header .htmx-indicator">
|
||||
Loading Nginx error log...
|
||||
</div>
|
||||
</div>
|
||||
@@ -65,42 +64,76 @@
|
||||
<div id="tab-dnsmasq" class="tab-content">
|
||||
<div class="card" style="padding:0;overflow:hidden;">
|
||||
<div class="log-viewer" id="log-dnsmasq"
|
||||
hx-get="/api/logs/dnsmasq"
|
||||
hx-trigger="every {{ (refresh_interval | default(15)) }}s"
|
||||
hx-swap="innerHTML"
|
||||
hx-indicator="#refresh-indicator">
|
||||
hx-get="/api/logs/dnsmasq"
|
||||
hx-trigger="none"
|
||||
hx-swap="innerHTML"
|
||||
hx-indicator=".page-header .htmx-indicator">
|
||||
Loading dnsmasq log...
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div id="tab-app" class="tab-content">
|
||||
<div class="card" style="padding:0;overflow:hidden;">
|
||||
<div class="log-viewer" id="log-app"
|
||||
hx-get="/api/logs/app"
|
||||
hx-trigger="none"
|
||||
hx-swap="innerHTML"
|
||||
hx-indicator=".page-header .htmx-indicator">
|
||||
Loading app log...
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
var autoRefreshTimer = null;
|
||||
var refreshInterval = {{ (refresh_interval | default(15)) }};
|
||||
var currentTab = 'journal';
|
||||
|
||||
function setActivePolling() {
|
||||
document.querySelectorAll('.log-viewer').forEach(function(el) {
|
||||
htmx.abort(el);
|
||||
el.setAttribute('hx-trigger', 'none');
|
||||
});
|
||||
var activeEl = document.getElementById('log-' + currentTab);
|
||||
if (activeEl) {
|
||||
activeEl.setAttribute('hx-trigger', 'every ' + refreshInterval + 's');
|
||||
}
|
||||
}
|
||||
|
||||
function loadActiveTab() {
|
||||
var activeEl = document.getElementById('log-' + currentTab);
|
||||
if (activeEl) {
|
||||
htmx.ajax('GET', activeEl);
|
||||
}
|
||||
}
|
||||
|
||||
var origSwitchTab = switchTab;
|
||||
switchTab = function(tabName) {
|
||||
currentTab = tabName;
|
||||
if (typeof origSwitchTab === 'function') {
|
||||
origSwitchTab(tabName);
|
||||
}
|
||||
if (document.getElementById('auto-refresh-toggle').checked) {
|
||||
setActivePolling();
|
||||
}
|
||||
loadActiveTab();
|
||||
};
|
||||
|
||||
function toggleAutoRefresh() {
|
||||
var toggle = document.getElementById('auto-refresh-toggle');
|
||||
var indicators = document.querySelectorAll('.log-viewer');
|
||||
|
||||
if (toggle.checked) {
|
||||
indicators.forEach(function(el) {
|
||||
el.setAttribute('hx-trigger', 'every 15s');
|
||||
hx.trigger(el, 'htmx:refresh');
|
||||
});
|
||||
setActivePolling();
|
||||
loadActiveTab();
|
||||
} else {
|
||||
indicators.forEach(function(el) {
|
||||
el.setAttribute('hx-trigger', 'never');
|
||||
document.querySelectorAll('.log-viewer').forEach(function(el) {
|
||||
htmx.abort(el);
|
||||
el.setAttribute('hx-trigger', 'none');
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
document.addEventListener('htmx:beforeRequest', function(evt) {
|
||||
if (evt.detail && evt.detail.path && evt.detail.path.startsWith('/api/logs')) {
|
||||
document.getElementById('refresh-indicator').style.display = 'inline';
|
||||
}
|
||||
});
|
||||
|
||||
document.addEventListener('htmx:afterRequest', function(evt) {
|
||||
document.getElementById('refresh-indicator').style.display = 'none';
|
||||
document.addEventListener('DOMContentLoaded', function() {
|
||||
loadActiveTab();
|
||||
});
|
||||
</script>
|
||||
{% endblock %}
|
||||
|
||||
Reference in New Issue
Block a user