Skip to content

Commit 17843ae

Browse files
committed
add policy metadata
1 parent dc1258e commit 17843ae

File tree

8 files changed

+390
-258
lines changed

8 files changed

+390
-258
lines changed

apps/web/app/routes/ws/deployments/_components/VersionActionsPanel.tsx

Lines changed: 165 additions & 172 deletions
Original file line numberDiff line numberDiff line change
@@ -1,192 +1,185 @@
1-
import { AlertCircle, Check, CheckCircle, Shield, XCircle } from "lucide-react";
1+
import type { RouterOutputs } from "@ctrlplane/trpc";
22

3-
import type { DeploymentVersion, Environment, ReleaseTarget } from "./types";
4-
import { Badge } from "~/components/ui/badge";
3+
import type { Environment } from "./types";
54
import {
65
Dialog,
76
DialogContent,
87
DialogDescription,
98
DialogHeader,
109
DialogTitle,
1110
} from "~/components/ui/dialog";
12-
import {
13-
Tooltip,
14-
TooltipContent,
15-
TooltipTrigger,
16-
} from "~/components/ui/tooltip";
1711

1812
type VersionActionsPanelProps = {
19-
version: DeploymentVersion;
13+
version: NonNullable<
14+
NonNullable<RouterOutputs["deployment"]["versions"]>["items"]
15+
>[number];
2016
environments: Environment[];
21-
releaseTargets: ReleaseTarget[];
2217
open: boolean;
2318
onOpenChange: (open: boolean) => void;
2419
};
2520

