Design changes
This commit is contained in:
parent
3b00fd2ec0
commit
aa1f7b25cf
7 changed files with 127 additions and 37 deletions
3
.env
Normal file
3
.env
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
#This file current does nothing, but is here for future use.
|
||||
URL=http://caddy.example.com
|
||||
CADDY_API=http://192.168.1.69:2019
|
||||
2
.gitignore
vendored
2
.gitignore
vendored
|
|
@ -20,6 +20,8 @@ package-lock.json
|
|||
.DS_Store
|
||||
*.pem
|
||||
|
||||
.env
|
||||
|
||||
# debug
|
||||
npm-debug.log*
|
||||
yarn-debug.log*
|
||||
|
|
|
|||
18
app/page.tsx
18
app/page.tsx
|
|
@ -1,6 +1,3 @@
|
|||
"use client"
|
||||
|
||||
|
||||
import { useRoutes } from '@/lib/clientActions';
|
||||
import Image from 'next/image';
|
||||
import Loading from '@/components/Loading';
|
||||
|
|
@ -9,25 +6,20 @@ import { useState } from 'react';
|
|||
import { RouteDialog } from '@/components/RouteDialog';
|
||||
import Header from '@/components/Header';
|
||||
import RouteCards from '@/components/RouteCards';
|
||||
import { SWRConfig } from 'swr';
|
||||
|
||||
|
||||
export default function Home() {
|
||||
|
||||
const { data: routes, error, isLoading } = useRoutes();
|
||||
let routesMap: Route[] = routes as Route[];
|
||||
|
||||
if (error) return <Error />
|
||||
if (isLoading) return <Loading />
|
||||
|
||||
return (
|
||||
<main>
|
||||
|
||||
|
||||
<div>
|
||||
<Header routes={routesMap} />
|
||||
<Header />
|
||||
</div>
|
||||
|
||||
<div className='grid grid-flow-row-dense md:grid-cols-6 sm:grid-cols-2 p-2'>
|
||||
<RouteCards routes={routesMap} />
|
||||
<div className='flex flex-grid p-2 flex-wrap justify-center gap-2'>
|
||||
<RouteCards />
|
||||
</div>
|
||||
</main>
|
||||
)
|
||||
|
|
|
|||
|
|
@ -11,15 +11,17 @@ export default function Error() {
|
|||
|
||||
return (
|
||||
<div className='flex justify-center'>
|
||||
<Card>
|
||||
<CardHeader>
|
||||
<CardTitle>Error</CardTitle>
|
||||
<CardDescription>There was an error fetching your data</CardDescription>
|
||||
</CardHeader>
|
||||
<CardFooter className="flex justify-center">
|
||||
<Button onClick={handleRefresh}>Retry</Button>
|
||||
</CardFooter>
|
||||
</Card>
|
||||
<div className="flex justify-center items-center min-h-screen h-[90vh]">
|
||||
<Card>
|
||||
<CardHeader>
|
||||
<CardTitle>Error</CardTitle>
|
||||
<CardDescription>There was an error fetching your data</CardDescription>
|
||||
</CardHeader>
|
||||
<CardFooter className="flex justify-center">
|
||||
<Button onClick={handleRefresh}>Retry</Button>
|
||||
</CardFooter>
|
||||
</Card>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
68
components/Header.tsx
Normal file
68
components/Header.tsx
Normal file
|
|
@ -0,0 +1,68 @@
|
|||
"use client"
|
||||
|
||||
import { CardTitle, Card, CardDescription, CardHeader, CardContent, CardFooter } from '@/components/ui/card';
|
||||
import RouteCards from '@/components/RouteCards';
|
||||
import { Button } from '@/components/ui/button';
|
||||
import { useState } from 'react';
|
||||
import { useRoutes } from '@/lib/clientActions';
|
||||
import Error from './Error';
|
||||
import Loading from './Loading';
|
||||
import { RouteDialog } from './RouteDialog';
|
||||
|
||||
export default function Header() {
|
||||
|
||||
const { data: routes, error, isLoading } = useRoutes();
|
||||
let routesMap: Route[] = routes as Route[];
|
||||
|
||||
const [route, setRoute] = useState<Route>();
|
||||
const [open, setOpen] = useState(false);
|
||||
|
||||
return (
|
||||
<>
|
||||
{route && <RouteDialog open={open} onOpenChange={setOpen} route={route} routesMap={routesMap} />}
|
||||
|
||||
<div className='flex items-center justify-center py-6'>
|
||||
<Card className='flex'>
|
||||
<CardHeader>
|
||||
<CardTitle>Active Routes</CardTitle>
|
||||
<CardDescription>Amount of configured routes</CardDescription>
|
||||
</CardHeader>
|
||||
<CardContent className='flex items-center'>
|
||||
<div>
|
||||
<p className='text-xl font-semibold translate-y-2'>{routesMap?.length}</p>
|
||||
</div>
|
||||
</CardContent>
|
||||
<CardFooter>
|
||||
<Button onClick={() => {
|
||||
setRoute({
|
||||
"handle": [
|
||||
{
|
||||
"handler": "subroute",
|
||||
"routes": [
|
||||
{
|
||||
"handle": [
|
||||
{
|
||||
"handler": "reverse_proxy",
|
||||
"upstreams": []
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
],
|
||||
"match": [
|
||||
{
|
||||
"host": []
|
||||
}
|
||||
],
|
||||
"terminal": true
|
||||
})
|
||||
setOpen(true);
|
||||
}} className='translate-y-2.5'>Create</Button>
|
||||
</CardFooter>
|
||||
</Card>
|
||||
</div>
|
||||
|
||||
</>
|
||||
)
|
||||
}
|
||||
|
|
@ -3,8 +3,10 @@ import Image from "next/image";
|
|||
export default function Loading() {
|
||||
return (
|
||||
<div className='flex justify-center'>
|
||||
<Image src="/loading.svg" alt="Loading" width={25} height={25} />
|
||||
<p className='p-2'>Loading</p>
|
||||
<div className="flex items-center min-h-screen h-[90vh]">
|
||||
<Image src="/loading.svg" alt="Loading" width={25} height={25} />
|
||||
<p className='p-2'>Loading</p>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
|
@ -2,18 +2,24 @@
|
|||
|
||||
import { Button } from '@/components/ui/button';
|
||||
import { Card, CardHeader, CardTitle, CardDescription, CardContent, CardFooter } from "./ui/card";
|
||||
import { getHosts, getRouteUpstreams } from '@/lib/utils';
|
||||
import { getHandler, getHosts, getRouteUpstreams } from '@/lib/utils';
|
||||
import { toast } from './ui/use-toast';
|
||||
import React, { useState } from 'react';
|
||||
import useSWRMutation from 'swr/mutation';
|
||||
import { deleteRoute } from '@/lib/clientActions';
|
||||
import { deleteRoute, useRoutes } from '@/lib/clientActions';
|
||||
import { RouteDialog } from './RouteDialog';
|
||||
import Error from './Error';
|
||||
import Loading from './Loading';
|
||||
|
||||
export default function RouteCards({ routes }: { routes: Route[] }) {
|
||||
export default function RouteCards() {
|
||||
|
||||
const { data: routes, error, isLoading } = useRoutes();
|
||||
let routesMap: Route[] = routes as Route[];
|
||||
|
||||
const [route, setRoute] = useState<Route>();
|
||||
const [open, setOpen] = useState(false);
|
||||
|
||||
|
||||
const { trigger: handleDelete } = useSWRMutation("/api/caddy/routes", deleteRoute, {
|
||||
onError: () => {
|
||||
return toast({
|
||||
|
|
@ -36,29 +42,44 @@ export default function RouteCards({ routes }: { routes: Route[] }) {
|
|||
setRoute(route);
|
||||
}
|
||||
|
||||
|
||||
if (error) return <Error />
|
||||
if (isLoading) return <Loading />
|
||||
|
||||
|
||||
return (
|
||||
<>
|
||||
{route && <RouteDialog open={open} onOpenChange={setOpen} route={route} routesMap={routes} />}
|
||||
{route && <RouteDialog open={open} onOpenChange={setOpen} route={route} routesMap={routesMap} />}
|
||||
{
|
||||
routes.map((route, index) => (
|
||||
<div key={index} className='p-2'>
|
||||
<Card key={index} className='w-[15vw]'>
|
||||
routesMap.map((route, index) => (
|
||||
<div key={index}>
|
||||
<Card key={index}>
|
||||
<CardHeader>
|
||||
<CardTitle>{getHosts(route)!.values().next().value}</CardTitle>
|
||||
{getHosts(route)!.map((route => <CardDescription key={route}>{route}</ CardDescription>))}
|
||||
<CardDescription></CardDescription>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<p className="text-sm font-medium leading-none">
|
||||
Tunneling to
|
||||
</p>
|
||||
<p className="text-sm text-muted-foreground">{getRouteUpstreams(route)?.map((upstream => upstream.dial))}</p>
|
||||
<div className='flex flex-grid gap-6 items-center justify-center'>
|
||||
<div>
|
||||
<p className='text-sm font-mdeium leading-none'>
|
||||
Type
|
||||
</p>
|
||||
<p className='text-sm text-muted-foreground'>{getHandler(route)}</p>
|
||||
</div>
|
||||
<div>
|
||||
<p className="text-sm font-medium leading-none">
|
||||
Tunneling to
|
||||
</p>
|
||||
<p className="text-sm text-muted-foreground">{getRouteUpstreams(route)?.map((upstream => upstream.dial))}</p>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
<CardFooter className="flex justify-between">
|
||||
<Button onClick={() => {
|
||||
<Button onClick={() => {
|
||||
editRoute(route)
|
||||
setOpen(true)
|
||||
}}>Edit</Button>
|
||||
}}>Edit</Button>
|
||||
<Button variant="destructive" onClick={() => { handleDelete(route) }}>Delete</Button>
|
||||
</CardFooter>
|
||||
</Card>
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue