{ "views": [ { "id": "view_overview", "client_requirement": "client_is_nothing+", "items": [ { "type": "auth_wrapper", "client_requirement": "client_is_nothing=", "items": [ { "type": "auth_card", "items": [ { "type": "h1", "text": "Routlin Dashboard" }, { "type": "p", "text": "Log in to monitor and manage your network." }, { "type": "spacer" }, { "type": "button_primary", "action": "/view/view_log_in", "text": "Log In" } ] } ] }, { "type": "page_header", "client_requirement": "client_is_viewer+", "items": [ { "type": "h1", "text": "Overview" }, { "type": "p", "text": "Current network status at a glance." } ] }, { "type": "stat_card_grid", "client_requirement": "client_is_viewer+", "items": [ { "type": "stat_card", "label": "DHCP Leases", "value": "%STAT_LEASE_COUNT%", "sub": "active leases", "variant": "accent" }, { "type": "stat_card", "label": "Queries Blocked", "value": "%STAT_BLOCKED_TODAY%", "sub": "since midnight", "variant": "warning" }, { "type": "stat_card", "label": "Public IP", "value": "%STAT_PUBLIC_IP%", "sub": "%STAT_DDNS_HOSTNAME%" } ] }, { "type": "card", "label": "Network", "client_requirement": "client_is_viewer+", "items": [ { "type": "grid", "rows": [ { "cells": [ { "type": "grid_label", "text": "WAN Interface" }, { "type": "grid_value", "text": "%GENERAL_WAN_INTERFACE%" } ] }, { "cells": [ { "type": "grid_label", "text": "VLANs" }, { "type": "grid_value", "text": "%OVERVIEW_VLAN_NAMES%" } ] }, { "cells": [ { "type": "grid_label", "text": "Firewall" }, { "type": "grid_value", "text": "%STAT_NFTABLES_STATUS%" } ] }, { "cells": [ { "type": "grid_label", "text": "System Uptime" }, { "type": "grid_value", "text": "%STAT_UPTIME%" } ] } ] } ] }, { "type": "card", "label": "DNS Blocking", "client_requirement": "client_is_viewer+", "items": [ { "type": "grid", "rows": [ { "cells": [ { "type": "grid_label", "text": "Blocked Domains" }, { "type": "grid_value", "text": "%STAT_BLOCKED_DOMAINS%" } ] }, { "cells": [ { "type": "grid_label", "text": "Active Blocklists" }, { "type": "grid_value", "text": "%STAT_BLOCKLIST_COUNT% lists" } ] }, { "cells": [ { "type": "grid_label", "text": "Last Refreshed" }, { "type": "grid_value", "text": "%STAT_BL_LAST_UPDATE%" } ] }, { "cells": [ { "type": "grid_label", "text": "Active IP Bans" }, { "type": "grid_value", "text": "%STAT_BANNED_IP_COUNT% rules" } ] } ] } ] }, { "type": "card", "label": "DNS Caching", "client_requirement": "client_is_viewer+", "items": [ { "type": "grid", "rows": [ { "cells": [ { "type": "grid_label", "text": "Total Queries" }, { "type": "grid_value", "text": "%DNS_STAT_QUERIES%" } ] }, { "cells": [ { "type": "grid_label", "text": "Cache Hits" }, { "type": "grid_value", "text": "%DNS_STAT_HITS% (%DNS_STAT_HIT_RATE% hit rate)" } ] }, { "cells": [ { "type": "grid_label", "text": "Forwarded" }, { "type": "grid_value", "text": "%DNS_STAT_FORWARDED%" } ] }, { "cells": [ { "type": "grid_label", "text": "Cache Capacity" }, { "type": "grid_value", "text": "%DNS_CACHE_SIZE% entries" } ] }, { "cells": [ { "type": "grid_label", "text": "Authoritative Answers" }, { "type": "grid_value", "text": "%DNS_STAT_AUTH%" } ] }, { "cells": [ { "type": "grid_label", "text": "TCP Connections Peak" }, { "type": "grid_value", "text": "%DNS_STAT_TCP_PEAK%" } ] }, { "cells": [ { "type": "grid_label", "text": "DNS Providers" }, { "type": "grid_value", "text": "%OVERVIEW_UPSTREAM_SERVERS%" } ] } ] } ] } ] }, { "id": "view_ddns", "client_requirement": "client_is_viewer+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "DDNS" }, { "type": "p", "text": "Dynamic DNS provider status and last known IP update." } ] }, { "type": "stat_card_grid", "items": [ { "type": "stat_card", "label": "Current Public IP", "value": "%STAT_PUBLIC_IP%", "sub": "%STAT_PUBLIC_IP_LAST_OBTAINED%" }, { "type": "stat_card", "label": "IP Check Interval", "value": "%DDNS_TIMER_INTERVAL%", "sub": "%STAT_PUBLIC_IP_LAST_CHECKED%", "edit_action": "/action/ddns_cardipcheckinterval_save", "edit_field": "timer_interval", "edit_input_type": "number", "edit_min": "1", "edit_suffix": "minutes", "edit_value": "%DDNS_TIMER_INTERVAL_MINS%" }, { "type": "stat_card", "label": "IP Check Services", "value": "%STAT_IP_CHECK_TOTAL%", "sub": "%STAT_IP_CHECK_SUB%", "reveal_card_id": "ip-check-services-edit" } ] }, { "type": "card", "id": "ip-check-services-edit", "label": "IP Check Services", "hidden": true, "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/ddns_cardipcheckservices_save", "method": "post", "items": [ { "type": "editable_list", "label": "HTTP APIs", "name": "http_services", "item_placeholder": "https://...", "add_label": "Add HTTP API", "items": "%IP_CHECK_HTTP_JSON%" }, { "type": "editable_list", "label": "Dig APIs", "name": "dig_services", "item_placeholder": "e.g. @1.1.1.1 ch txt whoami.cloudflare", "add_label": "Add Dig API", "items": "%IP_CHECK_DIG_JSON%" }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/ddns_cardipcheckservices_save", "method": "post", "text": "Save" }, { "type": "button_cancel", "text": "Cancel", "class": "js-hide-card" } ] } ] } ] }, { "type": "table", "datasource": "config:ddns_providers", "empty_message": "No DDNS providers configured.", "columns": [ { "label": "Description", "field": "description" }, { "label": "Provider", "field": "provider" }, { "label": "Hostname(s)", "field": "hostnames", "render": "tag_list" }, { "label": "Status", "field": "enabled", "render": "badge_enabled_disabled" }, { "label": "Credentials", "field": "credentials", "render": "raw_html" } ], "row_actions": [ { "client_requirement": "client_is_administrator+", "action": "/action/ddns_tableaccounts_rowedit", "method": "inline_edit", "text": "Edit", "class": "btn-ghost btn-sm", "fields": [ { "col": "description", "input_type": "text" }, { "col": "provider", "input_type": "select", "options": "%DDNS_PROVIDER_OPTIONS%" }, { "col": "hostnames", "input_type": "textarea" }, { "col": "enabled", "input_type": "checkbox" }, { "col": "credentials", "input_type": "credentials" } ] }, { "client_requirement": "client_is_administrator+", "action": "/action/ddns_tableaccounts_rowdelete", "method": "post", "text": "Delete", "class": "btn-danger btn-sm" } ] }, { "type": "card", "label": "Add DDNS Account", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/ddns_cardaddaccount_add", "method": "post", "items": [ { "type": "field", "label": "Description", "name": "description", "input_type": "text", "placeholder": "e.g. My DuckDNS Account" }, { "type": "field", "label": "Provider", "name": "provider", "input_type": "select", "options": "%DDNS_PROVIDER_OPTIONS%" }, { "type": "field", "label": "Hostnames (one per line)", "name": "hostnames", "input_type": "textarea", "placeholder": "e.g. myhome.duckdns.org" }, { "type": "credential_fields", "provider_select": "provider" }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/ddns_cardaddaccount_add", "method": "post", "text": "Add Provider" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] }, { "type": "card", "label": "Logging", "client_requirement": "client_is_administrator+", "items": [ { "type": "pre_block", "text": "%DDNS_LOG_TAIL%", "scroll_to_bottom": true }, { "type": "raw_html", "html": "%DDNS_LOG_SUMMARY%" }, { "type": "button_row", "justify": "space-between", "items": [ { "type": "button_ghost", "action": "/action/ddns_cardlogging_download", "text": "Download Log" }, { "type": "button_danger", "action": "/action/ddns_cardlogging_clear", "method": "post", "text": "Clear Log" } ] }, { "type": "hr" }, { "type": "form", "action": "/action/ddns_cardlogging_save", "method": "post", "items": [ { "type": "field", "label": "Max Log Size (KB)", "name": "log_max_kb", "input_type": "number", "layout": "inline", "value": "%DDNS_GEN_LOG_MAX_KB%", "min": "64" }, { "type": "field", "label": "", "name": "log_errors_only", "input_type": "checkbox", "checkbox_label": "Only record errors to log", "value": "%DDNS_GEN_LOG_ERRORS_ONLY%" }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/ddns_cardlogging_save", "method": "post", "text": "Save" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] } ] }, { "id": "view_general", "client_requirement": "client_is_viewer+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "General Settings" }, { "type": "p", "text": "Core network and logging configuration from core.json." } ] }, { "type": "card", "label": "Pending Changes", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/general_cardpendingchanges_save", "method": "post", "items": [ { "type": "field", "label": "Apply on Save", "name": "apply_on_save", "input_type": "checkbox", "value": "%GENERAL_APPLY_ON_SAVE%", "hint": "When enabled, saved changes are queued immediately. When disabled, changes accumulate here until you click Apply Now." }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/general_cardpendingchanges_save", "method": "post", "text": "Save" }, { "type": "button_cancel", "text": "Cancel" } ] } ] }, { "type": "raw_html", "html": "%PENDING_CHANGES_HTML%" } ] } ] }, { "id": "view_network_interfaces", "client_requirement": "client_is_administrator+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "Network Interfaces" }, { "type": "p", "text": "WAN/LAN interface assignments and per-interface settings." } ] }, { "type": "card", "label": "Network Interfaces", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/networkinterfaces_cardnetworkinterface_save", "method": "post", "items": [ { "type": "field", "label": "WAN Interface", "name": "wan_interface", "input_type": "interface_picker", "value": "%GENERAL_WAN_INTERFACE%", "data": "%NETWORK_INTERFACE_DATA_JSON%" }, { "type": "field", "label": "LAN Interface", "name": "lan_interface", "input_type": "interface_picker", "value": "%GENERAL_LAN_INTERFACE%", "data": "%NETWORK_INTERFACE_DATA_JSON%" }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/networkinterfaces_cardnetworkinterface_save", "method": "post", "text": "Save" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] }, { "type": "card", "id": "iface-config-card", "label": "Interface Configuration", "hidden": true, "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/networkinterfaces_cardinterfaceconfiguration_apply", "method": "post", "items": [ { "type": "hidden", "name": "original_mtu", "value": "" }, { "type": "hidden", "name": "original_mac", "value": "" }, { "type": "field_row", "cols": 3, "items": [ { "type": "field", "label": "Interface", "name": "iface", "input_type": "text", "readonly": true, "value": "" }, { "type": "field", "label": "MTU", "name": "mtu", "input_type": "select", "value": "", "options": [ { "label": "576", "value": "576" }, { "label": "1280", "value": "1280" }, { "label": "1492", "value": "1492" }, { "label": "1500", "value": "1500" }, { "label": "4096", "value": "4096" }, { "label": "9000", "value": "9000" } ] }, { "type": "field", "label": "MAC Address", "name": "mac", "input_type": "text", "validate": "mac", "value": "" } ] }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/networkinterfaces_cardinterfaceconfiguration_apply", "method": "post", "text": "Apply" }, { "type": "button_secondary", "action": "#", "text": "Cancel", "class": "iface-config-cancel" } ] } ] } ] }, { "type": "raw_html", "html": "




" } ] }, { "id": "view_upstream_dns", "client_requirement": "client_is_administrator+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "Upstream DNS" }, { "type": "p", "text": "Upstream resolvers and caching behaviour for dnsmasq." } ] }, { "type": "card", "label": "Upstream DNS", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/upstreamdns_cardupstreamdns_save", "method": "post", "items": [ { "type": "field", "label": "Strict Order", "name": "strict_order", "input_type": "checkbox", "value": "%DNS_STRICT_ORDER%", "hint": "Query DNS providers in list order rather than in parallel." }, { "type": "field", "label": "Cache Size", "name": "cache_size", "input_type": "number", "value": "%DNS_CACHE_SIZE%", "min": 0, "hint": "Max DNS responses to cache per instance. Set to 0 to disable caching." }, { "type": "editable_list", "label": "DNS Providers", "name": "upstream_servers", "item_placeholder": "e.g. 1.1.1.1", "add_label": "Add Provider", "validate": "ip", "hint": "DNS resolvers queried for external hostnames. Supports IPv4 and IPv6.", "items": "%DNS_UPSTREAM_SERVERS_JSON%" }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/upstreamdns_cardupstreamdns_save", "method": "post", "text": "Save" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] } ] }, { "id": "view_banned_ips", "client_requirement": "client_is_viewer+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "Banned IPs" }, { "type": "p", "text": "IPs and ranges blocked in both directions at the nftables firewall." } ] }, { "type": "info_bar", "variant": "info", "text": "Supports single IPs, CIDR (94.130.0.0/16), wildcards (94.130.*.*), and ranges (94.130.52.1-20). IPv4 and IPv6 are both supported." }, { "type": "table", "datasource": "config:banned_ips", "empty_message": "No IP bans configured.", "columns": [ { "label": "Description", "field": "description" }, { "label": "IP / Range", "field": "ip", "class": "col-mono" }, { "label": "Status", "field": "enabled", "render": "badge_enabled_disabled" } ], "row_actions": [ { "client_requirement": "client_is_administrator+", "action": "/action/edit_banned_ip", "method": "inline_edit", "text": "Edit", "class": "btn-ghost btn-sm", "fields": [ { "col": "description", "input_type": "text" }, { "col": "ip", "input_type": "text" }, { "col": "enabled", "input_type": "checkbox" } ] }, { "client_requirement": "client_is_administrator+", "action": "/action/delete_banned_ip", "method": "post", "text": "Delete", "class": "btn-danger btn-sm" } ] }, { "type": "card", "id": "add-form", "label": "Add Banned IP", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/add_banned_ip", "method": "post", "items": [ { "type": "field", "label": "Description", "name": "description", "input_type": "text", "placeholder": "e.g. Bad actor", "hint": "Optional label for this entry." }, { "type": "field", "label": "IP / Range", "name": "ip", "input_type": "text", "placeholder": "e.g. 1.2.3.4 or 1.2.3.0/24" }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/add_banned_ip", "method": "post", "text": "Add Banned IP" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] } ] }, { "id": "view_host_overrides", "client_requirement": "client_is_viewer+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "Host Overrides" }, { "type": "p", "text": "Force a hostname to resolve to a specific internal IP." } ] }, { "type": "table", "datasource": "config:host_overrides", "empty_message": "No host overrides configured.", "columns": [ { "label": "Description", "field": "description" }, { "label": "Hostname", "field": "host", "class": "col-mono" }, { "label": "Resolves To", "field": "ip", "class": "col-mono" }, { "label": "Status", "field": "enabled", "render": "badge_enabled_disabled" } ], "row_actions": [ { "client_requirement": "client_is_administrator+", "action": "/action/edit_host_override", "method": "inline_edit", "text": "Edit", "class": "btn-ghost btn-sm", "fields": [ { "col": "description", "input_type": "text" }, { "col": "host", "input_type": "text", "validate": "domainname" }, { "col": "ip", "input_type": "text", "validate": "ip" }, { "col": "enabled", "input_type": "checkbox" } ] }, { "client_requirement": "client_is_administrator+", "action": "/action/delete_host_override", "method": "post", "text": "Delete", "class": "btn-danger btn-sm" } ] }, { "type": "card", "id": "add-form", "label": "Add Host Override", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/add_host_override", "method": "post", "items": [ { "type": "field", "label": "Description", "name": "description", "input_type": "text", "placeholder": "e.g. Local server" }, { "type": "field", "label": "Hostname", "name": "host", "input_type": "text", "validate": "domainname", "placeholder": "e.g. server.home.local" }, { "type": "field", "label": "Resolves To", "name": "ip", "input_type": "text", "validate": "ip", "placeholder": "e.g. 192.168.1.100" }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/add_host_override", "method": "post", "text": "Add Host Override" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] } ] }, { "id": "view_dns_blocking", "client_requirement": "client_is_viewer+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "DNS Blocking" }, { "type": "p", "text": "Domain level blocking via dnsmasq." } ] }, { "type": "card", "label": "Logging", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/dnsblocking_cardlogging_save", "method": "post", "items": [ { "type": "field", "label": "Max Log Size (KB)", "name": "log_max_kb", "input_type": "number", "value": "%GENERAL_LOG_MAX_KB%", "min": 64, "hint": "Log is cleared and restarted when it exceeds this size." }, { "type": "field", "label": "Errors Only", "name": "log_errors_only", "input_type": "checkbox", "value": "%GENERAL_LOG_ERRORS_ONLY%", "hint": "Only write error-level messages to the log." }, { "type": "field", "label": "Log DNS Queries", "name": "dnsmasq_log_queries", "input_type": "checkbox", "value": "%GENERAL_DNSMASQ_LOG_QUERIES%", "hint": "Log every DNS query. High volume \u2014 enable for debugging only." }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/dnsblocking_cardlogging_save", "method": "post", "text": "Save" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] }, { "type": "table", "datasource": "config:blocklists", "empty_message": "No blocklists configured.", "columns": [ { "label": "Name", "field": "name" }, { "label": "Description", "field": "description" }, { "label": "Format", "field": "format", "class": "col-mono" }, { "label": "Source URL", "field": "url", "class": "col-mono" } ], "row_actions": [ { "client_requirement": "client_is_administrator+", "action": "/action/dnsblocking_tableblocklists_rowedit", "method": "inline_edit", "text": "Edit", "class": "btn-ghost btn-sm", "fields": [ { "col": "name", "input_type": "text", "validate": "dashname" }, { "col": "description", "input_type": "text" }, { "col": "format", "input_type": "select", "options": "%BLOCKLIST_FORMAT_OPTIONS%" }, { "col": "url", "input_type": "text", "validate": "url" } ] }, { "client_requirement": "client_is_administrator+", "action": "/action/dnsblocking_tableblocklists_rowdelete", "method": "post", "text": "Delete", "class": "btn-danger btn-sm" } ] }, { "type": "card", "id": "add-form", "label": "Add Blocklist", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/dnsblocking_cardaddblocklist_add", "method": "post", "items": [ { "type": "field", "label": "Name", "name": "name", "input_type": "text", "validate": "dashname", "placeholder": "e.g. steven-black" }, { "type": "field", "label": "Description", "name": "description", "input_type": "text", "placeholder": "e.g. Steven Black (ads, malware, trackers)" }, { "type": "field", "label": "Format", "name": "format", "input_type": "select", "options": "%BLOCKLIST_FORMAT_OPTIONS%" }, { "type": "field", "label": "Source URL", "name": "url", "input_type": "text", "validate": "url", "placeholder": "https://..." }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/dnsblocking_cardaddblocklist_add", "method": "post", "text": "Add Blocklist" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] }, { "type": "card", "label": "Blocklist Refresh", "client_requirement": "client_is_administrator+", "items": [ { "type": "raw_html", "html": "%BLOCKLIST_STATS_HTML%" }, { "type": "raw_html", "html": "
" }, { "type": "button_row", "items": [ { "type": "button_secondary", "action": "/action/dnsblocking_cardblocklistrefresh_refreshnow", "method": "post", "text": "Refresh All Now" } ] }, { "type": "raw_html", "html": "
" }, { "type": "form", "action": "/action/dnsblocking_cardblocklistrefresh_save", "method": "post", "items": [ { "type": "field", "label": "Daily Refresh Time", "name": "daily_execute_time_24hr_local", "input_type": "text", "validate": "time_24h", "value": "%GENERAL_DAILY_EXECUTE_TIME%", "placeholder": "e.g. 02:30", "hint": "24-hour local time for the daily blocklist refresh." }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/dnsblocking_cardblocklistrefresh_save", "method": "post", "text": "Save" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] } ] }, { "id": "view_vlans", "client_requirement": "client_is_viewer+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "VLANs" }, { "type": "p", "text": "Network segments managed by systemd-networkd, dnsmasq, nftables, and freeradius." } ] }, { "type": "info_bar", "variant": "info", "text": "For a basic flat network with no VLAN segmentation, only use VLAN 1 and delete the others." }, { "type": "table", "datasource": "config:vlans", "empty_message": "No VLANs configured.", "columns": [ { "label": "VLAN ID", "field": "vlan_id", "class": "col-mono col-narrow" }, { "label": "Name", "field": "name", "class": "col-narrow" }, { "label": "Interface", "field": "interface", "class": "col-mono col-narrow" }, { "label": "Subnet", "field": "subnet", "class": "col-mono col-narrow" }, { "label": "Mask", "field": "subnet_mask", "class": "col-mono col-narrow" }, { "label": "Blocklists", "field": "use_blocklists", "class": "col-expand", "render": "tag_list" }, { "label": "RADIUS Default", "field": "radius_default", "class": "col-narrow", "render": "badge_enabled_disabled" }, { "label": "mDNS Reflection", "field": "mdns_reflection", "class": "col-narrow", "render": "badge_enabled_disabled" } ], "row_actions": [ { "client_requirement": "client_is_administrator+", "action": "/action/edit_vlan", "method": "inline_edit", "text": "Edit", "class": "btn-ghost btn-sm", "fields": [ { "col": "name", "input_type": "text", "validate": "dashname" }, { "col": "subnet", "input_type": "text" }, { "col": "subnet_mask", "input_type": "number", "min": 1, "max": 30 }, { "col": "radius_default", "input_type": "checkbox" }, { "col": "mdns_reflection", "input_type": "checkbox" }, { "col": "use_blocklists", "input_type": "checkbox_multi", "options": "%BLOCKLIST_NAME_OPTIONS%" } ] }, { "client_requirement": "client_is_administrator+", "action": "/action/delete_vlan", "method": "post", "text": "Delete", "class": "btn-danger btn-sm", "disable_if": { "field": "vlan_id", "value": 1 } } ] }, { "type": "card", "id": "add-form", "label": "Add VLAN", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/add_vlan", "method": "post", "items": [ { "type": "field_row", "cols": 2, "items": [ { "type": "field", "label": "VLAN Name", "name": "name", "input_type": "text", "validate": "dashname", "hint": "Lowercase letters, digits, hyphens. E.g. iot" }, { "type": "subnet_row", "subnet_name": "subnet", "prefix_name": "subnet_mask", "subnet_placeholder": "e.g. 192.168.x.0", "prefix_value": "24" } ] }, { "type": "field_row", "cols": 3, "items": [ { "type": "field", "label": "Interface", "name": "", "input_type": "text", "readonly": true, "class": "vlan-iface-preview form-input-mono", "value": "" }, { "type": "field", "label": "VLAN ID", "name": "", "input_type": "text", "readonly": true, "class": "vlan-derived-id-preview form-input-mono", "value": "" }, { "type": "field", "label": "VLAN Type", "name": "is_vpn", "input_type": "checkbox", "checkbox_label": "Is VPN", "hint": "Check if this VLAN uses a WireGuard interface (e.g. wg0, wg1, etc)." } ] }, { "type": "divider" }, { "type": "field", "label": "Blocklists", "name": "use_blocklists", "input_type": "checkbox_group", "options": "%BLOCKLIST_NAME_OPTIONS%", "hint": "Note: Selected lists will be merged and de-duplicated prior to use." }, { "type": "divider" }, { "type": "field", "label": "RADIUS Default", "name": "radius_default", "input_type": "checkbox", "hint": "Wireless devices without a DHCP reservation will be placed into this VLAN. (Note: wired devices are not placed via RADIUS but rather by layer 3 switch policy.)" }, { "type": "field", "label": "mDNS Reflection", "name": "mdns_reflection", "input_type": "checkbox", "hint": "Reflect mDNS traffic to/from this VLAN via avahi-daemon. Not supported on WireGuard interfaces." }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/add_vlan", "method": "post", "text": "Add VLAN", "class": "add-vlan-btn", "disabled": true }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] } ] }, { "id": "view_inter_vlan", "client_requirement": "client_is_viewer+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "Inter-VLAN Exceptions" }, { "type": "p", "text": "Firewall rules that permit specific traffic to cross VLAN boundaries." } ] }, { "type": "table", "datasource": "config:inter_vlan_exceptions", "empty_message": "No inter-VLAN exceptions configured. All cross-VLAN traffic is blocked by default.", "columns": [ { "label": "Description", "field": "description" }, { "label": "Protocol", "field": "protocol", "class": "col-mono" }, { "label": "Source", "field": "src_ip_or_subnet", "class": "col-mono" }, { "label": "Destination", "field": "dst_ip_or_subnet", "class": "col-mono" }, { "label": "Dest Port", "field": "dst_port", "class": "col-mono" }, { "label": "Status", "field": "enabled", "render": "badge_enabled_disabled" } ], "row_actions": [ { "client_requirement": "client_is_administrator+", "action": "/action/edit_inter_vlan", "method": "inline_edit", "text": "Edit", "class": "btn-ghost btn-sm", "fields": [ { "col": "description", "input_type": "text" }, { "col": "protocol", "input_type": "select", "options": "%PROTOCOL_OPTIONS%" }, { "col": "src_ip_or_subnet", "input_type": "text" }, { "col": "dst_ip_or_subnet", "input_type": "text" }, { "col": "dst_port", "input_type": "text" }, { "col": "enabled", "input_type": "checkbox" } ] }, { "client_requirement": "client_is_administrator+", "action": "/action/delete_inter_vlan", "method": "post", "text": "Delete", "class": "btn-danger btn-sm" } ] }, { "type": "card", "id": "add-form", "label": "Add Exception", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/add_inter_vlan", "method": "post", "items": [ { "type": "field", "label": "Description", "name": "description", "input_type": "text", "placeholder": "e.g. Allow Chromecast" }, { "type": "field", "label": "Protocol", "name": "protocol", "input_type": "select", "options": "%PROTOCOL_OPTIONS%" }, { "type": "field", "label": "Source", "name": "src_ip_or_subnet", "input_type": "text", "validate": "ipv4cidr", "placeholder": "e.g. 192.168.20.0/24" }, { "type": "field", "label": "Destination", "name": "dst_ip_or_subnet", "input_type": "text", "validate": "ipv4", "placeholder": "e.g. 192.168.10.100" }, { "type": "field", "label": "Dest Port", "name": "dst_port", "input_type": "text", "validate": "port", "placeholder": "e.g. 8009" }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/add_inter_vlan", "method": "post", "text": "Add Exception" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] } ] }, { "id": "view_port_forwarding", "client_requirement": "client_is_viewer+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "Port Forwarding" }, { "type": "p", "text": "DNAT rules that forward inbound WAN traffic to internal hosts." } ] }, { "type": "table", "datasource": "config:port_forwarding", "empty_message": "No port forwarding rules configured.", "columns": [ { "label": "Description", "field": "description" }, { "label": "Protocol", "field": "protocol", "class": "col-mono" }, { "label": "Ext Port", "field": "dest_port", "class": "col-mono" }, { "label": "NAT IP", "field": "nat_ip", "class": "col-mono" }, { "label": "NAT Port", "field": "nat_port", "class": "col-mono" }, { "label": "Status", "field": "enabled", "render": "badge_enabled_disabled" } ], "row_actions": [ { "client_requirement": "client_is_administrator+", "action": "/action/edit_port_forward", "method": "inline_edit", "text": "Edit", "class": "btn-ghost btn-sm", "fields": [ { "col": "description", "input_type": "text" }, { "col": "protocol", "input_type": "select", "options": "%PROTOCOL_OPTIONS%" }, { "col": "dest_port", "input_type": "text" }, { "col": "nat_ip", "input_type": "text" }, { "col": "nat_port", "input_type": "text" }, { "col": "enabled", "input_type": "checkbox" } ] }, { "client_requirement": "client_is_administrator+", "action": "/action/delete_port_forward", "method": "post", "text": "Delete", "class": "btn-danger btn-sm" } ] }, { "type": "card", "id": "add-form", "label": "Add Rule", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/add_port_forward", "method": "post", "items": [ { "type": "field", "label": "Description", "name": "description", "input_type": "text", "placeholder": "e.g. Minecraft server" }, { "type": "field", "label": "Protocol", "name": "protocol", "input_type": "select", "options": "%PROTOCOL_OPTIONS%" }, { "type": "field", "label": "Ext Port", "name": "dest_port", "input_type": "text", "validate": "port", "placeholder": "e.g. 25565" }, { "type": "field", "label": "NAT IP", "name": "nat_ip", "input_type": "text", "validate": "ipv4", "placeholder": "e.g. 192.168.1.50" }, { "type": "field", "label": "NAT Port", "name": "nat_port", "input_type": "text", "validate": "port", "placeholder": "e.g. 25565" }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/add_port_forward", "method": "post", "text": "Add Rule" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] } ] }, { "id": "view_dhcp", "client_requirement": "client_is_viewer+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "DHCP" }, { "type": "p", "text": "Active leases and static reservations across all VLANs." } ] }, { "type": "table", "datasource": "live:dhcp_leases", "empty_message": "No active DHCP leases found.", "columns": [ { "label": "Hostname", "field": "hostname" }, { "label": "IP Address", "field": "ip_address", "class": "col-mono" }, { "label": "MAC Address", "field": "mac_address", "class": "col-mono" }, { "label": "VLAN", "field": "vlan_name" }, { "label": "Expires", "field": "expires" } ] }, { "type": "table", "datasource": "config:dhcp_reservations", "empty_message": "No DHCP reservations configured.", "columns": [ { "label": "Description", "field": "description" }, { "label": "Hostname", "field": "hostname", "class": "col-mono" }, { "label": "MAC", "field": "mac", "class": "col-mono" }, { "label": "IP", "field": "ip", "class": "col-mono" }, { "label": "VLAN", "field": "vlan_name" }, { "label": "RADIUS", "field": "radius_client", "render": "badge_enabled_disabled" }, { "label": "Status", "field": "enabled", "render": "badge_enabled_disabled" } ], "toolbar": { "items": [ { "type": "select", "name": "vlan_filter", "value": "all", "options": "%VLAN_FILTER_OPTIONS%", "filter_col": "vlan_name" } ] }, "row_actions": [ { "client_requirement": "client_is_administrator+", "action": "/action/edit_dhcp_reservation", "method": "inline_edit", "text": "Edit", "class": "btn-ghost btn-sm", "fields": [ { "col": "description", "input_type": "text" }, { "col": "hostname", "input_type": "text", "validate": "networkname" }, { "col": "mac", "input_type": "text", "validate": "mac" }, { "col": "ip", "input_type": "text", "validate": "ipv4" }, { "col": "radius_client", "input_type": "checkbox" }, { "col": "enabled", "input_type": "checkbox" } ] }, { "client_requirement": "client_is_administrator+", "action": "/action/delete_dhcp_reservation", "method": "post", "text": "Delete", "class": "btn-danger btn-sm" } ] }, { "type": "card", "id": "add-form", "label": "Add Reservation", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/add_dhcp_reservation", "method": "post", "items": [ { "type": "field", "label": "VLAN", "name": "vlan_name", "input_type": "select", "options": "%VLAN_NAMES_AS_OPTIONS%", "hint": "VLAN this reservation belongs to." }, { "type": "field", "label": "Description", "name": "description", "input_type": "text", "placeholder": "e.g. NAS" }, { "type": "field", "label": "Hostname", "name": "hostname", "input_type": "text", "validate": "networkname", "placeholder": "e.g. nas" }, { "type": "field", "label": "MAC Address", "name": "mac", "input_type": "text", "validate": "mac", "placeholder": "e.g. aa:bb:cc:dd:ee:ff" }, { "type": "field", "label": "IP Address", "name": "ip", "input_type": "text", "validate": "ipv4", "placeholder": "e.g. 192.168.10.50" }, { "type": "field", "label": "RADIUS Client", "name": "radius_client", "input_type": "checkbox", "hint": "Authenticate this device via RADIUS." }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/add_dhcp_reservation", "method": "post", "text": "Add Reservation" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] } ] }, { "id": "view_vpn", "client_requirement": "client_is_viewer+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "VPN" }, { "type": "p", "text": "WireGuard peer management and server interface configuration." } ] }, { "type": "table", "label": "Active Sessions", "datasource": "live:vpn_sessions", "empty_message": "No active VPN sessions.", "columns": [ { "label": "Peer", "field": "peer_name" }, { "label": "Tunnel IP", "field": "tunnel_ip", "class": "col-mono" }, { "label": "Endpoint", "field": "endpoint", "class": "col-mono" }, { "label": "Last Handshake", "field": "last_handshake" }, { "label": "Received", "field": "rx_bytes", "class": "col-mono" }, { "label": "Sent", "field": "tx_bytes", "class": "col-mono" } ] }, { "type": "table", "label": "Peers", "datasource": "config:vpn_peers", "empty_message": "No peers configured. Use Add Peer below.", "columns": [ { "label": "Name", "field": "name" }, { "label": "Assigned VLAN", "field": "vlan_display", "class": "col-mono" }, { "label": "Assigned IP", "field": "ip", "class": "col-mono" }, { "label": "Split Tunnel", "field": "split_tunnel" }, { "label": "Enabled", "field": "enabled", "render": "badge_enabled_disabled" }, { "label": "Public Key", "field": "pubkey_short", "class": "col-mono" } ], "row_actions": [ { "client_requirement": "client_is_administrator+", "action": "/action/edit_vpn_peer", "method": "inline_edit", "text": "Edit", "class": "btn-ghost btn-sm", "fields": [ { "col": "name", "input_type": "text", "validate": "dashname" }, { "col": "split_tunnel", "input_type": "checkbox" }, { "col": "enabled", "input_type": "checkbox" } ] }, { "client_requirement": "client_is_administrator+", "action": "/action/regenerate_vpn_peer", "method": "post", "text": "Regen Conf", "class": "btn-ghost btn-sm" }, { "client_requirement": "client_is_administrator+", "action": "/action/delete_vpn_peer", "method": "post", "text": "Delete", "class": "btn-danger btn-sm" } ] }, { "type": "card", "label": "Add Peer", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/add_vpn_peer", "method": "post", "items": [ { "type": "field", "label": "Name", "name": "peer_name", "input_type": "text", "validate": "dashname", "placeholder": "e.g. laptop", "hint": "Friendly name for this peer." }, { "type": "field", "label": "Assigned VLAN", "name": "peer_vlan", "input_type": "select", "options": "%VPN_VLAN_OPTIONS%" }, { "type": "field", "label": "Assigned IP", "name": "peer_ip", "input_type": "text", "validate": "ipv4", "placeholder": "e.g. 192.168.40.2", "hint": "Static IP assigned to this peer within the VPN subnet." }, { "type": "field", "label": "Split Tunnel", "name": "split_tunnel", "input_type": "checkbox", "hint": "Route only VPN subnet traffic through the tunnel. When unchecked all traffic is routed through the VPN." }, { "type": "field", "label": "Enabled", "name": "enabled", "input_type": "checkbox", "checked": true }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/add_vpn_peer", "method": "post", "text": "Add Peer & Download Conf" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] }, { "type": "card", "label": "WireGuard Interface", "client_requirement": "client_is_administrator+", "items": [ { "type": "form", "action": "/action/apply_vpn", "method": "post", "items": [ { "type": "field", "label": "Listen Port", "name": "vpn_listen_port", "input_type": "number", "value": "%VPN_LISTEN_PORT%", "min": 1024, "max": 65535, "hint": "UDP port WireGuard listens on. Must match your port forwarding rule." }, { "type": "field", "label": "Server Endpoint", "name": "vpn_server_endpoint", "input_type": "text", "validate": "endpoint", "value": "%VPN_SERVER_ENDPOINT%", "placeholder": "e.g. vpn.example.com", "hint": "Publicly reachable hostname or IP of this server, embedded in client config files." }, { "type": "field", "label": "Domain", "name": "vpn_domain", "input_type": "text", "validate": "dashname", "value": "%VPN_DOMAIN%", "placeholder": "e.g. local", "hint": "DNS search domain pushed to VPN clients." }, { "type": "field", "label": "DNS Override", "name": "vpn_dns_server", "input_type": "text", "validate": "ipv4", "value": "%VPN_DNS_SERVER%", "placeholder": "Leave blank to use gateway IP (%VPN_GATEWAY%)", "hint": "Explicit DNS server pushed to peers. Defaults to the gateway IP." }, { "type": "field", "label": "MTU Override", "name": "vpn_mtu", "input_type": "number", "value": "%VPN_MTU%", "placeholder": "Leave blank for default", "hint": "Override tunnel MTU. Leave blank for the system default." }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/apply_vpn", "method": "post", "text": "Save" }, { "type": "button_cancel", "text": "Cancel" } ] } ] } ] } ] }, { "id": "view_log_in", "client_requirement": "client_is_nothing=", "items": [ { "type": "auth_wrapper", "client_requirement": "client_is_nothing=", "items": [ { "type": "auth_card", "items": [ { "type": "h1", "text": "Log In" }, { "type": "p", "text": "Enter your credentials to access the dashboard." }, { "type": "divider" }, { "type": "form", "action": "/action/log_in", "method": "post", "items": [ { "type": "field", "label": "Email Address", "name": "email", "input_type": "text", "placeholder": "you@example.com" }, { "type": "field", "label": "Password", "name": "password", "input_type": "password", "placeholder": "Password" }, { "type": "button_primary", "action": "/action/log_in", "method": "post", "text": "Log In", "class": "btn-full" } ] }, { "type": "p", "text": "Need to complete your account?", "link": { "action": "/view/view_create_account", "text": "Create Account" } } ] } ] }, { "type": "section", "client_requirement": "client_is_viewer+", "items": [ { "type": "h1", "text": "Already logged in." }, { "type": "p", "text": "You are already authenticated." }, { "type": "spacer" }, { "type": "button_primary", "action": "/view/overview", "text": "Go to Overview" } ] } ] }, { "id": "view_create_account", "client_requirement": "client_is_nothing=", "items": [ { "type": "auth_wrapper", "client_requirement": "client_is_nothing=", "items": [ { "type": "auth_card", "items": [ { "type": "h1", "text": "Complete Your Account" }, { "type": "p", "text": "If your email has been pre-registered by a manager, setup your account below." }, { "type": "divider" }, { "type": "form", "action": "/action/create_account", "method": "post", "items": [ { "type": "field", "label": "Email Address", "name": "email", "input_type": "text", "placeholder": "you@example.com", "hint": "Must match your pre-registered email address." }, { "type": "field", "label": "New Password", "name": "password", "input_type": "password", "placeholder": "Choose a strong password" }, { "type": "field", "label": "Confirm Password", "name": "password_confirm", "input_type": "password", "placeholder": "Repeat your password" }, { "type": "field", "label": "Timezone", "name": "timezone", "input_type": "select", "value": "", "options": "%TIMEZONE_OPTIONS%", "hint": "Used to display timestamps in your local time." }, { "type": "button_primary", "action": "/action/create_account", "method": "post", "text": "Create Account", "class": "btn-full" } ] }, { "type": "p", "text": "Already have an account?", "link": { "action": "/view/view_log_in", "text": "Log In" } } ] } ] }, { "type": "section", "client_requirement": "client_is_viewer+", "items": [ { "type": "h1", "text": "Already logged in." }, { "type": "p", "text": "Your account is already active." }, { "type": "spacer" }, { "type": "button_primary", "action": "/view/overview", "text": "Go to Overview" } ] } ] }, { "id": "view_verify_email", "client_requirement": "client_is_nothing=", "items": [ { "type": "auth_wrapper", "client_requirement": "client_is_nothing=", "items": [ { "type": "auth_card", "items": [ { "type": "h1", "text": "Verify Your Email" }, { "type": "p", "text": "A 6-digit code was sent to your email address. Enter it below to complete your account." }, { "type": "form", "action": "/action/verify_email", "method": "post", "items": [ { "type": "field", "label": "Verification Code", "name": "code", "input_type": "text", "placeholder": "000000", "hint": "The code expires in 15 minutes." }, { "type": "button_primary", "action": "/action/verify_email", "method": "post", "text": "Verify", "class": "btn-full" } ] }, { "type": "p", "text": "Didn't receive it?", "link": { "action": "/action/resend_verification", "text": "Resend code" } }, { "type": "p", "text": "Wrong email?", "link": { "action": "/view/view_create_account", "text": "Start over" } } ] } ] }, { "type": "section", "client_requirement": "client_is_viewer+", "items": [ { "type": "h1", "text": "Already logged in." }, { "type": "p", "text": "Your account is already active." }, { "type": "spacer" }, { "type": "button_primary", "action": "/view/view_overview", "text": "Go to Overview" } ] } ] }, { "id": "view_preferences", "client_requirement": "client_is_viewer+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "Preferences" }, { "type": "p", "text": "Your personal account settings." } ] }, { "type": "card", "label": "Account Details", "items": [ { "type": "form", "action": "/action/save_preferences", "method": "post", "items": [ { "type": "field", "label": "Email Address", "name": "email", "input_type": "text", "value": "%PREF_EMAIL%", "hint": "Contact your manager to change your email address." }, { "type": "field", "label": "Timezone", "name": "timezone", "input_type": "select", "value": "%PREF_TIMEZONE%", "options": "%TIMEZONE_OPTIONS%", "hint": "All timestamps will be displayed in this timezone." }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/save_preferences", "method": "post", "text": "Save Preferences" } ] } ] } ] }, { "type": "card", "label": "Change Password", "items": [ { "type": "form", "action": "/action/change_password", "method": "post", "items": [ { "type": "field", "label": "Current Password", "name": "current_password", "input_type": "password", "placeholder": "Current password" }, { "type": "field", "label": "New Password", "name": "new_password", "input_type": "password", "placeholder": "New password" }, { "type": "field", "label": "Confirm Password", "name": "confirm_password", "input_type": "password", "placeholder": "Repeat new password" }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/change_password", "method": "post", "text": "Change Password" } ] } ] } ] } ] }, { "id": "view_manage_accounts", "client_requirement": "client_is_manager+", "items": [ { "type": "page_header", "items": [ { "type": "h1", "text": "Manage Accounts" } ] }, { "type": "table", "datasource": "config:accounts", "empty_message": "No accounts configured.", "columns": [ { "label": "Email Address", "field": "email_address" }, { "label": "Access Level", "field": "access_level" }, { "label": "Added By", "field": "account_created_by" }, { "label": "Added", "field": "account_created_utc" }, { "label": "Status", "field": "account_status", "render": "badge_active_inactive" } ], "row_actions": [ { "action": "/action/delete_account", "method": "post", "text": "Remove", "class": "btn-danger btn-sm" } ] }, { "type": "card", "label": "Authorize New Account", "items": [ { "type": "form", "action": "/action/add_account", "method": "post", "items": [ { "type": "field", "label": "Email Address", "name": "email_address", "input_type": "text", "placeholder": "user@example.com", "hint": "The user will verify ownership of this address during account setup." }, { "type": "field", "label": "Access Level", "name": "access_level", "input_type": "select", "options": "%ACCOUNT_LEVEL_OPTIONS%" }, { "type": "button_row", "items": [ { "type": "button_primary", "action": "/action/add_account", "method": "post", "text": "Authorize" } ] } ] } ] } ] } ] }