26-
type EnvironmentDeploymentStatus = {
27-
env: Environment;
28-
onVersion: number; // Number of release targets currently on this version
29-
total: number; // Total release targets in environment
30-
cannotDeployReasons: Array<{ reason: string; count: number }>; // Reasons why some can't deploy
31-
};
32-
33-
const EnvironmentRow: React.FC<EnvironmentDeploymentStatus> = ({
34-
env,
35-
onVersion,
36-
total,
37-
cannotDeployReasons,
38-
}) => {
39-
const isFullyDeployed = onVersion === total && total > 0;
40-
const isPartiallyDeployed = onVersion > 0 && onVersion < total;
41-
const isNotDeployed = onVersion === 0;
42-
const hasBlockedResources = cannotDeployReasons.length > 0;
43-
44-
return (
45-
<div className="rounded border p-2.5">
46-
<div className="flex items-start justify-between">
47-
<div className="flex-1">
48-
<div className="mb-1 flex items-center gap-2">
49-
<span className="text-sm font-medium">{env.name}</span>
50-
{isFullyDeployed && (
51-
<Badge className="border-green-500/20 bg-green-500/10 py-0 text-[10px] text-green-600">
52-
<CheckCircle className="mr-0.5 h-2.5 w-2.5" />
53-
Fully Deployed
54-
</Badge>
55-
)}
56-
</div>
57-
58-
<div className="mb-2 flex items-baseline gap-1.5">
59-
<span className="text-lg font-semibold">
60-
{onVersion}
61-
<span className="text-muted-foreground">/{total}</span>
62-
</span>
63-
<span className="text-xs text-muted-foreground">
64-
resource{total !== 1 ? "s" : ""} on this version
65-
</span>
66-
</div>
67-
68-
{/* Status Messages */}
69-
<div className="space-y-1">
70-
{isFullyDeployed && (
71-
<div className="flex items-center gap-1.5 text-xs text-green-600">
72-
<Check className="h-3 w-3" />
73-
All resources deployed successfully
74-
</div>
75-
)}
76-
77-
{isPartiallyDeployed && !hasBlockedResources && (
78-
<div className="flex items-center gap-1.5 text-xs text-blue-600">
79-
<AlertCircle className="h-3 w-3" />
80-
Can deploy to {total - onVersion} more resource
81-
{total - onVersion !== 1 ? "s" : ""}
82-
</div>
83-
)}
84-
85-
{isNotDeployed && !hasBlockedResources && (
86-
<div className="flex items-center gap-1.5 text-xs text-muted-foreground">
87-
<AlertCircle className="h-3 w-3" />
88-
Not yet deployed to this environment
89-
</div>
90-
)}
91-
92-
{hasBlockedResources && (
93-
<div className="space-y-1">
94-
{cannotDeployReasons.map((reason, idx) => (
95-
<Tooltip key={idx}>
96-
<TooltipTrigger asChild>
97-
<div className="flex items-center gap-1.5 text-xs text-amber-600">
98-
<Shield className="h-3 w-3" />
99-
<span>
100-
{reason.count} resource{reason.count !== 1 ? "s" : ""}{" "}
101-
blocked: {reason.reason}
102-
</span>
103-
</div>
104-
</TooltipTrigger>
105-
<TooltipContent side="left" className="max-w-sm">
106-
<div className="text-[11px]">
107-
{reason.reason} - preventing deployment to{" "}
108-
{reason.count} resource{reason.count !== 1 ? "s" : ""}
109-
</div>
110-
</TooltipContent>
111-
</Tooltip>
112-
))}
113-
</div>
114-
)}
115-
</div>
116-
</div>
117-
118-
{/* Status Icon */}
119-
<div className="ml-2 flex items-center">
120-
{isFullyDeployed ? (
121-
<CheckCircle className="h-5 w-5 text-green-600" />
122-
) : hasBlockedResources && onVersion === 0 ? (
123-
<XCircle className="h-5 w-5 text-amber-600" />
124-
) : (
125-
<AlertCircle className="h-5 w-5 text-blue-600" />
126-
)}
127-
</div>
128-
</div>
129-
</div>
130-
);
131-
};
21+
// type EnvironmentDeploymentStatus = {
22+
// env: Environment;
23+
// onVersion: number; // Number of release targets currently on this version
24+
// total: number; // Total release targets in environment
25+
// cannotDeployReasons: Array<{ reason: string; count: number }>; // Reasons why some can't deploy
26+
// };
27+
28+
// const EnvironmentRow: React.FC<EnvironmentDeploymentStatus> = ({
29+
// env,
30+
// onVersion,
31+
// total,
32+
// cannotDeployReasons,
33+
// }) => {
34+
// const isFullyDeployed = onVersion === total && total > 0;
35+
// const isPartiallyDeployed = onVersion > 0 && onVersion < total;
36+
// const isNotDeployed = onVersion === 0;
37+
// const hasBlockedResources = cannotDeployReasons.length > 0;
38+
39+
// return (
40+
// <div className="rounded border p-2.5">
41+
// <div className="flex items-start justify-between">
42+
// <div className="flex-1">
43+
// <div className="mb-1 flex items-center gap-2">
44+
// <span className="text-sm font-medium">{env.name}</span>
45+
// {isFullyDeployed && (
46+
// <Badge className="border-green-500/20 bg-green-500/10 py-0 text-[10px] text-green-600">
47+
// <CheckCircle className="mr-0.5 h-2.5 w-2.5" />
48+
// Fully Deployed
49+
// </Badge>
50+
// )}
51+
// </div>
52+
53+
// <div className="mb-2 flex items-baseline gap-1.5">
54+
// <span className="text-lg font-semibold">
55+
// {onVersion}
56+
// <span className="text-muted-foreground">/{total}</span>
57+
// </span>
58+
// <span className="text-xs text-muted-foreground">
59+
// resource{total !== 1 ? "s" : ""} on this version
60+
// </span>
61+
// </div>
62+
63+
// {/* Status Messages */}
64+
// <div className="space-y-1">
65+
// {isFullyDeployed && (
66+
// <div className="flex items-center gap-1.5 text-xs text-green-600">
67+
// <Check className="h-3 w-3" />
68+
// All resources deployed successfully
69+
// </div>
70+
// )}
71+
72+
// {isPartiallyDeployed && !hasBlockedResources && (
73+
// <div className="flex items-center gap-1.5 text-xs text-blue-600">
74+
// <AlertCircle className="h-3 w-3" />
75+
// Can deploy to {total - onVersion} more resource
76+
// {total - onVersion !== 1 ? "s" : ""}
77+
// </div>
78+
// )}
79+
80+
// {isNotDeployed && !hasBlockedResources && (
81+
// <div className="flex items-center gap-1.5 text-xs text-muted-foreground">
82+
// <AlertCircle className="h-3 w-3" />
83+
// Not yet deployed to this environment
84+
// </div>
85+
// )}
86+
87+
// {hasBlockedResources && (
88+
// <div className="space-y-1">
89+
// {cannotDeployReasons.map((reason, idx) => (
90+
// <Tooltip key={idx}>
91+
// <TooltipTrigger asChild>
92+
// <div className="flex items-center gap-1.5 text-xs text-amber-600">
93+
// <Shield className="h-3 w-3" />
94+
// <span>
95+
// {reason.count} resource{reason.count !== 1 ? "s" : ""}{" "}
96+
// blocked: {reason.reason}
97+
// </span>
98+
// </div>
99+
// </TooltipTrigger>
100+
// <TooltipContent side="left" className="max-w-sm">
101+
// <div className="text-[11px]">
102+
// {reason.reason} - preventing deployment to{" "}
103+
// {reason.count} resource{reason.count !== 1 ? "s" : ""}
104+
// </div>
105+
// </TooltipContent>
106+
// </Tooltip>
107+
// ))}
108+
// </div>
109+
// )}
110+
// </div>
111+
// </div>
112+
113+
// {/* Status Icon */}
114+
// <div className="ml-2 flex items-center">
115+
// {isFullyDeployed ? (
116+
// <CheckCircle className="h-5 w-5 text-green-600" />
117+
// ) : hasBlockedResources && onVersion === 0 ? (
118+
// <XCircle className="h-5 w-5 text-amber-600" />
119+
// ) : (
120+
// <AlertCircle className="h-5 w-5 text-blue-600" />
121+
// )}
122+
// </div>
123+
// </div>
124+
// </div>
125+
// );
126+
// };
132127

