clean up unused js parts
This commit is contained in:
5
pkgs/ui/src/app/join/page.tsx
Normal file
5
pkgs/ui/src/app/join/page.tsx
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
import JoinPrequel from "@/views/joinPrequel";
|
||||||
|
|
||||||
|
export default function Page() {
|
||||||
|
return <JoinPrequel />;
|
||||||
|
}
|
||||||
@@ -11,7 +11,7 @@ import {
|
|||||||
useMediaQuery,
|
useMediaQuery,
|
||||||
useTheme,
|
useTheme,
|
||||||
} from "@mui/material";
|
} from "@mui/material";
|
||||||
import { ChangeEvent, useState } from "react";
|
import { useState } from "react";
|
||||||
import { Toaster } from "react-hot-toast";
|
import { Toaster } from "react-hot-toast";
|
||||||
import { StyledEngineProvider } from "@mui/material/styles";
|
import { StyledEngineProvider } from "@mui/material/styles";
|
||||||
|
|
||||||
@@ -25,10 +25,10 @@ import axios from "axios";
|
|||||||
import {
|
import {
|
||||||
AppContext,
|
AppContext,
|
||||||
WithAppState,
|
WithAppState,
|
||||||
useAppState,
|
// useAppState,
|
||||||
} from "@/components/hooks/useAppContext";
|
} from "@/components/hooks/useAppContext";
|
||||||
import Background from "@/components/background";
|
import Background from "@/components/background";
|
||||||
import { usePathname, redirect } from "next/navigation";
|
// import { usePathname, redirect } from "next/navigation";
|
||||||
|
|
||||||
const roboto = localFont({
|
const roboto = localFont({
|
||||||
src: [
|
src: [
|
||||||
@@ -45,16 +45,16 @@ axios.defaults.baseURL = "http://localhost:2979";
|
|||||||
// add negative margin for smooth transition to fill the space of the sidebar
|
// add negative margin for smooth transition to fill the space of the sidebar
|
||||||
const translate = tw`lg:-ml-64 -ml-14`;
|
const translate = tw`lg:-ml-64 -ml-14`;
|
||||||
|
|
||||||
const AutoRedirectEffect = () => {
|
// const AutoRedirectEffect = () => {
|
||||||
const { isLoading, data } = useAppState();
|
// const { isLoading, data } = useAppState();
|
||||||
const pathname = usePathname();
|
// const pathname = usePathname();
|
||||||
React.useEffect(() => {
|
// React.useEffect(() => {
|
||||||
if (!isLoading && !data.isJoined && pathname !== "/") {
|
// if (!isLoading && !data.isJoined && pathname !== "/") {
|
||||||
redirect("/");
|
// redirect("/");
|
||||||
}
|
// }
|
||||||
}, [isLoading, data, pathname]);
|
// }, [isLoading, data, pathname]);
|
||||||
return <></>;
|
// return <></>;
|
||||||
};
|
// };
|
||||||
|
|
||||||
export default function RootLayout({
|
export default function RootLayout({
|
||||||
children,
|
children,
|
||||||
@@ -84,9 +84,9 @@ export default function RootLayout({
|
|||||||
}
|
}
|
||||||
}, [userPrefersDarkmode, useDarkTheme, setUseDarkTheme]);
|
}, [userPrefersDarkmode, useDarkTheme, setUseDarkTheme]);
|
||||||
|
|
||||||
const changeThemeHandler = (target: ChangeEvent, currentValue: boolean) => {
|
// const changeThemeHandler = (target: ChangeEvent, currentValue: boolean) => {
|
||||||
setUseDarkTheme(currentValue);
|
// setUseDarkTheme(currentValue);
|
||||||
};
|
// };
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<html lang="en">
|
<html lang="en">
|
||||||
@@ -105,9 +105,7 @@ export default function RootLayout({
|
|||||||
<AppContext.Consumer>
|
<AppContext.Consumer>
|
||||||
{(appState) => {
|
{(appState) => {
|
||||||
const showSidebarDerived = Boolean(
|
const showSidebarDerived = Boolean(
|
||||||
showSidebar &&
|
showSidebar && !appState.isLoading && appState.data.isJoined
|
||||||
!appState.isLoading &&
|
|
||||||
appState.data.isJoined,
|
|
||||||
);
|
);
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
@@ -149,7 +147,7 @@ export default function RootLayout({
|
|||||||
<div className="px-1">
|
<div className="px-1">
|
||||||
<div className="relative flex h-full flex-1 flex-col">
|
<div className="relative flex h-full flex-1 flex-col">
|
||||||
<main>
|
<main>
|
||||||
<AutoRedirectEffect />
|
{/* <AutoRedirectEffect /> */}
|
||||||
<Button
|
<Button
|
||||||
fullWidth
|
fullWidth
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ import { QuickActions } from "@/components/dashboard/quickActions";
|
|||||||
import { TaskQueue } from "@/components/dashboard/taskQueue";
|
import { TaskQueue } from "@/components/dashboard/taskQueue";
|
||||||
import { useAppState } from "@/components/hooks/useAppContext";
|
import { useAppState } from "@/components/hooks/useAppContext";
|
||||||
import { MachineContextProvider } from "@/components/hooks/useMachines";
|
import { MachineContextProvider } from "@/components/hooks/useMachines";
|
||||||
|
import { LoadingOverlay } from "@/components/join/loadingOverlay";
|
||||||
import { tw } from "@/utils/tailwind";
|
import { tw } from "@/utils/tailwind";
|
||||||
import JoinPrequel from "@/views/joinPrequel";
|
import JoinPrequel from "@/views/joinPrequel";
|
||||||
|
|
||||||
@@ -37,7 +38,20 @@ const DashboardPanel = (props: DashboardPanelProps) => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
export default function Dashboard() {
|
export default function Dashboard() {
|
||||||
const { data } = useAppState();
|
const { data, isLoading } = useAppState();
|
||||||
|
if (isLoading) {
|
||||||
|
return (
|
||||||
|
<div className="grid h-full place-items-center">
|
||||||
|
<div className="mt-8 w-full max-w-xl">
|
||||||
|
<LoadingOverlay
|
||||||
|
title="Clan Experience"
|
||||||
|
subtitle="Loading"
|
||||||
|
variant="circle"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
if (!data.isJoined) {
|
if (!data.isJoined) {
|
||||||
return <JoinPrequel />;
|
return <JoinPrequel />;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,16 +7,12 @@ import {
|
|||||||
Edit,
|
Edit,
|
||||||
Group,
|
Group,
|
||||||
Key,
|
Key,
|
||||||
MenuOpen,
|
|
||||||
NetworkCell,
|
|
||||||
Settings,
|
Settings,
|
||||||
SettingsEthernet,
|
SettingsEthernet,
|
||||||
VisibilityOff,
|
|
||||||
} from "@mui/icons-material";
|
} from "@mui/icons-material";
|
||||||
import {
|
import {
|
||||||
Avatar,
|
Avatar,
|
||||||
Button,
|
Button,
|
||||||
Divider,
|
|
||||||
IconButton,
|
IconButton,
|
||||||
List,
|
List,
|
||||||
ListItem,
|
ListItem,
|
||||||
@@ -29,7 +25,7 @@ import {
|
|||||||
Typography,
|
Typography,
|
||||||
} from "@mui/material";
|
} from "@mui/material";
|
||||||
import { useState } from "react";
|
import { useState } from "react";
|
||||||
import { useListMachines } from "@/api/default/default";
|
// import { useListMachines } from "@/api/default/default";
|
||||||
|
|
||||||
export async function generateStaticParams() {
|
export async function generateStaticParams() {
|
||||||
return [{ id: "1" }, { id: "2" }];
|
return [{ id: "1" }, { id: "2" }];
|
||||||
@@ -46,7 +42,7 @@ interface TemplateDetailProps {
|
|||||||
params: { id: string };
|
params: { id: string };
|
||||||
}
|
}
|
||||||
export default function TemplateDetail({ params }: TemplateDetailProps) {
|
export default function TemplateDetail({ params }: TemplateDetailProps) {
|
||||||
const { data, isLoading } = useListMachines();
|
// const { data, isLoading } = useListMachines();
|
||||||
const details = getTemplate(params);
|
const details = getTemplate(params);
|
||||||
|
|
||||||
const [anchorEl, setAnchorEl] = useState<null | HTMLElement>(null);
|
const [anchorEl, setAnchorEl] = useState<null | HTMLElement>(null);
|
||||||
|
|||||||
@@ -2,7 +2,6 @@ import { ChevronRight } from "@mui/icons-material";
|
|||||||
import {
|
import {
|
||||||
Avatar,
|
Avatar,
|
||||||
Divider,
|
Divider,
|
||||||
IconButton,
|
|
||||||
List,
|
List,
|
||||||
ListItem,
|
ListItem,
|
||||||
ListItemAvatar,
|
ListItemAvatar,
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ import {
|
|||||||
Paper,
|
Paper,
|
||||||
Typography,
|
Typography,
|
||||||
} from "@mui/material";
|
} from "@mui/material";
|
||||||
import { IChangeEvent, FormProps } from "@rjsf/core";
|
import { IChangeEvent } from "@rjsf/core";
|
||||||
import { Form } from "@rjsf/mui";
|
import { Form } from "@rjsf/mui";
|
||||||
import validator from "@rjsf/validator-ajv8";
|
import validator from "@rjsf/validator-ajv8";
|
||||||
import toast from "react-hot-toast";
|
import toast from "react-hot-toast";
|
||||||
@@ -54,7 +54,7 @@ export function CustomConfig(props: FormStepContentProps) {
|
|||||||
}
|
}
|
||||||
return acc;
|
return acc;
|
||||||
}, {}),
|
}, {}),
|
||||||
[schema],
|
[schema]
|
||||||
);
|
);
|
||||||
|
|
||||||
return isLoading ? (
|
return isLoading ? (
|
||||||
@@ -100,7 +100,7 @@ function ErrorList<
|
|||||||
}
|
}
|
||||||
|
|
||||||
function PureCustomConfig(props: PureCustomConfigProps) {
|
function PureCustomConfig(props: PureCustomConfigProps) {
|
||||||
const { schema, initialValues, formHooks } = props;
|
const { schema, formHooks } = props;
|
||||||
const { setValue, watch } = formHooks;
|
const { setValue, watch } = formHooks;
|
||||||
|
|
||||||
console.log({ schema });
|
console.log({ schema });
|
||||||
@@ -124,7 +124,7 @@ function PureCustomConfig(props: PureCustomConfigProps) {
|
|||||||
message: "invalid config",
|
message: "invalid config",
|
||||||
});
|
});
|
||||||
toast.error(
|
toast.error(
|
||||||
"Configuration is invalid. Please check the highlighted fields for details.",
|
"Configuration is invalid. Please check the highlighted fields for details."
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
formHooks.clearErrors("config");
|
formHooks.clearErrors("config");
|
||||||
|
|||||||
@@ -5,19 +5,14 @@ import {
|
|||||||
Step,
|
Step,
|
||||||
StepLabel,
|
StepLabel,
|
||||||
Stepper,
|
Stepper,
|
||||||
Typography,
|
|
||||||
useMediaQuery,
|
useMediaQuery,
|
||||||
useTheme,
|
useTheme,
|
||||||
} from "@mui/material";
|
} from "@mui/material";
|
||||||
import React, { ReactNode, useState } from "react";
|
import React, { useState } from "react";
|
||||||
import { useForm, UseFormReturn } from "react-hook-form";
|
import { useForm } from "react-hook-form";
|
||||||
import { CustomConfig } from "./customConfig";
|
import { CustomConfig } from "./customConfig";
|
||||||
import { CreateMachineForm, FormStep } from "./interfaces";
|
import { CreateMachineForm, FormStep } from "./interfaces";
|
||||||
|
|
||||||
const SC = (props: { children: ReactNode }) => {
|
|
||||||
return <>{props.children}</>;
|
|
||||||
};
|
|
||||||
|
|
||||||
export function CreateMachineForm() {
|
export function CreateMachineForm() {
|
||||||
const formHooks = useForm<CreateMachineForm>({
|
const formHooks = useForm<CreateMachineForm>({
|
||||||
defaultValues: {
|
defaultValues: {
|
||||||
@@ -25,7 +20,7 @@ export function CreateMachineForm() {
|
|||||||
config: {},
|
config: {},
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
const { handleSubmit, control, watch, reset, formState } = formHooks;
|
const { handleSubmit, reset } = formHooks;
|
||||||
const theme = useTheme();
|
const theme = useTheme();
|
||||||
const isMobile = useMediaQuery(theme.breakpoints.down("sm"));
|
const isMobile = useMediaQuery(theme.breakpoints.down("sm"));
|
||||||
const [activeStep, setActiveStep] = useState<number>(0);
|
const [activeStep, setActiveStep] = useState<number>(0);
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import { ReactElement, ReactNode } from "react";
|
import { ReactElement } from "react";
|
||||||
import { UseFormReturn } from "react-hook-form";
|
import { UseFormReturn } from "react-hook-form";
|
||||||
|
|
||||||
export type StepId = "template" | "modules" | "config" | "save";
|
export type StepId = "template" | "modules" | "config" | "save";
|
||||||
|
|||||||
@@ -8,7 +8,6 @@ import {
|
|||||||
ListItem,
|
ListItem,
|
||||||
ListItemIcon,
|
ListItemIcon,
|
||||||
ListItemText,
|
ListItemText,
|
||||||
Typography,
|
|
||||||
} from "@mui/material";
|
} from "@mui/material";
|
||||||
import Link from "next/link";
|
import Link from "next/link";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
|||||||
@@ -1,7 +1,5 @@
|
|||||||
import { DashboardCard } from "@/components/card";
|
import { DashboardCard } from "@/components/card";
|
||||||
import Image from "next/image";
|
import Image from "next/image";
|
||||||
import { ReactNode } from "react";
|
|
||||||
|
|
||||||
interface AppCardProps {
|
interface AppCardProps {
|
||||||
name: string;
|
name: string;
|
||||||
icon?: string;
|
icon?: string;
|
||||||
@@ -32,11 +30,6 @@ const AppCard = (props: AppCardProps) => {
|
|||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
type App = {
|
|
||||||
name: string;
|
|
||||||
icon?: string;
|
|
||||||
};
|
|
||||||
|
|
||||||
const apps = [
|
const apps = [
|
||||||
{
|
{
|
||||||
name: "Firefox",
|
name: "Firefox",
|
||||||
|
|||||||
@@ -1,17 +1,12 @@
|
|||||||
import { DashboardCard } from "@/components/card";
|
import { DashboardCard } from "@/components/card";
|
||||||
import { notificationData } from "@/data/dashboardData";
|
import { notificationData } from "@/data/dashboardData";
|
||||||
import { tw } from "@/utils/tailwind";
|
|
||||||
import {
|
import {
|
||||||
Avatar,
|
Avatar,
|
||||||
Chip,
|
|
||||||
List,
|
List,
|
||||||
ListItem,
|
ListItem,
|
||||||
ListItemAvatar,
|
ListItemAvatar,
|
||||||
ListItemButton,
|
|
||||||
ListItemIcon,
|
|
||||||
ListItemText,
|
ListItemText,
|
||||||
} from "@mui/material";
|
} from "@mui/material";
|
||||||
import { Label } from "recharts";
|
|
||||||
|
|
||||||
import CheckIcon from "@mui/icons-material/Check";
|
import CheckIcon from "@mui/icons-material/Check";
|
||||||
import InfoIcon from "@mui/icons-material/Info";
|
import InfoIcon from "@mui/icons-material/Info";
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
"use client";
|
"use client";
|
||||||
import { DashboardCard } from "@/components/card";
|
import { DashboardCard } from "@/components/card";
|
||||||
import { Button, Fab } from "@mui/material";
|
import { Fab } from "@mui/material";
|
||||||
import { MouseEventHandler, ReactNode } from "react";
|
import { MouseEventHandler, ReactNode } from "react";
|
||||||
|
|
||||||
import LanIcon from "@mui/icons-material/Lan";
|
import LanIcon from "@mui/icons-material/Lan";
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ interface TaskEntryProps {
|
|||||||
details?: string;
|
details?: string;
|
||||||
}
|
}
|
||||||
const TaskEntry = (props: TaskEntryProps) => {
|
const TaskEntry = (props: TaskEntryProps) => {
|
||||||
const { result, task, details, status } = props;
|
const { result, task, status } = props;
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<div className="col-span-1">{status}</div>
|
<div className="col-span-1">{status}</div>
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
import { useListMachines } from "@/api/default/default";
|
import { useListMachines } from "@/api/default/default";
|
||||||
import { Machine, MachinesResponse } from "@/api/model";
|
import { MachinesResponse } from "@/api/model";
|
||||||
import { AxiosError, AxiosResponse } from "axios";
|
import { AxiosError, AxiosResponse } from "axios";
|
||||||
import React, {
|
import React, {
|
||||||
createContext,
|
createContext,
|
||||||
@@ -22,9 +22,9 @@ type AppContextType = {
|
|||||||
swrKey: string | false | Record<any, any>;
|
swrKey: string | false | Record<any, any>;
|
||||||
};
|
};
|
||||||
|
|
||||||
const initialState = {
|
// const initialState = {
|
||||||
isLoading: true,
|
// isLoading: true,
|
||||||
} as const;
|
// } as const;
|
||||||
|
|
||||||
export const AppContext = createContext<AppContextType>({} as AppContextType);
|
export const AppContext = createContext<AppContextType>({} as AppContextType);
|
||||||
|
|
||||||
@@ -38,7 +38,7 @@ interface AppContextProviderProps {
|
|||||||
}
|
}
|
||||||
export const WithAppState = (props: AppContextProviderProps) => {
|
export const WithAppState = (props: AppContextProviderProps) => {
|
||||||
const { children } = props;
|
const { children } = props;
|
||||||
const { data: rawData, isLoading, error, mutate, swrKey } = useListMachines();
|
const { isLoading, error, mutate, swrKey } = useListMachines();
|
||||||
|
|
||||||
const [data, setAppState] = useState<AppState>({ isJoined: false });
|
const [data, setAppState] = useState<AppState>({ isJoined: false });
|
||||||
|
|
||||||
|
|||||||
@@ -62,7 +62,7 @@ export const MachineContextProvider = (props: MachineContextProviderProps) => {
|
|||||||
if (!isLoading && !error && !isValidating && rawData) {
|
if (!isLoading && !error && !isValidating && rawData) {
|
||||||
const { machines } = rawData.data;
|
const { machines } = rawData.data;
|
||||||
return machines.filter((m) =>
|
return machines.filter((m) =>
|
||||||
filters.every((f) => m[f.name] === f.value),
|
filters.every((f) => m[f.name] === f.value)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
return [];
|
return [];
|
||||||
|
|||||||
@@ -10,11 +10,7 @@ import {
|
|||||||
} from "@mui/material";
|
} from "@mui/material";
|
||||||
import { Controller, SubmitHandler, UseFormReturn } from "react-hook-form";
|
import { Controller, SubmitHandler, UseFormReturn } from "react-hook-form";
|
||||||
import { FlakeBadge } from "../flakeBadge/flakeBadge";
|
import { FlakeBadge } from "../flakeBadge/flakeBadge";
|
||||||
import {
|
import { createVm, useInspectFlakeAttrs } from "@/api/default/default";
|
||||||
createVm,
|
|
||||||
useGetVmLogs,
|
|
||||||
useInspectFlakeAttrs,
|
|
||||||
} from "@/api/default/default";
|
|
||||||
import { VmConfig } from "@/api/model";
|
import { VmConfig } from "@/api/model";
|
||||||
import { Dispatch, SetStateAction, useEffect, useState } from "react";
|
import { Dispatch, SetStateAction, useEffect, useState } from "react";
|
||||||
import { toast } from "react-hot-toast";
|
import { toast } from "react-hot-toast";
|
||||||
|
|||||||
@@ -3,7 +3,7 @@ import { useState } from "react";
|
|||||||
import { LoadingOverlay } from "./loadingOverlay";
|
import { LoadingOverlay } from "./loadingOverlay";
|
||||||
import { FlakeBadge } from "../flakeBadge/flakeBadge";
|
import { FlakeBadge } from "../flakeBadge/flakeBadge";
|
||||||
import { Typography, Button } from "@mui/material";
|
import { Typography, Button } from "@mui/material";
|
||||||
import { FlakeResponse } from "@/api/model";
|
// import { FlakeResponse } from "@/api/model";
|
||||||
import { ConfirmVM } from "./confirmVM";
|
import { ConfirmVM } from "./confirmVM";
|
||||||
import { Log } from "./log";
|
import { Log } from "./log";
|
||||||
import GppMaybeIcon from "@mui/icons-material/GppMaybe";
|
import GppMaybeIcon from "@mui/icons-material/GppMaybe";
|
||||||
@@ -11,22 +11,29 @@ import { useInspectFlake } from "@/api/default/default";
|
|||||||
|
|
||||||
interface ConfirmProps {
|
interface ConfirmProps {
|
||||||
flakeUrl: string;
|
flakeUrl: string;
|
||||||
|
flakeAttr: string;
|
||||||
handleBack: () => void;
|
handleBack: () => void;
|
||||||
}
|
}
|
||||||
export const Confirm = (props: ConfirmProps) => {
|
export const Confirm = (props: ConfirmProps) => {
|
||||||
const { flakeUrl, handleBack } = props;
|
const { flakeUrl, handleBack, flakeAttr } = props;
|
||||||
const [userConfirmed, setUserConfirmed] = useState(false);
|
const [userConfirmed, setUserConfirmed] = useState(false);
|
||||||
|
|
||||||
const { data, error, isLoading } = useInspectFlake({ url: flakeUrl });
|
const { data, isLoading } = useInspectFlake({
|
||||||
|
url: flakeUrl,
|
||||||
|
});
|
||||||
|
|
||||||
return userConfirmed ? (
|
return userConfirmed ? (
|
||||||
<ConfirmVM url={flakeUrl} handleBack={handleBack} />
|
<ConfirmVM
|
||||||
|
url={flakeUrl}
|
||||||
|
handleBack={handleBack}
|
||||||
|
defaultFlakeAttr={flakeAttr}
|
||||||
|
/>
|
||||||
) : (
|
) : (
|
||||||
<div className="mb-2 flex w-full max-w-2xl flex-col items-center justify-self-center pb-2 ">
|
<div className="mb-2 flex w-full max-w-2xl flex-col items-center justify-self-center pb-2 ">
|
||||||
{isLoading && (
|
{isLoading && (
|
||||||
<LoadingOverlay
|
<LoadingOverlay
|
||||||
title={"Loading Flake"}
|
title={"Loading Flake"}
|
||||||
subtitle={<FlakeBadge flakeUrl={flakeUrl} flakeAttr="" />}
|
subtitle={<FlakeBadge flakeUrl={flakeUrl} flakeAttr={flakeAttr} />}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
{data && (
|
{data && (
|
||||||
|
|||||||
@@ -3,30 +3,23 @@ import React, { useEffect, useState } from "react";
|
|||||||
import { VmConfig } from "@/api/model";
|
import { VmConfig } from "@/api/model";
|
||||||
import { useVms } from "@/components/hooks/useVms";
|
import { useVms } from "@/components/hooks/useVms";
|
||||||
|
|
||||||
import { Alert, AlertTitle, Button } from "@mui/material";
|
|
||||||
|
|
||||||
import { useSearchParams } from "next/navigation";
|
|
||||||
|
|
||||||
import { createVm, inspectVm, useGetVmLogs } from "@/api/default/default";
|
|
||||||
|
|
||||||
import { LoadingOverlay } from "./loadingOverlay";
|
import { LoadingOverlay } from "./loadingOverlay";
|
||||||
import { FlakeBadge } from "../flakeBadge/flakeBadge";
|
import { useForm } from "react-hook-form";
|
||||||
import { Log } from "./log";
|
|
||||||
import { SubmitHandler, useForm } from "react-hook-form";
|
|
||||||
import { ConfigureVM } from "./configureVM";
|
import { ConfigureVM } from "./configureVM";
|
||||||
import { VmBuildLogs } from "./vmBuildLogs";
|
import { VmBuildLogs } from "./vmBuildLogs";
|
||||||
|
|
||||||
interface ConfirmVMProps {
|
interface ConfirmVMProps {
|
||||||
url: string;
|
url: string;
|
||||||
handleBack: () => void;
|
handleBack: () => void;
|
||||||
|
defaultFlakeAttr: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function ConfirmVM(props: ConfirmVMProps) {
|
export function ConfirmVM(props: ConfirmVMProps) {
|
||||||
const { url, handleBack } = props;
|
const { url, defaultFlakeAttr } = props;
|
||||||
const formHooks = useForm<VmConfig>({
|
const formHooks = useForm<VmConfig>({
|
||||||
defaultValues: {
|
defaultValues: {
|
||||||
flake_url: url,
|
flake_url: url,
|
||||||
flake_attr: "default",
|
flake_attr: defaultFlakeAttr,
|
||||||
cores: 4,
|
cores: 4,
|
||||||
graphics: true,
|
graphics: true,
|
||||||
memory_size: 2048,
|
memory_size: 2048,
|
||||||
@@ -34,11 +27,12 @@ export function ConfirmVM(props: ConfirmVMProps) {
|
|||||||
});
|
});
|
||||||
const [vmUuid, setVmUuid] = useState<string | null>(null);
|
const [vmUuid, setVmUuid] = useState<string | null>(null);
|
||||||
|
|
||||||
const { setValue, watch, formState, handleSubmit } = formHooks;
|
const { setValue, watch, formState } = formHooks;
|
||||||
const { config, error, isLoading } = useVms({
|
const { config, isLoading } = useVms({
|
||||||
url,
|
url,
|
||||||
attr: watch("flake_attr"),
|
attr: watch("flake_attr") || defaultFlakeAttr,
|
||||||
});
|
});
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (config) {
|
if (config) {
|
||||||
setValue("cores", config?.cores);
|
setValue("cores", config?.cores);
|
||||||
@@ -51,44 +45,12 @@ export function ConfirmVM(props: ConfirmVMProps) {
|
|||||||
<div className="mb-2 flex w-full max-w-2xl flex-col items-center justify-self-center pb-2">
|
<div className="mb-2 flex w-full max-w-2xl flex-col items-center justify-self-center pb-2">
|
||||||
{!formState.isSubmitted && (
|
{!formState.isSubmitted && (
|
||||||
<>
|
<>
|
||||||
{/* {error && (
|
|
||||||
<Alert severity="error" className="w-full max-w-2xl">
|
|
||||||
<AlertTitle>Error</AlertTitle>
|
|
||||||
An Error occurred - See details below
|
|
||||||
</Alert>
|
|
||||||
)} */}
|
|
||||||
<div className="mb-2 w-full max-w-2xl">
|
<div className="mb-2 w-full max-w-2xl">
|
||||||
{isLoading && (
|
{isLoading && (
|
||||||
<LoadingOverlay
|
<LoadingOverlay title={"Loading VM Configuration"} subtitle="" />
|
||||||
title={"Loading VM Configuration"}
|
|
||||||
subtitle={<FlakeBadge flakeUrl={url} flakeAttr={url} />}
|
|
||||||
/>
|
|
||||||
)}
|
)}
|
||||||
|
|
||||||
<ConfigureVM formHooks={formHooks} setVmUuid={setVmUuid} />
|
<ConfigureVM formHooks={formHooks} setVmUuid={setVmUuid} />
|
||||||
|
|
||||||
{/* {error && (
|
|
||||||
<>
|
|
||||||
<Button
|
|
||||||
color="error"
|
|
||||||
fullWidth
|
|
||||||
variant="contained"
|
|
||||||
onClick={handleBack}
|
|
||||||
className="my-2"
|
|
||||||
>
|
|
||||||
Back
|
|
||||||
</Button>
|
|
||||||
<Log
|
|
||||||
title="Log"
|
|
||||||
lines={
|
|
||||||
error?.response?.data?.detail
|
|
||||||
?.map((err, idx) => err.msg.split("\n"))
|
|
||||||
?.flat()
|
|
||||||
.filter(Boolean) || []
|
|
||||||
}
|
|
||||||
/>
|
|
||||||
</>
|
|
||||||
)} */}
|
|
||||||
</div>
|
</div>
|
||||||
</>
|
</>
|
||||||
)}
|
)}
|
||||||
|
|||||||
@@ -1,18 +1,27 @@
|
|||||||
"use client";
|
"use client";
|
||||||
import { LinearProgress, Typography } from "@mui/material";
|
import { CircularProgress, LinearProgress, Typography } from "@mui/material";
|
||||||
|
|
||||||
interface LoadingOverlayProps {
|
interface LoadingOverlayProps {
|
||||||
title: React.ReactNode;
|
title: React.ReactNode;
|
||||||
subtitle: React.ReactNode;
|
subtitle: React.ReactNode;
|
||||||
|
variant?: "linear" | "circle";
|
||||||
}
|
}
|
||||||
export const LoadingOverlay = (props: LoadingOverlayProps) => {
|
export const LoadingOverlay = (props: LoadingOverlayProps) => {
|
||||||
const { title, subtitle } = props;
|
const { title, subtitle, variant = "linear" } = props;
|
||||||
return (
|
return (
|
||||||
<div className="w-full">
|
<div className="w-full">
|
||||||
<Typography variant="subtitle2">{title}</Typography>
|
<div className="grid w-full place-items-center">
|
||||||
<LinearProgress className="mb-2 w-full" />
|
<Typography variant="subtitle1">{title}</Typography>
|
||||||
<div className="grid w-full place-items-center">{subtitle}</div>
|
</div>
|
||||||
<Typography variant="subtitle1"></Typography>
|
<div className="grid w-full place-items-center">
|
||||||
|
<Typography variant="subtitle2">{subtitle}</Typography>
|
||||||
|
</div>
|
||||||
|
{variant === "linear" && <LinearProgress className="my-2 w-full" />}
|
||||||
|
{variant === "circle" && (
|
||||||
|
<div className="grid w-full place-items-center">
|
||||||
|
<CircularProgress className="my-2 w-full" />
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -9,11 +9,7 @@ interface VmBuildLogsProps {
|
|||||||
export const VmBuildLogs = (props: VmBuildLogsProps) => {
|
export const VmBuildLogs = (props: VmBuildLogsProps) => {
|
||||||
const { vmUuid } = props;
|
const { vmUuid } = props;
|
||||||
|
|
||||||
const {
|
const { data: logs, isLoading } = useGetVmLogs(vmUuid as string, {
|
||||||
data: logs,
|
|
||||||
isLoading,
|
|
||||||
error,
|
|
||||||
} = useGetVmLogs(vmUuid as string, {
|
|
||||||
swr: {
|
swr: {
|
||||||
enabled: vmUuid !== null,
|
enabled: vmUuid !== null,
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -1,17 +1,14 @@
|
|||||||
import {
|
import {
|
||||||
Alert,
|
|
||||||
Divider,
|
Divider,
|
||||||
Icon,
|
|
||||||
IconButton,
|
IconButton,
|
||||||
List,
|
List,
|
||||||
ListItem,
|
ListItem,
|
||||||
ListItemButton,
|
ListItemButton,
|
||||||
ListItemIcon,
|
ListItemIcon,
|
||||||
ListItemText,
|
ListItemText,
|
||||||
Snackbar,
|
|
||||||
} from "@mui/material";
|
} from "@mui/material";
|
||||||
import Image from "next/image";
|
import Image from "next/image";
|
||||||
import { ReactNode, useState } from "react";
|
import { ReactNode } from "react";
|
||||||
|
|
||||||
import DashboardIcon from "@mui/icons-material/Dashboard";
|
import DashboardIcon from "@mui/icons-material/Dashboard";
|
||||||
import DevicesIcon from "@mui/icons-material/Devices";
|
import DevicesIcon from "@mui/icons-material/Devices";
|
||||||
@@ -29,7 +26,7 @@ type MenuEntry = {
|
|||||||
icon: ReactNode;
|
icon: ReactNode;
|
||||||
label: string;
|
label: string;
|
||||||
to: string;
|
to: string;
|
||||||
missing: boolean;
|
disabled: boolean;
|
||||||
} & {
|
} & {
|
||||||
subMenuEntries?: MenuEntry[];
|
subMenuEntries?: MenuEntry[];
|
||||||
};
|
};
|
||||||
@@ -39,37 +36,37 @@ const menuEntries: MenuEntry[] = [
|
|||||||
icon: <DashboardIcon />,
|
icon: <DashboardIcon />,
|
||||||
label: "Dashoard",
|
label: "Dashoard",
|
||||||
to: "/",
|
to: "/",
|
||||||
missing: false,
|
disabled: false,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
icon: <DevicesIcon />,
|
icon: <DevicesIcon />,
|
||||||
label: "Machines",
|
label: "Machines",
|
||||||
to: "/machines",
|
to: "/machines",
|
||||||
missing: false,
|
disabled: false,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
icon: <AppsIcon />,
|
icon: <AppsIcon />,
|
||||||
label: "Applications",
|
label: "Applications",
|
||||||
to: "/applications",
|
to: "/applications",
|
||||||
missing: true,
|
disabled: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
icon: <LanIcon />,
|
icon: <LanIcon />,
|
||||||
label: "Network",
|
label: "Network",
|
||||||
to: "/network",
|
to: "/network",
|
||||||
missing: true,
|
disabled: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
icon: <DesignServicesIcon />,
|
icon: <DesignServicesIcon />,
|
||||||
label: "Templates",
|
label: "Templates",
|
||||||
to: "/templates",
|
to: "/templates",
|
||||||
missing: false,
|
disabled: false,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
icon: <BackupIcon />,
|
icon: <BackupIcon />,
|
||||||
label: "Backups",
|
label: "Backups",
|
||||||
to: "/backups",
|
to: "/backups",
|
||||||
missing: true,
|
disabled: true,
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
@@ -83,22 +80,6 @@ interface SidebarProps {
|
|||||||
export function Sidebar(props: SidebarProps) {
|
export function Sidebar(props: SidebarProps) {
|
||||||
const { show, onClose } = props;
|
const { show, onClose } = props;
|
||||||
|
|
||||||
const [open, setOpen] = React.useState(false);
|
|
||||||
const handleClick = () => {
|
|
||||||
setOpen(true);
|
|
||||||
};
|
|
||||||
|
|
||||||
const handleClose = (
|
|
||||||
event?: React.SyntheticEvent | Event,
|
|
||||||
reason?: string,
|
|
||||||
) => {
|
|
||||||
if (reason === "clickaway") {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
setOpen(false);
|
|
||||||
};
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<aside
|
<aside
|
||||||
className={tw`${
|
className={tw`${
|
||||||
@@ -137,10 +118,8 @@ export function Sidebar(props: SidebarProps) {
|
|||||||
<ListItemButton
|
<ListItemButton
|
||||||
className="justify-center lg:justify-normal"
|
className="justify-center lg:justify-normal"
|
||||||
LinkComponent={Link}
|
LinkComponent={Link}
|
||||||
href={menuEntry.missing ? "" : menuEntry.to}
|
href={menuEntry.to}
|
||||||
onClickCapture={
|
disabled={menuEntry.disabled}
|
||||||
menuEntry.missing ? () => handleClick() : undefined
|
|
||||||
}
|
|
||||||
>
|
>
|
||||||
<ListItemIcon
|
<ListItemIcon
|
||||||
color="inherit"
|
color="inherit"
|
||||||
@@ -160,12 +139,6 @@ export function Sidebar(props: SidebarProps) {
|
|||||||
);
|
);
|
||||||
})}
|
})}
|
||||||
</List>
|
</List>
|
||||||
|
|
||||||
<Snackbar open={open} autoHideDuration={2000} onClose={handleClose}>
|
|
||||||
<Alert onClose={handleClose} severity="error" sx={{ width: "100%" }}>
|
|
||||||
Site does not exist yet
|
|
||||||
</Alert>
|
|
||||||
</Snackbar>
|
|
||||||
<Divider flexItem className="mx-8 my-10 hidden bg-zinc-600 lg:block" />
|
<Divider flexItem className="mx-8 my-10 hidden bg-zinc-600 lg:block" />
|
||||||
<div className="mx-auto mb-8 hidden w-full max-w-xs rounded-sm px-4 py-6 text-center align-bottom shadow-sm lg:block">
|
<div className="mx-auto mb-8 hidden w-full max-w-xs rounded-sm px-4 py-6 text-center align-bottom shadow-sm lg:block">
|
||||||
<h3 className="mb-2 w-full font-semibold text-white">
|
<h3 className="mb-2 w-full font-semibold text-white">
|
||||||
|
|||||||
@@ -15,7 +15,7 @@ export type NodeStatusKeys = (typeof NodeStatus)[keyof typeof NodeStatus];
|
|||||||
function createData(
|
function createData(
|
||||||
name: string,
|
name: string,
|
||||||
status: NodeStatusKeys,
|
status: NodeStatusKeys,
|
||||||
last_seen: number,
|
last_seen: number
|
||||||
): TableData {
|
): TableData {
|
||||||
if (status == NodeStatus.Online) {
|
if (status == NodeStatus.Online) {
|
||||||
last_seen = 0;
|
last_seen = 0;
|
||||||
@@ -58,20 +58,20 @@ function getRandomName(): string {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// A function to generate random IPv6 addresses
|
// A function to generate random IPv6 addresses
|
||||||
function getRandomId(): string {
|
// function getRandomId(): string {
|
||||||
let hex = "0123456789abcdef";
|
// let hex = "0123456789abcdef";
|
||||||
let id = "";
|
// let id = "";
|
||||||
for (let i = 0; i < 8; i++) {
|
// for (let i = 0; i < 8; i++) {
|
||||||
for (let j = 0; j < 4; j++) {
|
// for (let j = 0; j < 4; j++) {
|
||||||
let index = Math.floor(Math.random() * hex.length);
|
// let index = Math.floor(Math.random() * hex.length);
|
||||||
id += hex[index];
|
// id += hex[index];
|
||||||
}
|
// }
|
||||||
if (i < 7) {
|
// if (i < 7) {
|
||||||
id += ":";
|
// id += ":";
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
return id;
|
// return id;
|
||||||
}
|
// }
|
||||||
|
|
||||||
// A function to generate random status keys
|
// A function to generate random status keys
|
||||||
function getRandomStatus(): NodeStatusKeys {
|
function getRandomStatus(): NodeStatusKeys {
|
||||||
@@ -96,61 +96,61 @@ export const tableData = [
|
|||||||
"Matchbox",
|
"Matchbox",
|
||||||
|
|
||||||
NodeStatus.Pending,
|
NodeStatus.Pending,
|
||||||
0,
|
0
|
||||||
),
|
),
|
||||||
createData(
|
createData(
|
||||||
"Ahorn",
|
"Ahorn",
|
||||||
|
|
||||||
NodeStatus.Online,
|
NodeStatus.Online,
|
||||||
0,
|
0
|
||||||
),
|
),
|
||||||
createData(
|
createData(
|
||||||
"Yellow",
|
"Yellow",
|
||||||
|
|
||||||
NodeStatus.Offline,
|
NodeStatus.Offline,
|
||||||
16.0,
|
16.0
|
||||||
),
|
),
|
||||||
createData(
|
createData(
|
||||||
"Rauter",
|
"Rauter",
|
||||||
|
|
||||||
NodeStatus.Offline,
|
NodeStatus.Offline,
|
||||||
6.0,
|
6.0
|
||||||
),
|
),
|
||||||
createData(
|
createData(
|
||||||
"Porree",
|
"Porree",
|
||||||
|
|
||||||
NodeStatus.Offline,
|
NodeStatus.Offline,
|
||||||
13,
|
13
|
||||||
),
|
),
|
||||||
createData(
|
createData(
|
||||||
"Helsinki",
|
"Helsinki",
|
||||||
|
|
||||||
NodeStatus.Online,
|
NodeStatus.Online,
|
||||||
0,
|
0
|
||||||
),
|
),
|
||||||
createData(
|
createData(
|
||||||
"Kelle",
|
"Kelle",
|
||||||
|
|
||||||
NodeStatus.Online,
|
NodeStatus.Online,
|
||||||
0,
|
0
|
||||||
),
|
),
|
||||||
createData(
|
createData(
|
||||||
"Shodan",
|
"Shodan",
|
||||||
|
|
||||||
NodeStatus.Online,
|
NodeStatus.Online,
|
||||||
0.0,
|
0.0
|
||||||
),
|
),
|
||||||
createData(
|
createData(
|
||||||
"Qubasa",
|
"Qubasa",
|
||||||
|
|
||||||
NodeStatus.Offline,
|
NodeStatus.Offline,
|
||||||
7.0,
|
7.0
|
||||||
),
|
),
|
||||||
createData(
|
createData(
|
||||||
"Green",
|
"Green",
|
||||||
|
|
||||||
NodeStatus.Offline,
|
NodeStatus.Offline,
|
||||||
2,
|
2
|
||||||
),
|
),
|
||||||
createData("Gum", NodeStatus.Offline, 0),
|
createData("Gum", NodeStatus.Offline, 0),
|
||||||
createData("Xu", NodeStatus.Online, 0),
|
createData("Xu", NodeStatus.Online, 0),
|
||||||
@@ -158,7 +158,7 @@ export const tableData = [
|
|||||||
"Zaatar",
|
"Zaatar",
|
||||||
|
|
||||||
NodeStatus.Online,
|
NodeStatus.Online,
|
||||||
0,
|
0
|
||||||
),
|
),
|
||||||
];
|
];
|
||||||
|
|
||||||
|
|||||||
@@ -1,15 +1,9 @@
|
|||||||
"use client";
|
"use client";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
import {
|
import { IconButton, Input, InputAdornment } from "@mui/material";
|
||||||
FormControl,
|
|
||||||
FormHelperText,
|
|
||||||
IconButton,
|
|
||||||
Input,
|
|
||||||
InputAdornment,
|
|
||||||
} from "@mui/material";
|
|
||||||
import { useSearchParams } from "next/navigation";
|
import { useSearchParams } from "next/navigation";
|
||||||
|
|
||||||
import { useForm, SubmitHandler, Controller } from "react-hook-form";
|
import { useForm, Controller } from "react-hook-form";
|
||||||
import { Confirm } from "@/components/join/confirm";
|
import { Confirm } from "@/components/join/confirm";
|
||||||
import { Layout } from "@/components/join/layout";
|
import { Layout } from "@/components/join/layout";
|
||||||
import { ChevronRight } from "@mui/icons-material";
|
import { ChevronRight } from "@mui/icons-material";
|
||||||
@@ -21,6 +15,7 @@ type FormValues = {
|
|||||||
export default function JoinPrequel() {
|
export default function JoinPrequel() {
|
||||||
const queryParams = useSearchParams();
|
const queryParams = useSearchParams();
|
||||||
const flakeUrl = queryParams.get("flake") || "";
|
const flakeUrl = queryParams.get("flake") || "";
|
||||||
|
const flakeAttr = queryParams.get("attr") || "default";
|
||||||
const { handleSubmit, control, formState, getValues, reset } =
|
const { handleSubmit, control, formState, getValues, reset } =
|
||||||
useForm<FormValues>({ defaultValues: { flakeUrl: "" } });
|
useForm<FormValues>({ defaultValues: { flakeUrl: "" } });
|
||||||
|
|
||||||
@@ -60,6 +55,7 @@ export default function JoinPrequel() {
|
|||||||
<Confirm
|
<Confirm
|
||||||
handleBack={() => reset()}
|
handleBack={() => reset()}
|
||||||
flakeUrl={formState.isSubmitted ? getValues("flakeUrl") : flakeUrl}
|
flakeUrl={formState.isSubmitted ? getValues("flakeUrl") : flakeUrl}
|
||||||
|
flakeAttr={flakeAttr}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
</Layout>
|
</Layout>
|
||||||
|
|||||||
@@ -14,6 +14,7 @@
|
|||||||
"isolatedModules": true,
|
"isolatedModules": true,
|
||||||
"jsx": "preserve",
|
"jsx": "preserve",
|
||||||
"incremental": true,
|
"incremental": true,
|
||||||
|
"noUnusedLocals": true,
|
||||||
"plugins": [
|
"plugins": [
|
||||||
{
|
{
|
||||||
"name": "next"
|
"name": "next"
|
||||||
|
|||||||
Reference in New Issue
Block a user