Redeploy
This commit is contained in:
@@ -10,13 +10,14 @@ import {
|
|||||||
} from "@/components/ui/card";
|
} from "@/components/ui/card";
|
||||||
import { Badge } from "@/components/ui/badge";
|
import { Badge } from "@/components/ui/badge";
|
||||||
import { Button } from "@/components/ui/button";
|
import { Button } from "@/components/ui/button";
|
||||||
import { Plus, Play, Pause, Square } from "lucide-react";
|
import { Plus, Play, Pause, Square, RotateCcw } from "lucide-react";
|
||||||
import { getDeployments, toggleDeployment } from "@/lib/dockship/deploy";
|
import { getDeployments, toggleDeployment } from "@/lib/dockship/deploy";
|
||||||
import { getApps } from "@/lib/dockship/application";
|
import { getApps } from "@/lib/dockship/application";
|
||||||
import { cn } from "@/lib/utils";
|
import { cn } from "@/lib/utils";
|
||||||
import DeployAppDialog from "@/components/dialogs/DeployApp";
|
import DeployAppDialog from "@/components/dialogs/DeployApp";
|
||||||
import { useAsync, useAsyncInterval } from "@/hooks/use-async";
|
import { useAsync, useAsyncInterval } from "@/hooks/use-async";
|
||||||
import RemoveDialog from "@/components/dialogs/Remove";
|
import RemoveDialog from "@/components/dialogs/Remove";
|
||||||
|
import { Application } from "@/lib/types";
|
||||||
|
|
||||||
const statusDot = {
|
const statusDot = {
|
||||||
running: "bg-chart-2",
|
running: "bg-chart-2",
|
||||||
@@ -34,11 +35,11 @@ export default function DeploymentsPage() {
|
|||||||
[apps],
|
[apps],
|
||||||
);
|
);
|
||||||
|
|
||||||
const appNameByContainer = useMemo(() => {
|
const appByContainer = useMemo(() => {
|
||||||
const map = new Map<string, string>();
|
const map = new Map<string, Application>();
|
||||||
for (const app of apps) {
|
for (const app of apps) {
|
||||||
for (const container of app.deployments) {
|
for (const container of app.deployments) {
|
||||||
map.set(container, app.name);
|
map.set(container, app);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return map;
|
return map;
|
||||||
@@ -90,7 +91,8 @@ export default function DeploymentsPage() {
|
|||||||
<CardTitle>
|
<CardTitle>
|
||||||
{dep.name} @{" "}
|
{dep.name} @{" "}
|
||||||
<span className="text-primary-foreground">
|
<span className="text-primary-foreground">
|
||||||
{appNameByContainer.get(dep.container) ?? "Unknown app"}
|
{appByContainer.get(dep.container)?.name ??
|
||||||
|
"Unknown app"}
|
||||||
</span>
|
</span>
|
||||||
</CardTitle>
|
</CardTitle>
|
||||||
<CardDescription className="flex gap-3">
|
<CardDescription className="flex gap-3">
|
||||||
@@ -123,6 +125,19 @@ export default function DeploymentsPage() {
|
|||||||
<Square className="w-3 h-3 text-primary" />
|
<Square className="w-3 h-3 text-primary" />
|
||||||
)}
|
)}
|
||||||
</Button>
|
</Button>
|
||||||
|
<DeployAppDialog
|
||||||
|
defaultApp={appByContainer.get(dep.container)?.id}
|
||||||
|
ports={dep.ports.map(([to, from]) => ({
|
||||||
|
containerPort: from.toString(),
|
||||||
|
hostPort: to.toString(),
|
||||||
|
protocol: "tcp",
|
||||||
|
}))}
|
||||||
|
nodeId={dep.nodeId}
|
||||||
|
>
|
||||||
|
<Button variant="ghost" size="icon-sm">
|
||||||
|
<RotateCcw className="w-3 h-3" />
|
||||||
|
</Button>
|
||||||
|
</DeployAppDialog>
|
||||||
<RemoveDialog remove={() => {}} />
|
<RemoveDialog remove={() => {}} />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -24,17 +24,21 @@ import { Plus } from "lucide-react";
|
|||||||
export default function DeployAppDialog({
|
export default function DeployAppDialog({
|
||||||
defaultApp,
|
defaultApp,
|
||||||
children,
|
children,
|
||||||
|
ports: initialPorts,
|
||||||
|
nodeId: defaultNode,
|
||||||
}: {
|
}: {
|
||||||
defaultApp?: string;
|
defaultApp?: string;
|
||||||
|
nodeId?: string;
|
||||||
|
ports?: Port[];
|
||||||
children: ReactNode;
|
children: ReactNode;
|
||||||
}) {
|
}) {
|
||||||
const { value: nodes } = useAsync("liveNodes", [], getLiveNodes);
|
const { value: nodes } = useAsync("liveNodes", [], getLiveNodes);
|
||||||
const { value: apps } = useAsync<Application[]>("apps", [], getApps);
|
const { value: apps } = useAsync<Application[]>("apps", [], getApps);
|
||||||
const [name, setName] = useState("");
|
const [name, setName] = useState("");
|
||||||
const [app, setApp] = useState(defaultApp || "");
|
const [app, setApp] = useState(defaultApp || "");
|
||||||
const [node, setNode] = useState("");
|
const [node, setNode] = useState(defaultNode || "");
|
||||||
|
|
||||||
const [ports, setPorts] = useState<Port[]>([]);
|
const [ports, setPorts] = useState<Port[]>(initialPorts || []);
|
||||||
const [newPort, setNewPort] = useState<Port>({
|
const [newPort, setNewPort] = useState<Port>({
|
||||||
containerPort: "",
|
containerPort: "",
|
||||||
hostPort: "",
|
hostPort: "",
|
||||||
|
|||||||
@@ -5,7 +5,9 @@ import { getNodes } from "./node";
|
|||||||
import axios from "axios";
|
import axios from "axios";
|
||||||
import { editApp, getApp, getApps } from "./application";
|
import { editApp, getApp, getApps } from "./application";
|
||||||
|
|
||||||
export async function getDeployments(): Promise<Deployment[]> {
|
export async function getDeployments(): Promise<
|
||||||
|
(Deployment & { nodeId: string })[]
|
||||||
|
> {
|
||||||
const nodes = await getNodes();
|
const nodes = await getNodes();
|
||||||
const apps = await getApps();
|
const apps = await getApps();
|
||||||
|
|
||||||
@@ -17,7 +19,7 @@ export async function getDeployments(): Promise<Deployment[]> {
|
|||||||
await axios.post(`http://${n.ip}:3000/api/get-deployments`, apps, {
|
await axios.post(`http://${n.ip}:3000/api/get-deployments`, apps, {
|
||||||
headers: { Authorization: `ApiKey ${n.key}` },
|
headers: { Authorization: `ApiKey ${n.key}` },
|
||||||
})
|
})
|
||||||
).data.deployments,
|
).data.deployments.map((d: any) => ({ ...d, nodeId: n.node_id })),
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
).flat();
|
).flat();
|
||||||
|
|||||||
Reference in New Issue
Block a user