133128
export const VersionActionsPanel: React.FC<VersionActionsPanelProps> = ({
134129
version,
135-
environments,
136-
releaseTargets,
137130
open,
138131
onOpenChange,
139132
}) => {
140-
// Calculate deployment status for each environment
141-
const environmentStatuses: EnvironmentDeploymentStatus[] = environments.map(
142-
(env) => {
143-
const envReleaseTargets = releaseTargets.filter(
144-
(rt) => rt.environment.id === env.id,
145-
);
146-
const total = envReleaseTargets.length;
147-
148-
// Count how many are currently on this version
149-
const onVersion = envReleaseTargets.filter(
150-
(rt) => rt.version.currentId === version.id,
151-
).length;
152-
153-
// Find resources that cannot deploy this version and why
154-
const blockReasonsMap = new Map<string, number>();
155-
envReleaseTargets.forEach((rt) => {
156-
const blockForVersion = rt.version.blockedVersions?.find(
157-
(bv) => bv.versionId === version.id,
158-
);
159-
if (blockForVersion) {
160-
const currentCount = blockReasonsMap.get(blockForVersion.reason) ?? 0;
161-
blockReasonsMap.set(blockForVersion.reason, currentCount + 1);
162-
}
163-
});
164-
165-
const cannotDeployReasons = Array.from(blockReasonsMap.entries()).map(
166-
([reason, count]) => ({
167-
reason,
168-
count,
169-
}),
170-
);
171-
172-
return {
173-
env,
174-
onVersion,
175-
total,
176-
cannotDeployReasons,
177-
};
178-
},
179-
);
180-
181-
// Calculate summary stats
182-
const totalResources = environmentStatuses.reduce(
183-
(sum, e) => sum + e.total,
184-
0,
185-
);
186-
const totalOnVersion = environmentStatuses.reduce(
187-
(sum, e) => sum + e.onVersion,
188-
0,
189-
);
133+
// // Calculate deployment status for each environment
134+
// const environmentStatuses: EnvironmentDeploymentStatus[] = environments.map(
135+
// (env) => {
136+
// const envReleaseTargets = releaseTargets.filter(
137+
// (rt) => rt.environment.id === env.id,
138+
// );
139+
// const total = envReleaseTargets.length;
140+
141+
// // Count how many are currently on this version
142+
// const onVersion = envReleaseTargets.filter(
143+
// (rt) => rt.state.currentRelease.version.id === version.id,
144+
// ).length;
145+
146+
// // Find resources that cannot deploy this version and why
147+
// const blockReasonsMap = new Map<string, number>();
148+
// // envReleaseTargets.forEach((rt) => {
149+
// // const blockForVersion = rt.state.desiredRelease.blockedVersions?.find(
150+
// // (bv) => bv.versionId === version.id,
151+
// // );
152+
// // if (blockForVersion) {
153+
// // const currentCount = blockReasonsMap.get(blockForVersion.reason) ?? 0;
154+
// // blockReasonsMap.set(blockForVersion.reason, currentCount + 1);
155+
// // }
156+
// // });
157+
158+
// const cannotDeployReasons = Array.from(blockReasonsMap.entries()).map(
159+
// ([reason, count]) => ({
160+
// reason,
161+
// count,
162+
// }),
163+
// );
164+
165+
// return {
166+
// env,
167+
// onVersion,
168+
// total,
169+
// cannotDeployReasons,
170+
// };
171+
// },
172+
// );
173+
174+
// // Calculate summary stats
175+
// const totalResources = environmentStatuses.reduce(
176+
// (sum, e) => sum + e.total,
177+
// 0,
178+
// );
179+
// const totalOnVersion = environmentStatuses.reduce(
180+
// (sum, e) => sum + e.onVersion,
181+
// 0,
182+
// );
190183

191184
return (
192185
<Dialog open={open} onOpenChange={onOpenChange}>
@@ -196,17 +189,17 @@ export const VersionActionsPanel: React.FC<VersionActionsPanelProps> = ({
196189
{version.tag}
197190
</DialogTitle>
198191
<DialogDescription className="text-[10px]">
199-
Deployed to {totalOnVersion} of {totalResources} total resources
200-
across all environments
192+
{/* Deployed to {totalOnVersion} of {totalResources} total resources
193+
across all environments */}
201194
</DialogDescription>
202195
</DialogHeader>
203196

204197
{/* Scrollable Content */}
205198
<div className="max-h-[calc(85vh-120px)] overflow-y-auto px-4 pb-4">
206199
<div className="space-y-2.5 pt-4">
207-
{environmentStatuses.map((status) => (
200+
{/* {environmentStatuses.map((status) => (
208201
<EnvironmentRow key={status.env.id} {...status} />
209-
))}
202+
))} */}
210203
</div>
211204
</div>
212205
</DialogContent>

0 commit comments

Comments
 (0)