fix(striker-ui): render async server screenshots

main
Tsu-ba-me 3 years ago
parent 4c4ce1834b
commit e06281bce0
  1. 27
      striker-ui/components/Display/Preview.tsx
  2. 71
      striker-ui/pages/index.tsx

@ -5,6 +5,7 @@ import {
PowerOffOutlined as PowerOffOutlinedIcon,
} from '@mui/icons-material';
import API_BASE_URL from '../../lib/consts/API_BASE_URL';
import { BORDER_RADIUS, GREY } from '../../lib/consts/DEFAULT_THEME';
import IconButton from '../IconButton';
@ -12,6 +13,8 @@ import { InnerPanel, InnerPanelHeader, Panel, PanelHeader } from '../Panels';
import { BodyText, HeaderText } from '../Text';
type PreviewOptionalProps = {
externalPreview?: string;
isFetchScreenshot?: boolean;
isShowControls?: boolean;
isUseInnerPanel?: boolean;
setMode?: Dispatch<SetStateAction<boolean>> | null;
@ -23,6 +26,8 @@ type PreviewProps = PreviewOptionalProps & {
};
const PREVIEW_DEFAULT_PROPS: Required<PreviewOptionalProps> = {
externalPreview: '',
isFetchScreenshot: true,
isShowControls: true,
isUseInnerPanel: false,
setMode: null,
@ -56,33 +61,37 @@ const PreviewPanelHeader: FC<{ isUseInnerPanel: boolean; text: string }> = ({
);
const Preview: FC<PreviewProps> = ({
externalPreview = PREVIEW_DEFAULT_PROPS.externalPreview,
isFetchScreenshot = PREVIEW_DEFAULT_PROPS.isFetchScreenshot,
isShowControls = PREVIEW_DEFAULT_PROPS.isShowControls,
isUseInnerPanel = PREVIEW_DEFAULT_PROPS.isUseInnerPanel,
serverName,
setMode,
uuid,
}) => {
const [preview, setPreview] = useState<string>();
const [preview, setPreview] = useState<string>('');
useEffect(() => {
if (isFetchScreenshot) {
(async () => {
try {
const res = await fetch(
`${process.env.NEXT_PUBLIC_API_URL}/get_server_screenshot?server_uuid=${uuid}`,
{
const response = await fetch(`${API_BASE_URL}/server/${uuid}?ss`, {
method: 'GET',
headers: {
'Content-Type': 'application/json',
},
},
);
const { screenshot } = await res.json();
setPreview(screenshot);
});
const { screenshot: fetchedScreenshot } = await response.json();
setPreview(fetchedScreenshot);
} catch {
setPreview('');
}
})();
}, [uuid]);
} else if (externalPreview) {
setPreview(externalPreview);
}
}, [externalPreview, isFetchScreenshot, uuid]);
return (
<PreviewPanel isUseInnerPanel={isUseInnerPanel}>

@ -11,8 +11,14 @@ import OutlinedInput from '../components/OutlinedInput';
import { Panel, PanelHeader } from '../components/Panels';
import periodicFetch from '../lib/fetchers/periodicFetch';
import Spinner from '../components/Spinner';
import fetchJSON from '../lib/fetchers/fetchJSON';
const createServerPreviewContainer = (servers: ServerOverviewMetadata[]) => (
type ServerListItem = ServerOverviewMetadata & {
isScreenshotStale?: boolean;
screenshot: string;
};
const createServerPreviewContainer = (servers: ServerListItem[]) => (
<Box
sx={{
display: 'flex',
@ -22,13 +28,19 @@ const createServerPreviewContainer = (servers: ServerOverviewMetadata[]) => (
'& > *': {
width: { xs: '20em', md: '30em' },
},
'& > :not(:last-child)': {
marginRight: '2em',
},
}}
>
{servers.map(({ serverName, serverUUID }) => (
{servers.map(({ screenshot, serverName, serverUUID }) => (
<Preview
key={`server-preview-${serverUUID}`}
isFetchScreenshot={false}
isShowControls={false}
isUseInnerPanel
externalPreview={screenshot}
serverName={serverName}
uuid={serverUUID}
/>
@ -36,18 +48,15 @@ const createServerPreviewContainer = (servers: ServerOverviewMetadata[]) => (
</Box>
);
const filterServers = (
allServers: ServerOverviewMetadata[],
searchTerm: string,
) =>
const filterServers = (allServers: ServerListItem[], searchTerm: string) =>
searchTerm === ''
? {
exclude: allServers,
include: [],
}
: allServers.reduce<{
exclude: ServerOverviewMetadata[];
include: ServerOverviewMetadata[];
exclude: ServerListItem[];
include: ServerListItem[];
}>(
(reduceContainer, server) => {
const { serverName } = server;
@ -64,13 +73,9 @@ const filterServers = (
);
const Dashboard: FC = () => {
const [allServers, setAllServers] = useState<ServerOverviewMetadata[]>([]);
const [excludeServers, setExcludeServers] = useState<
ServerOverviewMetadata[]
>([]);
const [includeServers, setIncludeServers] = useState<
ServerOverviewMetadata[]
>([]);
const [allServers, setAllServers] = useState<ServerListItem[]>([]);
const [excludeServers, setExcludeServers] = useState<ServerListItem[]>([]);
const [includeServers, setIncludeServers] = useState<ServerListItem[]>([]);
const [inputSearchTerm, setInputSearchTerm] = useState<string>('');
@ -83,13 +88,42 @@ const Dashboard: FC = () => {
setIncludeServers(include);
};
const { isLoading } = periodicFetch<ServerOverviewMetadata[]>(
const { isLoading } = periodicFetch<ServerListItem[]>(
`${API_BASE_URL}/server`,
{
onSuccess: (data = []) => {
setAllServers(data);
const serverListItems: ServerListItem[] = (
data as ServerOverviewMetadata[]
).map((serverOverview) => {
const { serverUUID } = serverOverview;
const previousScreenshot: string =
allServers.find(({ serverUUID: uuid }) => uuid === serverUUID)
?.screenshot || '';
const item: ServerListItem = {
...serverOverview,
screenshot: previousScreenshot,
};
updateServerList(data, inputSearchTerm);
fetchJSON<{ screenshot: string }>(
`${API_BASE_URL}/server/${serverUUID}?ss`,
)
.then(({ screenshot }) => {
item.screenshot = screenshot;
const allServersWithScreenshots = [...serverListItems];
setAllServers(allServersWithScreenshots);
updateServerList(allServersWithScreenshots, inputSearchTerm);
})
.catch(() => {
item.isScreenshotStale = true;
});
return item;
});
setAllServers(serverListItems);
updateServerList(serverListItems, inputSearchTerm);
},
refreshInterval: 60000,
},
@ -111,7 +145,6 @@ const Dashboard: FC = () => {
placeholder="Search by server name"
onChange={({ target: { value } }) => {
setInputSearchTerm(value);
updateServerList(allServers, value);
}}
value={inputSearchTerm}

Loading…
Cancel
Save