admin/internet: nicer while loading

Massimo Melina committed May 11, 2026 at 23:43 UTC 6b5a3472013873f0f1bca2c9b92387a351060483
1 file changed +9 -8
admin/src/InternetPage.ts
+9 -8
@@ -1,5 +1,7 @@
1 import { createElement as h, ReactNode, useEffect, useMemo, useRef, useState } from 'react'
2 -import { Alert, Box, Button, Card, CardContent, CircularProgress, Divider, LinearProgress, Link, Typography } from '@mui/material'
2 +import {
3 + Alert, Box, Button, Card, CardContent, CircularProgress, Divider, LinearProgress, Link, Typography, Skeleton,
4 +} from '@mui/material'
5 import { CardMembership, Check, Dns, HomeWorkTwoTone, Lock, Public, PublicTwoTone, RouterTwoTone, Send, Storage,
6 Error as ErrorIcon, SvgIconComponent, Search } from '@mui/icons-material'
7 import { apiCall, useApiEvents, useApiEx } from './api'
@@ -311,8 +313,7 @@ export default function InternetPage({ setTitleSide }: PageProps) {
313
314 function networkBox() {
315 if (nat.error) return nat.element
314 - if (!data || !publicIps) return h(CircularProgress)
315 - const direct = publicIps.includes(data?.localIp!)
316 + const direct = publicIps?.includes(data?.localIp!)
317 return h(Flex, { justifyContent: 'space-around' },
318 h(Device, { name: "Server", icon: direct ? Storage : HomeWorkTwoTone, color: localColor, ip: data?.localIp,
319 below: port && h(Box, { sx: { fontSize: 'smaller' }, className: 'port ' + HIDE_IN_TESTS }, "port ", port),
@@ -322,17 +323,17 @@ export default function InternetPage({ setTitleSide }: PageProps) {
323 name: "Router", icon: RouterTwoTone, ip: data?.gatewayIp,
324 color: checkResult ? 'success' : data?.mapped && (wrongMap ? 'warning' : 'success'),
325 below: mapping ? h(LinearProgress, { sx: { height: '1em' } })
325 - : h(LinkBtn, { sx: { fontSize: 'smaller', display: 'block' }, onClick: configure },
326 + : data && h(LinkBtn, { sx: { fontSize: 'smaller', display: 'block' }, onClick: configure },
327 "port ", wrongMap ? "is wrong" : data?.externalPort || (checkResult ? "verified" : "unknown")),
328 }),
329 h(DataLine),
330 h(Device, { name: "Internet", icon: PublicTwoTone, ip: publicIps,
331 color: checkResult ? 'success' : checkResult === false ? 'error' : doubleNat ? 'warning' : undefined,
331 - below: checking ? h(LinearProgress, { sx: { height: '1em' } }) : h(Box, { sx: { fontSize: 'smaller' }, className: HIDE_IN_TESTS },
332 + below: checking ? h(LinearProgress, { sx: { height: '1em' } }) : publicIps && h(Box, { sx: { fontSize: 'smaller' }, className: HIDE_IN_TESTS },
333 doubleNat && h(LinkBtn, { sx: { display: 'block', fontSize: 'smaller' }, onClick: () => alertDialog(MSG_ISP, 'warning') }, "Double NAT"),
334 checkResult ? "Working!" : checkResult === false ? "Failed!" : '',
335 ' ',
335 - (baseUrl > '' || publicIps.length > 0) && data.internalPort && h(LinkBtn, { onClick: () => verify() }, "Verify")
336 + (baseUrl > '' || publicIps?.length > 0) && data?.internalPort && h(LinkBtn, { onClick: () => verify() }, "Verify")
337 || ' ' // steadier layout, mainly for testing
338 )
339 }),
@@ -474,8 +475,8 @@ function Device({ name, icon, color, ip, below }: any) {
475 return h(Box, { sx: { display: 'inline-block', textAlign: 'center' } },
476 h(icon, { color, sx: { fontSize, mb: '-0.1em' } }),
477 h(Box, { sx: { fontSize: 'larger' } }, name),
477 - h(Box, { sx: { fontSize: 'smaller', whiteSpace: 'pre-wrap' }, className: 'ip ' + HIDE_IN_TESTS }, wantArray(ip).join('\n') || "unknown"),
478 - below,
478 + ip === undefined ? h(Skeleton) : h(Box, { sx: { fontSize: 'smaller', whiteSpace: 'pre-wrap' }, className: 'ip ' + HIDE_IN_TESTS }, wantArray(ip).join('\n') || "unknown"),
479 + below ?? h(Skeleton),
480 )
481 }
482