mirror of
https://github.com/Dokploy/dokploy
synced 2025-06-26 18:27:59 +00:00
Merge pull request #1106 from DJKnaeckebrot/fix/styling-after-sidebar-fixes
fix(style): clean up sidebar related style issue
This commit is contained in:
@@ -1,13 +1,13 @@
|
|||||||
import {
|
import {
|
||||||
type ColumnFiltersState,
|
type ColumnFiltersState,
|
||||||
type SortingState,
|
type SortingState,
|
||||||
type VisibilityState,
|
type VisibilityState,
|
||||||
flexRender,
|
flexRender,
|
||||||
getCoreRowModel,
|
getCoreRowModel,
|
||||||
getFilteredRowModel,
|
getFilteredRowModel,
|
||||||
getPaginationRowModel,
|
getPaginationRowModel,
|
||||||
getSortedRowModel,
|
getSortedRowModel,
|
||||||
useReactTable,
|
useReactTable,
|
||||||
} from "@tanstack/react-table";
|
} from "@tanstack/react-table";
|
||||||
import { ChevronDown, Container } from "lucide-react";
|
import { ChevronDown, Container } from "lucide-react";
|
||||||
import * as React from "react";
|
import * as React from "react";
|
||||||
@@ -15,228 +15,228 @@ import * as React from "react";
|
|||||||
import { AlertBlock } from "@/components/shared/alert-block";
|
import { AlertBlock } from "@/components/shared/alert-block";
|
||||||
import { Button } from "@/components/ui/button";
|
import { Button } from "@/components/ui/button";
|
||||||
import {
|
import {
|
||||||
Card,
|
Card,
|
||||||
CardContent,
|
CardContent,
|
||||||
CardDescription,
|
CardDescription,
|
||||||
CardHeader,
|
CardHeader,
|
||||||
CardTitle,
|
CardTitle,
|
||||||
} from "@/components/ui/card";
|
} from "@/components/ui/card";
|
||||||
import {
|
import {
|
||||||
DropdownMenu,
|
DropdownMenu,
|
||||||
DropdownMenuCheckboxItem,
|
DropdownMenuCheckboxItem,
|
||||||
DropdownMenuContent,
|
DropdownMenuContent,
|
||||||
DropdownMenuTrigger,
|
DropdownMenuTrigger,
|
||||||
} from "@/components/ui/dropdown-menu";
|
} from "@/components/ui/dropdown-menu";
|
||||||
import { Input } from "@/components/ui/input";
|
import { Input } from "@/components/ui/input";
|
||||||
import {
|
import {
|
||||||
Table,
|
Table,
|
||||||
TableBody,
|
TableBody,
|
||||||
TableCell,
|
TableCell,
|
||||||
TableHead,
|
TableHead,
|
||||||
TableHeader,
|
TableHeader,
|
||||||
TableRow,
|
TableRow,
|
||||||
} from "@/components/ui/table";
|
} from "@/components/ui/table";
|
||||||
import { type RouterOutputs, api } from "@/utils/api";
|
import { type RouterOutputs, api } from "@/utils/api";
|
||||||
import { columns } from "./colums";
|
import { columns } from "./colums";
|
||||||
export type Container = NonNullable<
|
export type Container = NonNullable<
|
||||||
RouterOutputs["docker"]["getContainers"]
|
RouterOutputs["docker"]["getContainers"]
|
||||||
>[0];
|
>[0];
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
serverId?: string;
|
serverId?: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const ShowContainers = ({ serverId }: Props) => {
|
export const ShowContainers = ({ serverId }: Props) => {
|
||||||
const { data, isLoading } = api.docker.getContainers.useQuery({
|
const { data, isLoading } = api.docker.getContainers.useQuery({
|
||||||
serverId,
|
serverId,
|
||||||
});
|
});
|
||||||
|
|
||||||
const [sorting, setSorting] = React.useState<SortingState>([]);
|
const [sorting, setSorting] = React.useState<SortingState>([]);
|
||||||
const [columnFilters, setColumnFilters] = React.useState<ColumnFiltersState>(
|
const [columnFilters, setColumnFilters] = React.useState<ColumnFiltersState>(
|
||||||
[],
|
[]
|
||||||
);
|
);
|
||||||
const [columnVisibility, setColumnVisibility] =
|
const [columnVisibility, setColumnVisibility] =
|
||||||
React.useState<VisibilityState>({});
|
React.useState<VisibilityState>({});
|
||||||
const [rowSelection, setRowSelection] = React.useState({});
|
const [rowSelection, setRowSelection] = React.useState({});
|
||||||
|
|
||||||
const table = useReactTable({
|
const table = useReactTable({
|
||||||
data: data ?? [],
|
data: data ?? [],
|
||||||
columns,
|
columns,
|
||||||
onSortingChange: setSorting,
|
onSortingChange: setSorting,
|
||||||
onColumnFiltersChange: setColumnFilters,
|
onColumnFiltersChange: setColumnFilters,
|
||||||
getCoreRowModel: getCoreRowModel(),
|
getCoreRowModel: getCoreRowModel(),
|
||||||
getPaginationRowModel: getPaginationRowModel(),
|
getPaginationRowModel: getPaginationRowModel(),
|
||||||
getSortedRowModel: getSortedRowModel(),
|
getSortedRowModel: getSortedRowModel(),
|
||||||
getFilteredRowModel: getFilteredRowModel(),
|
getFilteredRowModel: getFilteredRowModel(),
|
||||||
onColumnVisibilityChange: setColumnVisibility,
|
onColumnVisibilityChange: setColumnVisibility,
|
||||||
onRowSelectionChange: setRowSelection,
|
onRowSelectionChange: setRowSelection,
|
||||||
state: {
|
state: {
|
||||||
sorting,
|
sorting,
|
||||||
columnFilters,
|
columnFilters,
|
||||||
columnVisibility,
|
columnVisibility,
|
||||||
rowSelection,
|
rowSelection,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="w-full">
|
<div className="w-full">
|
||||||
<Card className="h-full bg-sidebar p-2.5 rounded-xl max-w-8xl mx-auto">
|
<Card className="h-full bg-sidebar p-2.5 rounded-xl">
|
||||||
<div className="rounded-xl bg-background shadow-md ">
|
<div className="rounded-xl bg-background shadow-md ">
|
||||||
<CardHeader className="">
|
<CardHeader className="">
|
||||||
<CardTitle className="text-xl flex flex-row gap-2">
|
<CardTitle className="text-xl flex flex-row gap-2">
|
||||||
<Container className="size-6 text-muted-foreground self-center" />
|
<Container className="size-6 text-muted-foreground self-center" />
|
||||||
Docker Containers
|
Docker Containers
|
||||||
</CardTitle>
|
</CardTitle>
|
||||||
<CardDescription>
|
<CardDescription>
|
||||||
See all the containers of your dokploy server
|
See all the containers of your dokploy server
|
||||||
</CardDescription>
|
</CardDescription>
|
||||||
</CardHeader>
|
</CardHeader>
|
||||||
<CardContent className="space-y-2 py-8 border-t">
|
<CardContent className="space-y-2 py-8 border-t">
|
||||||
<div className="gap-4 pb-20 w-full">
|
<div className="gap-4 pb-20 w-full">
|
||||||
<div className="flex flex-col gap-4 w-full overflow-auto">
|
<div className="flex flex-col gap-4 w-full overflow-auto">
|
||||||
<div className="flex items-center gap-2 max-sm:flex-wrap">
|
<div className="flex items-center gap-2 max-sm:flex-wrap">
|
||||||
<Input
|
<Input
|
||||||
placeholder="Filter by name..."
|
placeholder="Filter by name..."
|
||||||
value={
|
value={
|
||||||
(table.getColumn("name")?.getFilterValue() as string) ??
|
(table.getColumn("name")?.getFilterValue() as string) ??
|
||||||
""
|
""
|
||||||
}
|
}
|
||||||
onChange={(event) =>
|
onChange={(event) =>
|
||||||
table
|
table
|
||||||
.getColumn("name")
|
.getColumn("name")
|
||||||
?.setFilterValue(event.target.value)
|
?.setFilterValue(event.target.value)
|
||||||
}
|
}
|
||||||
className="md:max-w-sm"
|
className="md:max-w-sm"
|
||||||
/>
|
/>
|
||||||
<DropdownMenu>
|
<DropdownMenu>
|
||||||
<DropdownMenuTrigger asChild>
|
<DropdownMenuTrigger asChild>
|
||||||
<Button
|
<Button
|
||||||
variant="outline"
|
variant="outline"
|
||||||
className="sm:ml-auto max-sm:w-full"
|
className="sm:ml-auto max-sm:w-full"
|
||||||
>
|
>
|
||||||
Columns <ChevronDown className="ml-2 h-4 w-4" />
|
Columns <ChevronDown className="ml-2 h-4 w-4" />
|
||||||
</Button>
|
</Button>
|
||||||
</DropdownMenuTrigger>
|
</DropdownMenuTrigger>
|
||||||
<DropdownMenuContent align="end">
|
<DropdownMenuContent align="end">
|
||||||
{table
|
{table
|
||||||
.getAllColumns()
|
.getAllColumns()
|
||||||
.filter((column) => column.getCanHide())
|
.filter((column) => column.getCanHide())
|
||||||
.map((column) => {
|
.map((column) => {
|
||||||
return (
|
return (
|
||||||
<DropdownMenuCheckboxItem
|
<DropdownMenuCheckboxItem
|
||||||
key={column.id}
|
key={column.id}
|
||||||
className="capitalize"
|
className="capitalize"
|
||||||
checked={column.getIsVisible()}
|
checked={column.getIsVisible()}
|
||||||
onCheckedChange={(value) =>
|
onCheckedChange={(value) =>
|
||||||
column.toggleVisibility(!!value)
|
column.toggleVisibility(!!value)
|
||||||
}
|
}
|
||||||
>
|
>
|
||||||
{column.id}
|
{column.id}
|
||||||
</DropdownMenuCheckboxItem>
|
</DropdownMenuCheckboxItem>
|
||||||
);
|
);
|
||||||
})}
|
})}
|
||||||
</DropdownMenuContent>
|
</DropdownMenuContent>
|
||||||
</DropdownMenu>
|
</DropdownMenu>
|
||||||
</div>
|
</div>
|
||||||
<div className="rounded-md border">
|
<div className="rounded-md border">
|
||||||
{isLoading ? (
|
{isLoading ? (
|
||||||
<div className="w-full flex-col gap-2 flex items-center justify-center h-[55vh]">
|
<div className="w-full flex-col gap-2 flex items-center justify-center h-[55vh]">
|
||||||
<span className="text-muted-foreground text-lg font-medium">
|
<span className="text-muted-foreground text-lg font-medium">
|
||||||
Loading...
|
Loading...
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
) : data?.length === 0 ? (
|
) : data?.length === 0 ? (
|
||||||
<div className="flex-col gap-2 flex items-center justify-center h-[55vh]">
|
<div className="flex-col gap-2 flex items-center justify-center h-[55vh]">
|
||||||
<span className="text-muted-foreground text-lg font-medium">
|
<span className="text-muted-foreground text-lg font-medium">
|
||||||
No results.
|
No results.
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
) : (
|
) : (
|
||||||
<Table>
|
<Table>
|
||||||
<TableHeader>
|
<TableHeader>
|
||||||
{table.getHeaderGroups().map((headerGroup) => (
|
{table.getHeaderGroups().map((headerGroup) => (
|
||||||
<TableRow key={headerGroup.id}>
|
<TableRow key={headerGroup.id}>
|
||||||
{headerGroup.headers.map((header) => {
|
{headerGroup.headers.map((header) => {
|
||||||
return (
|
return (
|
||||||
<TableHead key={header.id}>
|
<TableHead key={header.id}>
|
||||||
{header.isPlaceholder
|
{header.isPlaceholder
|
||||||
? null
|
? null
|
||||||
: flexRender(
|
: flexRender(
|
||||||
header.column.columnDef.header,
|
header.column.columnDef.header,
|
||||||
header.getContext(),
|
header.getContext()
|
||||||
)}
|
)}
|
||||||
</TableHead>
|
</TableHead>
|
||||||
);
|
);
|
||||||
})}
|
})}
|
||||||
</TableRow>
|
</TableRow>
|
||||||
))}
|
))}
|
||||||
</TableHeader>
|
</TableHeader>
|
||||||
<TableBody>
|
<TableBody>
|
||||||
{table?.getRowModel()?.rows?.length ? (
|
{table?.getRowModel()?.rows?.length ? (
|
||||||
table.getRowModel().rows.map((row) => (
|
table.getRowModel().rows.map((row) => (
|
||||||
<TableRow
|
<TableRow
|
||||||
key={row.id}
|
key={row.id}
|
||||||
data-state={row.getIsSelected() && "selected"}
|
data-state={row.getIsSelected() && "selected"}
|
||||||
>
|
>
|
||||||
{row.getVisibleCells().map((cell) => (
|
{row.getVisibleCells().map((cell) => (
|
||||||
<TableCell key={cell.id}>
|
<TableCell key={cell.id}>
|
||||||
{flexRender(
|
{flexRender(
|
||||||
cell.column.columnDef.cell,
|
cell.column.columnDef.cell,
|
||||||
cell.getContext(),
|
cell.getContext()
|
||||||
)}
|
)}
|
||||||
</TableCell>
|
</TableCell>
|
||||||
))}
|
))}
|
||||||
</TableRow>
|
</TableRow>
|
||||||
))
|
))
|
||||||
) : (
|
) : (
|
||||||
<TableRow>
|
<TableRow>
|
||||||
<TableCell
|
<TableCell
|
||||||
colSpan={columns.length}
|
colSpan={columns.length}
|
||||||
className="h-24 text-center"
|
className="h-24 text-center"
|
||||||
>
|
>
|
||||||
{isLoading ? (
|
{isLoading ? (
|
||||||
<div className="w-full flex-col gap-2 flex items-center justify-center h-[55vh]">
|
<div className="w-full flex-col gap-2 flex items-center justify-center h-[55vh]">
|
||||||
<span className="text-muted-foreground text-lg font-medium">
|
<span className="text-muted-foreground text-lg font-medium">
|
||||||
Loading...
|
Loading...
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
) : (
|
) : (
|
||||||
<>No results.</>
|
<>No results.</>
|
||||||
)}
|
)}
|
||||||
</TableCell>
|
</TableCell>
|
||||||
</TableRow>
|
</TableRow>
|
||||||
)}
|
)}
|
||||||
</TableBody>
|
</TableBody>
|
||||||
</Table>
|
</Table>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
{data && data?.length > 0 && (
|
{data && data?.length > 0 && (
|
||||||
<div className="flex items-center justify-end space-x-2 py-4">
|
<div className="flex items-center justify-end space-x-2 py-4">
|
||||||
<div className="space-x-2 flex flex-wrap">
|
<div className="space-x-2 flex flex-wrap">
|
||||||
<Button
|
<Button
|
||||||
variant="outline"
|
variant="outline"
|
||||||
size="sm"
|
size="sm"
|
||||||
onClick={() => table.previousPage()}
|
onClick={() => table.previousPage()}
|
||||||
disabled={!table.getCanPreviousPage()}
|
disabled={!table.getCanPreviousPage()}
|
||||||
>
|
>
|
||||||
Previous
|
Previous
|
||||||
</Button>
|
</Button>
|
||||||
<Button
|
<Button
|
||||||
variant="outline"
|
variant="outline"
|
||||||
size="sm"
|
size="sm"
|
||||||
onClick={() => table.nextPage()}
|
onClick={() => table.nextPage()}
|
||||||
disabled={!table.getCanNextPage()}
|
disabled={!table.getCanNextPage()}
|
||||||
>
|
>
|
||||||
Next
|
Next
|
||||||
</Button>
|
</Button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</CardContent>
|
</CardContent>
|
||||||
</div>
|
</div>
|
||||||
</Card>
|
</Card>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
import { AlertBlock } from "@/components/shared/alert-block";
|
import { AlertBlock } from "@/components/shared/alert-block";
|
||||||
import {
|
import {
|
||||||
Card,
|
Card,
|
||||||
CardContent,
|
CardContent,
|
||||||
CardDescription,
|
CardDescription,
|
||||||
CardHeader,
|
CardHeader,
|
||||||
CardTitle,
|
CardTitle,
|
||||||
} from "@/components/ui/card";
|
} from "@/components/ui/card";
|
||||||
import { Tree } from "@/components/ui/file-tree";
|
import { Tree } from "@/components/ui/file-tree";
|
||||||
import { cn } from "@/lib/utils";
|
import { cn } from "@/lib/utils";
|
||||||
@@ -14,97 +14,97 @@ import React from "react";
|
|||||||
import { ShowTraefikFile } from "./show-traefik-file";
|
import { ShowTraefikFile } from "./show-traefik-file";
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
serverId?: string;
|
serverId?: string;
|
||||||
}
|
}
|
||||||
export const ShowTraefikSystem = ({ serverId }: Props) => {
|
export const ShowTraefikSystem = ({ serverId }: Props) => {
|
||||||
const [file, setFile] = React.useState<null | string>(null);
|
const [file, setFile] = React.useState<null | string>(null);
|
||||||
|
|
||||||
const {
|
const {
|
||||||
data: directories,
|
data: directories,
|
||||||
isLoading,
|
isLoading,
|
||||||
error,
|
error,
|
||||||
isError,
|
isError,
|
||||||
} = api.settings.readDirectories.useQuery(
|
} = api.settings.readDirectories.useQuery(
|
||||||
{
|
{
|
||||||
serverId,
|
serverId,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
retry: 2,
|
retry: 2,
|
||||||
},
|
}
|
||||||
);
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="w-full">
|
<div className="w-full">
|
||||||
<Card className="h-full bg-sidebar p-2.5 rounded-xl max-w-8xl mx-auto">
|
<Card className="h-full bg-sidebar p-2.5 rounded-xl">
|
||||||
<div className="rounded-xl bg-background shadow-md ">
|
<div className="rounded-xl bg-background shadow-md ">
|
||||||
<CardHeader className="">
|
<CardHeader className="">
|
||||||
<CardTitle className="text-xl flex flex-row gap-2">
|
<CardTitle className="text-xl flex flex-row gap-2">
|
||||||
<FileIcon className="size-6 text-muted-foreground self-center" />
|
<FileIcon className="size-6 text-muted-foreground self-center" />
|
||||||
Traefik File System
|
Traefik File System
|
||||||
</CardTitle>
|
</CardTitle>
|
||||||
<CardDescription>
|
<CardDescription>
|
||||||
Manage all the files and directories in {"'/etc/dokploy/traefik'"}
|
Manage all the files and directories in {"'/etc/dokploy/traefik'"}
|
||||||
.
|
.
|
||||||
</CardDescription>
|
</CardDescription>
|
||||||
|
|
||||||
<AlertBlock type="warning">
|
<AlertBlock type="warning">
|
||||||
Adding invalid configuration to existing files, can break your
|
Adding invalid configuration to existing files, can break your
|
||||||
Traefik instance, preventing access to your applications.
|
Traefik instance, preventing access to your applications.
|
||||||
</AlertBlock>
|
</AlertBlock>
|
||||||
</CardHeader>
|
</CardHeader>
|
||||||
<CardContent className="space-y-2 py-8 border-t">
|
<CardContent className="space-y-2 py-8 border-t">
|
||||||
<div>
|
<div>
|
||||||
<div className="flex flex-col lg:flex-row gap-4 md:gap-10 w-full">
|
<div className="flex flex-col lg:flex-row gap-4 md:gap-10 w-full">
|
||||||
{isError && (
|
{isError && (
|
||||||
<AlertBlock type="error" className="w-full">
|
<AlertBlock type="error" className="w-full">
|
||||||
{error?.message}
|
{error?.message}
|
||||||
</AlertBlock>
|
</AlertBlock>
|
||||||
)}
|
)}
|
||||||
{isLoading && (
|
{isLoading && (
|
||||||
<div className="w-full flex-col gap-2 flex items-center justify-center h-[55vh]">
|
<div className="w-full flex-col gap-2 flex items-center justify-center h-[55vh]">
|
||||||
<span className="text-muted-foreground text-lg font-medium">
|
<span className="text-muted-foreground text-lg font-medium">
|
||||||
Loading...
|
Loading...
|
||||||
</span>
|
</span>
|
||||||
<Loader2 className="animate-spin size-8 text-muted-foreground" />
|
<Loader2 className="animate-spin size-8 text-muted-foreground" />
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
{directories?.length === 0 && (
|
{directories?.length === 0 && (
|
||||||
<div className="w-full flex-col gap-2 flex items-center justify-center h-[55vh]">
|
<div className="w-full flex-col gap-2 flex items-center justify-center h-[55vh]">
|
||||||
<span className="text-muted-foreground text-lg font-medium">
|
<span className="text-muted-foreground text-lg font-medium">
|
||||||
No directories or files detected in{" "}
|
No directories or files detected in{" "}
|
||||||
{"'/etc/dokploy/traefik'"}
|
{"'/etc/dokploy/traefik'"}
|
||||||
</span>
|
</span>
|
||||||
<Folder className="size-8 text-muted-foreground" />
|
<Folder className="size-8 text-muted-foreground" />
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
{directories && directories?.length > 0 && (
|
{directories && directories?.length > 0 && (
|
||||||
<>
|
<>
|
||||||
<Tree
|
<Tree
|
||||||
data={directories}
|
data={directories}
|
||||||
className="lg:max-w-[19rem] w-full lg:h-[660px] border rounded-lg"
|
className="lg:max-w-[19rem] w-full lg:h-[660px] border rounded-lg"
|
||||||
onSelectChange={(item) => setFile(item?.id || null)}
|
onSelectChange={(item) => setFile(item?.id || null)}
|
||||||
folderIcon={Folder}
|
folderIcon={Folder}
|
||||||
itemIcon={Workflow}
|
itemIcon={Workflow}
|
||||||
/>
|
/>
|
||||||
<div className="w-full">
|
<div className="w-full">
|
||||||
{file ? (
|
{file ? (
|
||||||
<ShowTraefikFile path={file} serverId={serverId} />
|
<ShowTraefikFile path={file} serverId={serverId} />
|
||||||
) : (
|
) : (
|
||||||
<div className="h-full w-full flex-col gap-2 flex items-center justify-center">
|
<div className="h-full w-full flex-col gap-2 flex items-center justify-center">
|
||||||
<span className="text-muted-foreground text-lg font-medium">
|
<span className="text-muted-foreground text-lg font-medium">
|
||||||
No file selected
|
No file selected
|
||||||
</span>
|
</span>
|
||||||
<FileIcon className="size-8 text-muted-foreground" />
|
<FileIcon className="size-8 text-muted-foreground" />
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
</>
|
</>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</CardContent>
|
</CardContent>
|
||||||
</div>
|
</div>
|
||||||
</Card>
|
</Card>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -3,7 +3,7 @@ import { DockerMonitoring } from "../docker/show";
|
|||||||
|
|
||||||
export const ShowMonitoring = () => {
|
export const ShowMonitoring = () => {
|
||||||
return (
|
return (
|
||||||
<div className="my-6 w-full ">
|
<div className="w-full">
|
||||||
<DockerMonitoring appName="dokploy" />
|
<DockerMonitoring appName="dokploy" />
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -75,7 +75,7 @@ export const ShowProjects = () => {
|
|||||||
list={[{ name: "Projects", href: "/dashboard/projects" }]}
|
list={[{ name: "Projects", href: "/dashboard/projects" }]}
|
||||||
/>
|
/>
|
||||||
<div className="w-full">
|
<div className="w-full">
|
||||||
<Card className="h-full bg-sidebar p-2.5 rounded-xl ">
|
<Card className="h-full bg-sidebar p-2.5 rounded-xl ">
|
||||||
<div className="rounded-xl bg-background shadow-md ">
|
<div className="rounded-xl bg-background shadow-md ">
|
||||||
<div className="flex justify-between gap-4 w-full items-center">
|
<div className="flex justify-between gap-4 w-full items-center">
|
||||||
<CardHeader className="">
|
<CardHeader className="">
|
||||||
|
|||||||
@@ -70,7 +70,7 @@ export default function SwarmMonitorCard({ serverId }: Props) {
|
|||||||
);
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Card className="h-full bg-sidebar p-2.5 rounded-xl max-w-8xl mx-auto w-full">
|
<Card className="h-full bg-sidebar p-2.5 rounded-xl mx-auto w-full">
|
||||||
<div className="rounded-xl bg-background shadow-md p-6 flex flex-col gap-4">
|
<div className="rounded-xl bg-background shadow-md p-6 flex flex-col gap-4">
|
||||||
<header className="flex items-center justify-between">
|
<header className="flex items-center justify-between">
|
||||||
<div className="space-y-1">
|
<div className="space-y-1">
|
||||||
@@ -94,7 +94,7 @@ export default function SwarmMonitorCard({ serverId }: Props) {
|
|||||||
)}
|
)}
|
||||||
</header>
|
</header>
|
||||||
|
|
||||||
<div className="grid gap-6 md:grid-cols-3">
|
<div className="grid gap-6 lg:grid-cols-3">
|
||||||
<Card className="bg-background">
|
<Card className="bg-background">
|
||||||
<CardHeader className="flex flex-row items-center justify-between space-y-0 pb-2">
|
<CardHeader className="flex flex-row items-center justify-between space-y-0 pb-2">
|
||||||
<CardTitle className="text-sm font-medium">Total Nodes</CardTitle>
|
<CardTitle className="text-sm font-medium">Total Nodes</CardTitle>
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ import {
|
|||||||
BlocksIcon,
|
BlocksIcon,
|
||||||
BookIcon,
|
BookIcon,
|
||||||
ChevronRight,
|
ChevronRight,
|
||||||
|
CircleHelp,
|
||||||
Command,
|
Command,
|
||||||
CreditCard,
|
CreditCard,
|
||||||
Database,
|
Database,
|
||||||
@@ -127,7 +128,7 @@ const data = {
|
|||||||
isActive: false,
|
isActive: false,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: "File System",
|
title: "Traefik File System",
|
||||||
url: "/dashboard/traefik",
|
url: "/dashboard/traefik",
|
||||||
icon: GalleryVerticalEnd,
|
icon: GalleryVerticalEnd,
|
||||||
isSingle: true,
|
isSingle: true,
|
||||||
@@ -317,9 +318,15 @@ const data = {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "Support",
|
name: "Support",
|
||||||
|
url: "https://discord.gg/2tBnJ3jDJc",
|
||||||
|
icon: CircleHelp,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "Sponsor",
|
||||||
url: "https://opencollective.com/dokploy",
|
url: "https://opencollective.com/dokploy",
|
||||||
icon: Heart,
|
icon: Heart,
|
||||||
},
|
},
|
||||||
|
|
||||||
// {
|
// {
|
||||||
// name: "Sales & Marketing",
|
// name: "Sales & Marketing",
|
||||||
// url: "#",
|
// url: "#",
|
||||||
|
|||||||
@@ -26,7 +26,7 @@ const Page = () => {
|
|||||||
const { data: isCloud } = api.settings.isCloud.useQuery();
|
const { data: isCloud } = api.settings.isCloud.useQuery();
|
||||||
return (
|
return (
|
||||||
<div className="w-full">
|
<div className="w-full">
|
||||||
<div className="h-full p-2.5 rounded-xl max-w-5xl mx-auto flex flex-col gap-4">
|
<div className="h-full rounded-xl max-w-5xl mx-auto flex flex-col gap-4">
|
||||||
<ProfileForm />
|
<ProfileForm />
|
||||||
{(user?.canAccessToAPI || data?.rol === "admin") && <GenerateToken />}
|
{(user?.canAccessToAPI || data?.rol === "admin") && <GenerateToken />}
|
||||||
|
|
||||||
|
|||||||
@@ -13,7 +13,7 @@ import superjson from "superjson";
|
|||||||
const Page = () => {
|
const Page = () => {
|
||||||
return (
|
return (
|
||||||
<div className="w-full">
|
<div className="w-full">
|
||||||
<div className="h-full p-2.5 rounded-xl max-w-5xl mx-auto flex flex-col gap-4">
|
<div className="h-full rounded-xl max-w-5xl mx-auto flex flex-col gap-4">
|
||||||
<WebDomain />
|
<WebDomain />
|
||||||
<WebServer />
|
<WebServer />
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
Reference in New Issue
Block a user