@kuadrant/kuadrant-backstage-plugin-frontend 0.0.2-dev-d2ba42b → 0.0.2-dev-8189c1c

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (111) hide show
  1. package/dist/api.esm.js +236 -0
  2. package/dist/api.esm.js.map +1 -0
  3. package/dist/apis.esm.js +15 -0
  4. package/dist/apis.esm.js.map +1 -0
  5. package/dist/components/ApiAccessCard/ApiAccessCard.esm.js +25 -36
  6. package/dist/components/ApiAccessCard/ApiAccessCard.esm.js.map +1 -1
  7. package/dist/components/ApiKeyDetailPage/ApiKeyDetailPage.esm.js +24 -36
  8. package/dist/components/ApiKeyDetailPage/ApiKeyDetailPage.esm.js.map +1 -1
  9. package/dist/components/ApiKeyManagementTab/ApiKeyManagementTab.esm.js +20 -46
  10. package/dist/components/ApiKeyManagementTab/ApiKeyManagementTab.esm.js.map +1 -1
  11. package/dist/components/ApiProductDetailPage/ApiProductDetailPage.esm.js +9 -43
  12. package/dist/components/ApiProductDetailPage/ApiProductDetailPage.esm.js.map +1 -1
  13. package/dist/components/ApiProductDetails/ApiProductDetails.esm.js.map +1 -1
  14. package/dist/components/ApiProductInfoCard/ApiProductInfoCard.esm.js +5 -13
  15. package/dist/components/ApiProductInfoCard/ApiProductInfoCard.esm.js.map +1 -1
  16. package/dist/components/ApiProductOpenApiAlert/ApiProductOpenApiAlert.esm.js +7 -10
  17. package/dist/components/ApiProductOpenApiAlert/ApiProductOpenApiAlert.esm.js.map +1 -1
  18. package/dist/components/ApiProductPolicies/ApiProductPolicies.esm.js +113 -0
  19. package/dist/components/ApiProductPolicies/ApiProductPolicies.esm.js.map +1 -0
  20. package/dist/components/ApprovalQueueTable/ApprovalQueueTable.esm.js +32 -64
  21. package/dist/components/ApprovalQueueTable/ApprovalQueueTable.esm.js.map +1 -1
  22. package/dist/components/CreateAPIProductDialog/CreateAPIProductDialog.esm.js +85 -63
  23. package/dist/components/CreateAPIProductDialog/CreateAPIProductDialog.esm.js.map +1 -1
  24. package/dist/components/EditAPIKeyDialog/EditAPIKeyDialog.esm.js +8 -18
  25. package/dist/components/EditAPIKeyDialog/EditAPIKeyDialog.esm.js.map +1 -1
  26. package/dist/components/EditAPIProductDialog/EditAPIProductDialog.esm.js +56 -35
  27. package/dist/components/EditAPIProductDialog/EditAPIProductDialog.esm.js.map +1 -1
  28. package/dist/components/EntityApiApprovalTab/EntityApiApprovalTab.esm.js +9 -25
  29. package/dist/components/EntityApiApprovalTab/EntityApiApprovalTab.esm.js.map +1 -1
  30. package/dist/components/KuadrantPage/ApiProductsPage.esm.js +20 -54
  31. package/dist/components/KuadrantPage/ApiProductsPage.esm.js.map +1 -1
  32. package/dist/components/MyApiKeysTable/MyApiKeysTable.esm.js +25 -52
  33. package/dist/components/MyApiKeysTable/MyApiKeysTable.esm.js.map +1 -1
  34. package/dist/components/RequestAccessDialog/RequestAccessDialog.esm.js +10 -25
  35. package/dist/components/RequestAccessDialog/RequestAccessDialog.esm.js.map +1 -1
  36. package/dist/index.d.ts +510 -1
  37. package/dist/index.esm.js +3 -1
  38. package/dist/index.esm.js.map +1 -1
  39. package/dist/permissions.esm.js +12 -2
  40. package/dist/permissions.esm.js.map +1 -1
  41. package/dist/utils/policies.esm.js +11 -0
  42. package/dist/utils/policies.esm.js.map +1 -0
  43. package/dist-scalprum/internal.plugin-kuadrant.1ed3b3b414caa08ac5be.js +2 -0
  44. package/dist-scalprum/internal.plugin-kuadrant.1ed3b3b414caa08ac5be.js.map +1 -0
  45. package/dist-scalprum/plugin-manifest.json +3 -3
  46. package/dist-scalprum/static/2967.17aec2fb.chunk.js +2 -0
  47. package/dist-scalprum/static/2967.17aec2fb.chunk.js.map +1 -0
  48. package/dist-scalprum/static/{3947.ff1c25cf.chunk.js → 3947.ad129ba4.chunk.js} +1 -1
  49. package/dist-scalprum/static/{3947.ff1c25cf.chunk.js.map → 3947.ad129ba4.chunk.js.map} +1 -1
  50. package/dist-scalprum/static/3976.c8138b52.chunk.js +2 -0
  51. package/dist-scalprum/static/3976.c8138b52.chunk.js.map +1 -0
  52. package/dist-scalprum/static/4447.d924bc59.chunk.js +2 -0
  53. package/dist-scalprum/static/4447.d924bc59.chunk.js.map +1 -0
  54. package/dist-scalprum/static/5203.11ef2211.chunk.js +2 -0
  55. package/dist-scalprum/static/5203.11ef2211.chunk.js.map +1 -0
  56. package/dist-scalprum/static/6371.d849c508.chunk.js +2 -0
  57. package/dist-scalprum/static/6371.d849c508.chunk.js.map +1 -0
  58. package/dist-scalprum/static/6387.79be6155.chunk.js +2 -0
  59. package/dist-scalprum/static/6387.79be6155.chunk.js.map +1 -0
  60. package/dist-scalprum/static/6800.6faeb7c6.chunk.js +2 -0
  61. package/dist-scalprum/static/6800.6faeb7c6.chunk.js.map +1 -0
  62. package/dist-scalprum/static/69.b6afd1fe.chunk.js +2 -0
  63. package/dist-scalprum/static/69.b6afd1fe.chunk.js.map +1 -0
  64. package/dist-scalprum/static/7005.98c5e400.chunk.js +2 -0
  65. package/dist-scalprum/static/7005.98c5e400.chunk.js.map +1 -0
  66. package/dist-scalprum/static/7270.4a71807b.chunk.js +2 -0
  67. package/dist-scalprum/static/7270.4a71807b.chunk.js.map +1 -0
  68. package/dist-scalprum/static/7791.0a1d55bc.chunk.js +2 -0
  69. package/dist-scalprum/static/7791.0a1d55bc.chunk.js.map +1 -0
  70. package/dist-scalprum/static/8789.2f437443.chunk.js +2 -0
  71. package/dist-scalprum/static/8789.2f437443.chunk.js.map +1 -0
  72. package/dist-scalprum/static/9051.d45ac154.chunk.js +2 -0
  73. package/dist-scalprum/static/9051.d45ac154.chunk.js.map +1 -0
  74. package/dist-scalprum/static/{2946.a35243f1.chunk.js → 9370.2e9fe34b.chunk.js} +3 -3
  75. package/dist-scalprum/static/9370.2e9fe34b.chunk.js.map +1 -0
  76. package/dist-scalprum/static/9838.966ce0a0.chunk.js +2 -0
  77. package/dist-scalprum/static/9838.966ce0a0.chunk.js.map +1 -0
  78. package/dist-scalprum/static/exposed-PluginRoot.3b24e5af.chunk.js +2 -0
  79. package/dist-scalprum/static/{exposed-PluginRoot.8d8f0b09.chunk.js.map → exposed-PluginRoot.3b24e5af.chunk.js.map} +1 -1
  80. package/package.json +3 -1
  81. package/dist/components/PlanPolicyDetailsCard/PlanPolicyDetails.esm.js +0 -48
  82. package/dist/components/PlanPolicyDetailsCard/PlanPolicyDetails.esm.js.map +0 -1
  83. package/dist-scalprum/internal.plugin-kuadrant.eacc31ca4d6c1340f8a8.js +0 -2
  84. package/dist-scalprum/internal.plugin-kuadrant.eacc31ca4d6c1340f8a8.js.map +0 -1
  85. package/dist-scalprum/static/2946.a35243f1.chunk.js.map +0 -1
  86. package/dist-scalprum/static/2967.5bade048.chunk.js +0 -2
  87. package/dist-scalprum/static/2967.5bade048.chunk.js.map +0 -1
  88. package/dist-scalprum/static/3650.89dfc64c.chunk.js +0 -2
  89. package/dist-scalprum/static/3650.89dfc64c.chunk.js.map +0 -1
  90. package/dist-scalprum/static/3976.4cf18515.chunk.js +0 -2
  91. package/dist-scalprum/static/3976.4cf18515.chunk.js.map +0 -1
  92. package/dist-scalprum/static/4447.adbf663f.chunk.js +0 -2
  93. package/dist-scalprum/static/4447.adbf663f.chunk.js.map +0 -1
  94. package/dist-scalprum/static/5203.fce2a28f.chunk.js +0 -2
  95. package/dist-scalprum/static/5203.fce2a28f.chunk.js.map +0 -1
  96. package/dist-scalprum/static/6371.d45f37cc.chunk.js +0 -2
  97. package/dist-scalprum/static/6371.d45f37cc.chunk.js.map +0 -1
  98. package/dist-scalprum/static/6800.cd5c7bcb.chunk.js +0 -2
  99. package/dist-scalprum/static/6800.cd5c7bcb.chunk.js.map +0 -1
  100. package/dist-scalprum/static/7005.72759857.chunk.js +0 -2
  101. package/dist-scalprum/static/7005.72759857.chunk.js.map +0 -1
  102. package/dist-scalprum/static/7270.9473c969.chunk.js +0 -2
  103. package/dist-scalprum/static/7270.9473c969.chunk.js.map +0 -1
  104. package/dist-scalprum/static/7791.01371352.chunk.js +0 -2
  105. package/dist-scalprum/static/7791.01371352.chunk.js.map +0 -1
  106. package/dist-scalprum/static/8789.30227526.chunk.js +0 -2
  107. package/dist-scalprum/static/8789.30227526.chunk.js.map +0 -1
  108. package/dist-scalprum/static/8804.63919453.chunk.js +0 -2
  109. package/dist-scalprum/static/8804.63919453.chunk.js.map +0 -1
  110. package/dist-scalprum/static/exposed-PluginRoot.8d8f0b09.chunk.js +0 -2
  111. /package/dist-scalprum/static/{2946.a35243f1.chunk.js.LICENSE.txt → 9370.2e9fe34b.chunk.js.LICENSE.txt} +0 -0
@@ -2,12 +2,13 @@ import React, { useState, useEffect } from 'react';
2
2
  import { makeStyles, Dialog, DialogTitle, DialogContent, Box, Button, Typography, Grid, TextField, InputAdornment, IconButton, Chip, Tooltip, MenuItem, FormControl, RadioGroup, FormControlLabel, Radio, DialogActions, CircularProgress } from '@material-ui/core';
3
3
  import InfoOutlinedIcon from '@material-ui/icons/InfoOutlined';
4
4
  import AddIcon from '@material-ui/icons/Add';
5
- import { useApi, configApiRef, fetchApiRef } from '@backstage/core-plugin-api';
5
+ import { useApi } from '@backstage/core-plugin-api';
6
+ import { kuadrantApiRef } from '../../api.esm.js';
6
7
  import { Alert } from '@material-ui/lab';
7
8
  import useAsync from 'react-use/lib/useAsync';
8
- import { PlanPolicyDetails } from '../PlanPolicyDetailsCard/PlanPolicyDetails.esm.js';
9
+ import { ApiProductPolicies } from '../ApiProductPolicies/ApiProductPolicies.esm.js';
9
10
  import { validateKubernetesName, validateURL } from '../../utils/validation.esm.js';
10
- import { handleFetchError } from '../../utils/errors.esm.js';
11
+ import { getPolicyForRoute } from '../../utils/policies.esm.js';
11
12
 
12
13
  const useStyles = makeStyles((theme) => ({
13
14
  asterisk: {
@@ -31,9 +32,7 @@ const useStyles = makeStyles((theme) => ({
31
32
  }));
32
33
  const CreateAPIProductDialog = ({ open, onClose, onSuccess }) => {
33
34
  const classes = useStyles();
34
- const config = useApi(configApiRef);
35
- const fetchApi = useApi(fetchApiRef);
36
- const backendUrl = config.getString("backend.baseUrl");
35
+ const kuadrantApi = useApi(kuadrantApiRef);
37
36
  const [name, setName] = useState("");
38
37
  const [displayName, setDisplayName] = useState("");
39
38
  const [description, setDescription] = useState("");
@@ -60,34 +59,67 @@ const CreateAPIProductDialog = ({ open, onClose, onSuccess }) => {
60
59
  loading: httpRoutesLoading,
61
60
  error: httpRoutesError
62
61
  } = useAsync(async () => {
63
- const response = await fetchApi.fetch(`${backendUrl}/api/kuadrant/httproutes`);
64
- if (!response.ok) {
65
- const error2 = await handleFetchError(response);
66
- throw new Error(`failed to fetch routes. ${error2}`);
67
- }
68
- const data = await response.json();
62
+ const data = await kuadrantApi.getHttpRoutes();
69
63
  return data.items || [];
70
- }, [backendUrl, fetchApi, open, httpRoutesRetry]);
64
+ }, [kuadrantApi, open, httpRoutesRetry]);
71
65
  const {
72
66
  value: planPolicies,
73
67
  error: planPoliciesError
74
68
  } = useAsync(async () => {
75
- const response = await fetchApi.fetch(`${backendUrl}/api/kuadrant/planpolicies`);
76
- if (!response.ok) {
77
- const error2 = await handleFetchError(response);
78
- throw new Error(`failed to fetch PlanPolicies. ${error2}`);
79
- }
80
- return await response.json();
81
- }, [backendUrl, fetchApi, open]);
69
+ return await kuadrantApi.getPlanPolicies();
70
+ }, [kuadrantApi, open]);
71
+ const {
72
+ value: authPolicies,
73
+ error: authPoliciesError
74
+ } = useAsync(async () => {
75
+ return await kuadrantApi.getAuthPolicies();
76
+ }, [kuadrantApi, open]);
77
+ const {
78
+ value: rateLimitPolicies,
79
+ error: rateLimitPoliciesError
80
+ } = useAsync(async () => {
81
+ return await kuadrantApi.getRateLimitPolicies();
82
+ }, [kuadrantApi, open]);
82
83
  const getPlanPolicyForRoute = (routeNamespace, routeName) => {
83
- if (!planPolicies?.items) return null;
84
- return planPolicies.items.find((pp) => {
85
- const ref = pp.targetRef;
86
- return ref?.kind === "HTTPRoute" && ref?.name === routeName && (!ref?.namespace || ref?.namespace === routeNamespace);
87
- });
84
+ return getPolicyForRoute(planPolicies?.items, routeNamespace, routeName);
85
+ };
86
+ const getAuthPolicyForRoute = (routeNamespace, routeName) => {
87
+ return getPolicyForRoute(authPolicies?.items, routeNamespace, routeName);
88
+ };
89
+ const getRateLimitPolicyForRoute = (routeNamespace, routeName) => {
90
+ return getPolicyForRoute(rateLimitPolicies?.items, routeNamespace, routeName);
88
91
  };
89
92
  const selectedRouteInfo = selectedHTTPRoute ? selectedHTTPRoute.split("/") : null;
90
- const selectedPolicy = selectedRouteInfo ? getPlanPolicyForRoute(selectedRouteInfo[0], selectedRouteInfo[1]) : null;
93
+ const selectedPlanPolicy = selectedRouteInfo ? getPlanPolicyForRoute(selectedRouteInfo[0], selectedRouteInfo[1]) : null;
94
+ const planPolicyAcceptedCondition = selectedPlanPolicy?.status?.conditions?.find(
95
+ (c) => c.type === "Accepted"
96
+ );
97
+ const selectedAuthPolicy = selectedRouteInfo ? getAuthPolicyForRoute(selectedRouteInfo[0], selectedRouteInfo[1]) : null;
98
+ const authPolicyAcceptedCondition = selectedAuthPolicy?.status?.conditions?.find(
99
+ (c) => c.type === "Accepted"
100
+ );
101
+ const selectedRateLimitPolicy = selectedRouteInfo ? getRateLimitPolicyForRoute(selectedRouteInfo[0], selectedRouteInfo[1]) : null;
102
+ const rateLimitPolicyAcceptedCondition = selectedRateLimitPolicy?.status?.conditions?.find(
103
+ (c) => c.type === "Accepted"
104
+ );
105
+ const planPolicyProps = {
106
+ statusCondition: planPolicyAcceptedCondition,
107
+ discoveredPlans: selectedPlanPolicy?.spec.plans
108
+ };
109
+ const authPolicyProps = {
110
+ namespacedName: {
111
+ namespace: selectedAuthPolicy?.metadata.namespace,
112
+ name: selectedAuthPolicy?.metadata.name
113
+ },
114
+ statusCondition: authPolicyAcceptedCondition
115
+ };
116
+ const rateLimitPolicyProps = {
117
+ namespacedName: {
118
+ namespace: selectedRateLimitPolicy?.metadata.namespace,
119
+ name: selectedRateLimitPolicy?.metadata.name
120
+ },
121
+ statusCondition: rateLimitPolicyAcceptedCondition
122
+ };
91
123
  const formatTierInfo = (policy) => {
92
124
  if (!policy?.spec?.plans) return "";
93
125
  const tiers = Object.entries(policy.spec.plans).map(([name2, plan]) => {
@@ -135,6 +167,26 @@ const CreateAPIProductDialog = ({ open, onClose, onSuccess }) => {
135
167
  const handleDeleteTag = (tagToDelete) => {
136
168
  setTags(tags.filter((tag) => tag !== tagToDelete));
137
169
  };
170
+ const handleClose = () => {
171
+ setName("");
172
+ setDisplayName("");
173
+ setDescription("");
174
+ setVersion("v1");
175
+ setApprovalMode("manual");
176
+ setPublishStatus("Published");
177
+ setLifecycle("production");
178
+ setTags([]);
179
+ setTagInput("");
180
+ setSelectedHTTPRoute("");
181
+ setContactEmail("");
182
+ setContactTeam("");
183
+ setDocsURL("");
184
+ setOpenAPISpec("");
185
+ setError("");
186
+ setNameError(null);
187
+ setOpenAPISpecError(null);
188
+ onClose();
189
+ };
138
190
  const handleCreate = async () => {
139
191
  setError("");
140
192
  setCreating(true);
@@ -181,17 +233,7 @@ const CreateAPIProductDialog = ({ open, onClose, onSuccess }) => {
181
233
  } : {}
182
234
  }
183
235
  };
184
- const response = await fetchApi.fetch(`${backendUrl}/api/kuadrant/apiproducts`, {
185
- method: "POST",
186
- headers: {
187
- "Content-Type": "application/json"
188
- },
189
- body: JSON.stringify(apiProduct)
190
- });
191
- if (!response.ok) {
192
- const error2 = await handleFetchError(response);
193
- throw new Error(`failed to create APIProduct. ${error2}`);
194
- }
236
+ await kuadrantApi.createApiProduct(apiProduct);
195
237
  onSuccess({ namespace, name, displayName });
196
238
  handleClose();
197
239
  } catch (err) {
@@ -200,26 +242,6 @@ const CreateAPIProductDialog = ({ open, onClose, onSuccess }) => {
200
242
  setCreating(false);
201
243
  }
202
244
  };
203
- const handleClose = () => {
204
- setName("");
205
- setDisplayName("");
206
- setDescription("");
207
- setVersion("v1");
208
- setApprovalMode("manual");
209
- setPublishStatus("Published");
210
- setLifecycle("production");
211
- setTags([]);
212
- setTagInput("");
213
- setSelectedHTTPRoute("");
214
- setContactEmail("");
215
- setContactTeam("");
216
- setDocsURL("");
217
- setOpenAPISpec("");
218
- setError("");
219
- setNameError(null);
220
- setOpenAPISpecError(null);
221
- onClose();
222
- };
223
245
  const hasValidationErrors = !!nameError || !!openAPISpecError;
224
246
  return /* @__PURE__ */ React.createElement(Dialog, { open, onClose: handleClose, maxWidth: "md", fullWidth: true }, /* @__PURE__ */ React.createElement(DialogTitle, null, "Create API Product"), /* @__PURE__ */ React.createElement(DialogContent, null, error && /* @__PURE__ */ React.createElement(Alert, { severity: "error", style: { marginBottom: 16 } }, error), httpRoutesError && /* @__PURE__ */ React.createElement(Alert, { severity: "error", style: { marginBottom: 16 } }, /* @__PURE__ */ React.createElement("strong", null, "Failed to load HTTPRoutes:"), " ", httpRoutesError.message, /* @__PURE__ */ React.createElement(Box, { mt: 1 }, /* @__PURE__ */ React.createElement(
225
247
  Button,
@@ -229,7 +251,7 @@ const CreateAPIProductDialog = ({ open, onClose, onSuccess }) => {
229
251
  onClick: () => setHttpRoutesRetry((prev) => prev + 1)
230
252
  },
231
253
  "Retry"
232
- ))), planPoliciesError && /* @__PURE__ */ React.createElement(Alert, { severity: "warning", style: { marginBottom: 16 } }, /* @__PURE__ */ React.createElement("strong", null, "Failed to load PlanPolicies:"), " ", planPoliciesError.message, /* @__PURE__ */ React.createElement(Typography, { variant: "body2", style: { marginTop: 8 } }, "You can still create the API Product, but plan information may be incomplete.")), /* @__PURE__ */ React.createElement(Box, { className: classes.sectionHeader }, /* @__PURE__ */ React.createElement(Typography, { variant: "subtitle1" }, /* @__PURE__ */ React.createElement("strong", null, "API product info"))), /* @__PURE__ */ React.createElement(Grid, { container: true, spacing: 2 }, /* @__PURE__ */ React.createElement(Grid, { item: true, xs: 6 }, /* @__PURE__ */ React.createElement(
254
+ ))), planPoliciesError && /* @__PURE__ */ React.createElement(Alert, { severity: "warning", style: { marginBottom: 16 } }, /* @__PURE__ */ React.createElement("strong", null, "Failed to load PlanPolicies:"), " ", planPoliciesError.message, /* @__PURE__ */ React.createElement(Typography, { variant: "body2", style: { marginTop: 8 } }, "You can still create the API Product, but plan information may be incomplete.")), authPoliciesError && /* @__PURE__ */ React.createElement(Alert, { severity: "warning", style: { marginBottom: 16 } }, /* @__PURE__ */ React.createElement("strong", null, "Failed to load AuthPolicies:"), " ", authPoliciesError.message), rateLimitPoliciesError && /* @__PURE__ */ React.createElement(Alert, { severity: "warning", style: { marginBottom: 16 } }, /* @__PURE__ */ React.createElement("strong", null, "Failed to load RateLimitPolicies:"), " ", rateLimitPoliciesError.message), /* @__PURE__ */ React.createElement(Box, { className: classes.sectionHeader }, /* @__PURE__ */ React.createElement(Typography, { variant: "subtitle1" }, /* @__PURE__ */ React.createElement("strong", null, "API product info"))), /* @__PURE__ */ React.createElement(Grid, { container: true, spacing: 2 }, /* @__PURE__ */ React.createElement(Grid, { item: true, xs: 6 }, /* @__PURE__ */ React.createElement(
233
255
  TextField,
234
256
  {
235
257
  fullWidth: true,
@@ -463,12 +485,12 @@ const CreateAPIProductDialog = ({ open, onClose, onSuccess }) => {
463
485
  /* @__PURE__ */ React.createElement(Box, null, /* @__PURE__ */ React.createElement(Typography, { variant: "body1" }, routeName), /* @__PURE__ */ React.createElement(Typography, { variant: "caption", color: "textSecondary" }, "Associated PlanPolicy: ", policyInfo))
464
486
  );
465
487
  })
466
- ))), selectedHTTPRoute && selectedPolicy && /* @__PURE__ */ React.createElement(React.Fragment, null, /* @__PURE__ */ React.createElement(Box, { className: classes.sectionHeader }, /* @__PURE__ */ React.createElement(Typography, { variant: "subtitle1" }, /* @__PURE__ */ React.createElement("strong", null, "HTTPRoute policies")), /* @__PURE__ */ React.createElement(Tooltip, { title: "Shows the associated policies and rate limit tiers for the selected HTTPRoute" }, /* @__PURE__ */ React.createElement(InfoOutlinedIcon, { className: classes.infoIcon }))), /* @__PURE__ */ React.createElement(
467
- PlanPolicyDetails,
488
+ ))), selectedHTTPRoute && /* @__PURE__ */ React.createElement(React.Fragment, null, /* @__PURE__ */ React.createElement(Box, { className: classes.sectionHeader }, /* @__PURE__ */ React.createElement(Typography, { variant: "subtitle1" }, /* @__PURE__ */ React.createElement("strong", null, "HTTPRoute policies")), /* @__PURE__ */ React.createElement(Tooltip, { title: "Shows the associated policies and rate limit tiers for the selected HTTPRoute" }, /* @__PURE__ */ React.createElement(InfoOutlinedIcon, { className: classes.infoIcon }))), /* @__PURE__ */ React.createElement(
489
+ ApiProductPolicies,
468
490
  {
469
- discoveredPlans: selectedPolicy.plans,
470
- alertSeverity: "warning",
471
- alertMessage: "No PlanPolicy found for this HTTPRoute. API keys and rate limiting may not be available.",
491
+ planPolicy: planPolicyProps,
492
+ authPolicy: authPolicyProps,
493
+ rateLimitPolicy: rateLimitPolicyProps,
472
494
  includeTopMargin: false
473
495
  }
474
496
  )), /* @__PURE__ */ React.createElement(Box, { className: classes.sectionHeader }, /* @__PURE__ */ React.createElement(Typography, { variant: "subtitle1" }, /* @__PURE__ */ React.createElement("strong", null, "Lifecycle and Visibility")), /* @__PURE__ */ React.createElement(Tooltip, { title: "Control the lifecycle state and catalog visibility of this API product" }, /* @__PURE__ */ React.createElement(InfoOutlinedIcon, { className: classes.infoIcon }))), /* @__PURE__ */ React.createElement(Grid, { container: true, spacing: 2 }, /* @__PURE__ */ React.createElement(Grid, { item: true, xs: 6 }, /* @__PURE__ */ React.createElement(
@@ -1 +1 @@
1
- {"version":3,"file":"CreateAPIProductDialog.esm.js","sources":["../../../src/components/CreateAPIProductDialog/CreateAPIProductDialog.tsx"],"sourcesContent":["import React, { useEffect, useState } from 'react';\nimport {\n Dialog,\n DialogTitle,\n DialogContent,\n DialogActions,\n Button,\n TextField,\n Box,\n Typography,\n Chip,\n Grid,\n MenuItem,\n CircularProgress,\n makeStyles,\n FormControl,\n RadioGroup,\n FormControlLabel,\n Radio,\n Tooltip,\n IconButton,\n InputAdornment,\n} from '@material-ui/core';\nimport InfoOutlinedIcon from '@material-ui/icons/InfoOutlined';\nimport AddIcon from '@material-ui/icons/Add';\nimport { useApi, configApiRef, fetchApiRef } from '@backstage/core-plugin-api';\nimport { Alert } from '@material-ui/lab';\nimport useAsync from 'react-use/lib/useAsync';\nimport { PlanPolicyDetails } from '../PlanPolicyDetailsCard';\nimport { validateKubernetesName, validateURL } from '../../utils/validation';\nimport { handleFetchError } from \"../../utils/errors\";\nimport { Lifecycle } from '../../types/api-management';\n\nconst useStyles = makeStyles((theme) => ({\n asterisk: {\n color: '#f44336',\n },\n sectionHeader: {\n display: 'flex',\n alignItems: 'center',\n gap: theme.spacing(0.5),\n marginTop: theme.spacing(2),\n marginBottom: theme.spacing(1),\n },\n infoIcon: {\n fontSize: 18,\n color: theme.palette.text.secondary,\n },\n tagChip: {\n marginRight: theme.spacing(0.5),\n marginBottom: theme.spacing(0.5),\n },\n}));\n\ninterface CreateAPIProductDialogProps {\n open: boolean;\n onClose: () => void;\n onSuccess: (productInfo: { namespace: string; name: string; displayName: string }) => void;\n}\n\nexport const CreateAPIProductDialog = ({ open, onClose, onSuccess }: CreateAPIProductDialogProps) => {\n const classes = useStyles();\n const config = useApi(configApiRef);\n const fetchApi = useApi(fetchApiRef);\n const backendUrl = config.getString('backend.baseUrl');\n\n const [name, setName] = useState('');\n const [displayName, setDisplayName] = useState('');\n const [description, setDescription] = useState('');\n const [version, setVersion] = useState('v1');\n const [approvalMode, setApprovalMode] = useState<'automatic' | 'manual'>('manual');\n const [publishStatus, setPublishStatus] = useState<'Draft' | 'Published'>('Published');\n const [lifecycle, setLifecycle] = useState<Lifecycle>('production');\n const [tags, setTags] = useState<string[]>([]);\n const [tagInput, setTagInput] = useState('');\n const [selectedHTTPRoute, setSelectedHTTPRoute] = useState('');\n const [contactEmail, setContactEmail] = useState('');\n const [contactTeam, setContactTeam] = useState('');\n const [docsURL, setDocsURL] = useState('');\n const [openAPISpec, setOpenAPISpec] = useState('');\n const [error, setError] = useState('');\n const [creating, setCreating] = useState(false);\n const [httpRoutesRetry, setHttpRoutesRetry] = useState(0);\n const [nameError, setNameError] = useState<string | null>(null);\n const [openAPISpecError, setOpenAPISpecError] = useState<string | null>(null);\n const [routeSearchTerm, setRouteSearchTerm] = useState('');\n const [routeSearchField, setRouteSearchField] = useState<'name' | 'namespace' | 'planpolicy'>('name');\n const {\n value: httpRoutes,\n loading: httpRoutesLoading,\n error: httpRoutesError\n } = useAsync(async () => {\n const response = await fetchApi.fetch(`${backendUrl}/api/kuadrant/httproutes`);\n\n if (!response.ok) {\n const error = await handleFetchError(response);\n throw new Error(`failed to fetch routes. ${error}`);\n }\n\n const data = await response.json();\n return data.items || [];\n }, [backendUrl, fetchApi, open, httpRoutesRetry]);\n\n // load planpolicies with full details to show associated plans\n const {\n value: planPolicies,\n error: planPoliciesError\n } = useAsync(async () => {\n const response = await fetchApi.fetch(`${backendUrl}/api/kuadrant/planpolicies`);\n\n if (!response.ok) {\n const error = await handleFetchError(response);\n throw new Error(`failed to fetch PlanPolicies. ${error}`);\n }\n\n return await response.json();\n }, [backendUrl, fetchApi, open]);\n\n // find planpolicy associated with selected httproute\n const getPlanPolicyForRoute = (routeNamespace: string, routeName: string) => {\n if (!planPolicies?.items) return null;\n\n return planPolicies.items.find((pp: any) => {\n const ref = pp.targetRef;\n return (\n ref?.kind === 'HTTPRoute' &&\n ref?.name === routeName &&\n (!ref?.namespace || ref?.namespace === routeNamespace)\n );\n });\n };\n\n const selectedRouteInfo = selectedHTTPRoute ? selectedHTTPRoute.split('/') : null;\n const selectedPolicy = selectedRouteInfo\n ? getPlanPolicyForRoute(selectedRouteInfo[0], selectedRouteInfo[1])\n : null;\n\n // format tier info for dropdown display\n const formatTierInfo = (policy: any): string => {\n if (!policy?.spec?.plans) return '';\n const tiers = Object.entries(policy.spec.plans)\n .map(([name, plan]: [string, any]) => {\n const limit = plan?.limits?.requests;\n if (!limit) return name;\n return `${name}: ${limit.count}/${limit.period}`;\n })\n .join('; ');\n return tiers ? ` (${tiers})` : '';\n };\n\n // get policy info for a route (for dropdown display)\n const getPolicyInfoForRoute = (routeNamespace: string, routeName: string): string => {\n const policy = getPlanPolicyForRoute(routeNamespace, routeName);\n if (!policy) return 'N/A';\n return `${policy.metadata.name}${formatTierInfo(policy)}`;\n };\n\n useEffect(() => {\n if (open) {\n setNameError(null);\n setOpenAPISpecError(null);\n }\n }, [open]);\n\n // validate handlers\n const handleNameChange = (value: string) => {\n setName(value);\n setNameError(validateKubernetesName(value));\n };\n\n const handleDisplayNameChange = (value: string) => {\n setDisplayName(value);\n // Auto-generate Kubernetes resource name from display name with random hex suffix\n if (!name || name.match(/-[a-f0-9]{6}$/)) {\n const baseName = value.toLowerCase().replace(/[^a-z0-9-]/g, '-').replace(/-+/g, '-').replace(/^-|-$/g, '');\n const randomHex = Math.floor(Math.random() * 16777215).toString(16).padStart(6, '0');\n const autoName = `${baseName}-${randomHex}`;\n setName(autoName);\n setNameError(validateKubernetesName(autoName));\n }\n };\n\n const handleOpenAPISpecChange = (value: string) => {\n setOpenAPISpec(value);\n setOpenAPISpecError(validateURL(value));\n };\n\n const handleAddTag = () => {\n if (tagInput.trim() && !tags.includes(tagInput.trim())) {\n setTags([...tags, tagInput.trim()]);\n setTagInput('');\n }\n };\n\n const handleDeleteTag = (tagToDelete: string) => {\n setTags(tags.filter(tag => tag !== tagToDelete));\n };\n\n const handleCreate = async () => {\n setError('');\n setCreating(true);\n\n try {\n if (!selectedHTTPRoute) {\n throw new Error('Please select an HTTPRoute');\n }\n\n const [selectedRouteNamespace, selectedRouteName] = selectedHTTPRoute.split('/');\n\n // derive namespace from selected httproute\n const namespace = selectedRouteNamespace;\n\n const apiProduct = {\n apiVersion: 'devportal.kuadrant.io/v1alpha1',\n kind: 'APIProduct',\n metadata: {\n name,\n namespace,\n labels: {\n lifecycle,\n },\n },\n spec: {\n displayName,\n description,\n version,\n approvalMode,\n publishStatus,\n tags,\n targetRef: {\n group: 'gateway.networking.k8s.io',\n kind: 'HTTPRoute',\n name: selectedRouteName,\n namespace: selectedRouteNamespace,\n },\n ...(contactEmail || contactTeam ? {\n contact: {\n ...(contactEmail && { email: contactEmail }),\n ...(contactTeam && { team: contactTeam }),\n },\n } : {}),\n ...(docsURL || openAPISpec ? {\n documentation: {\n ...(docsURL && { docsURL }),\n ...(openAPISpec && { openAPISpecURL: openAPISpec }),\n },\n } : {}),\n },\n };\n\n const response = await fetchApi.fetch(`${backendUrl}/api/kuadrant/apiproducts`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify(apiProduct),\n });\n\n if (!response.ok) {\n const error = await handleFetchError(response);\n throw new Error(`failed to create APIProduct. ${error}`);\n }\n\n onSuccess({ namespace, name, displayName });\n handleClose();\n } catch (err) {\n setError(err instanceof Error ? err.message : String(err));\n } finally {\n setCreating(false);\n }\n };\n\n const handleClose = () => {\n setName('');\n setDisplayName('');\n setDescription('');\n setVersion('v1');\n setApprovalMode('manual');\n setPublishStatus('Published');\n setLifecycle('production');\n setTags([]);\n setTagInput('');\n setSelectedHTTPRoute('');\n setContactEmail('');\n setContactTeam('');\n setDocsURL('');\n setOpenAPISpec('');\n setError('');\n setNameError(null);\n setOpenAPISpecError(null);\n onClose();\n };\n\n const hasValidationErrors = !!nameError || !!openAPISpecError;\n\n return (\n <Dialog open={open} onClose={handleClose} maxWidth=\"md\" fullWidth>\n <DialogTitle>Create API Product</DialogTitle>\n <DialogContent>\n {error && (\n <Alert severity=\"error\" style={{ marginBottom: 16 }}>\n {error}\n </Alert>\n )}\n {httpRoutesError && (\n <Alert severity=\"error\" style={{ marginBottom: 16 }}>\n <strong>Failed to load HTTPRoutes:</strong> {httpRoutesError.message}\n <Box mt={1}>\n <Button\n size=\"small\"\n variant=\"outlined\"\n onClick={() => setHttpRoutesRetry(prev => prev + 1)}\n >\n Retry\n </Button>\n </Box>\n </Alert>\n )}\n\n {planPoliciesError && (\n <Alert severity=\"warning\" style={{ marginBottom: 16 }}>\n <strong>Failed to load PlanPolicies:</strong> {planPoliciesError.message}\n <Typography variant=\"body2\" style={{ marginTop: 8 }}>\n You can still create the API Product, but plan information may be incomplete.\n </Typography>\n </Alert>\n )}\n {/* API product info section */}\n <Box className={classes.sectionHeader}>\n <Typography variant=\"subtitle1\"><strong>API product info</strong></Typography>\n </Box>\n <Grid container spacing={2}>\n <Grid item xs={6}>\n <TextField\n fullWidth\n label=\"API product name\"\n value={displayName}\n onChange={e => handleDisplayNameChange(e.target.value)}\n placeholder=\"My API\"\n helperText=\"Display name for your API product (shown to users)\"\n margin=\"normal\"\n required\n disabled={creating}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n />\n </Grid>\n <Grid item xs={6}>\n <TextField\n fullWidth\n label=\"Kubernetes resource name\"\n value={name}\n onChange={e => handleNameChange(e.target.value)}\n placeholder=\"my-api\"\n helperText={nameError || \"Auto-generated from product name. Only lowercase, numbers, and hyphens allowed.\"}\n error={!!nameError}\n margin=\"normal\"\n required\n disabled={creating}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n />\n </Grid>\n <Grid item xs={6}>\n <TextField\n fullWidth\n label=\"Version\"\n value={version}\n onChange={e => setVersion(e.target.value)}\n placeholder=\"v1\"\n helperText=\"Give a version to your API product\"\n margin=\"normal\"\n required\n disabled={creating}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n />\n </Grid>\n <Grid item xs={6}>\n <TextField\n fullWidth\n label=\"Tag\"\n value={tagInput}\n onChange={e => setTagInput(e.target.value)}\n onKeyPress={e => {\n if (e.key === 'Enter') {\n e.preventDefault();\n handleAddTag();\n }\n }}\n placeholder=\"Add tag\"\n helperText=\"Add a tag to your API product\"\n margin=\"normal\"\n disabled={creating}\n InputProps={{\n endAdornment: tagInput ? (\n <InputAdornment position=\"end\">\n <IconButton size=\"small\" onClick={handleAddTag} disabled={creating}>\n <AddIcon fontSize=\"small\" />\n </IconButton>\n </InputAdornment>\n ) : undefined,\n }}\n />\n </Grid>\n {tags.length > 0 && (\n <Grid item xs={12}>\n <Box display=\"flex\" flexWrap=\"wrap\">\n {tags.map(tag => (\n <Chip\n key={tag}\n label={tag}\n onDelete={creating ? undefined : () => handleDeleteTag(tag)}\n size=\"small\"\n className={classes.tagChip}\n disabled={creating}\n />\n ))}\n </Box>\n </Grid>\n )}\n <Grid item xs={12}>\n <TextField\n fullWidth\n label=\"Description\"\n value={description}\n onChange={e => setDescription(e.target.value)}\n placeholder=\"API description\"\n margin=\"normal\"\n multiline\n rows={2}\n required\n disabled={creating}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n />\n </Grid>\n </Grid>\n\n {/* Add API and Associate route section */}\n <Box className={classes.sectionHeader}>\n <Typography variant=\"subtitle1\"><strong>Add API and Associate route</strong></Typography>\n <Tooltip title=\"Register an existing API and associate HTTPRoute for your API product\">\n <InfoOutlinedIcon className={classes.infoIcon} />\n </Tooltip>\n </Box>\n <Grid container spacing={2}>\n <Grid item xs={12}>\n <TextField\n fullWidth\n label=\"OpenAPI Spec URL\"\n value={openAPISpec}\n onChange={e => handleOpenAPISpecChange(e.target.value)}\n placeholder=\"https://api.example.com/openapi.json\"\n helperText={openAPISpecError || \"Enter the full path to your API spec file\"}\n error={!!openAPISpecError}\n margin=\"normal\"\n required\n disabled={creating}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n />\n </Grid>\n <Grid item xs={12}>\n <TextField\n fullWidth\n label=\"Documentation URL\"\n value={docsURL}\n onChange={e => setDocsURL(e.target.value)}\n placeholder=\"https://docs.example.com/api\"\n helperText=\"Link to external documentation for this API\"\n margin=\"normal\"\n disabled={creating}\n />\n </Grid>\n <Grid item xs={12}>\n <TextField\n fullWidth\n select\n label=\"HTTPRoute\"\n value={selectedHTTPRoute}\n onChange={e => setSelectedHTTPRoute(e.target.value)}\n margin=\"normal\"\n required\n helperText={\n httpRoutesError\n ? \"Unable to load HTTPRoutes. Please retry.\"\n : \"Select an HTTPRoute. APIProduct will be created in the same namespace.\"\n }\n error={!!httpRoutesError}\n disabled={httpRoutesLoading || creating || !!httpRoutesError}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n SelectProps={{\n 'data-testid': 'httproute-select',\n MenuProps: {\n PaperProps: {\n style: { maxHeight: 400 },\n },\n anchorOrigin: {\n vertical: 'bottom',\n horizontal: 'left',\n },\n transformOrigin: {\n vertical: 'top',\n horizontal: 'left',\n },\n getContentAnchorEl: null,\n },\n } as any}\n >\n {/* Search bar inside dropdown */}\n <Box px={2} pt={1} pb={1} style={{ position: 'sticky', top: 0, zIndex: 1 }}>\n <TextField\n fullWidth\n size=\"small\"\n placeholder=\"Search...\"\n value={routeSearchTerm}\n onChange={e => setRouteSearchTerm(e.target.value)}\n onKeyDown={e => e.stopPropagation()}\n onClick={e => e.stopPropagation()}\n InputProps={{\n endAdornment: (\n <InputAdornment position=\"end\">\n <TextField\n select\n size=\"small\"\n value={routeSearchField}\n onChange={e => setRouteSearchField(e.target.value as 'name' | 'namespace' | 'planpolicy')}\n onKeyDown={e => e.stopPropagation()}\n onClick={e => e.stopPropagation()}\n style={{ minWidth: 120 }}\n variant=\"standard\"\n >\n <MenuItem value=\"name\">Name</MenuItem>\n <MenuItem value=\"namespace\">Namespace</MenuItem>\n <MenuItem value=\"planpolicy\">PlanPolicy</MenuItem>\n </TextField>\n </InputAdornment>\n ),\n }}\n />\n </Box>\n {httpRoutesLoading && (\n <MenuItem value=\"\">Loading...</MenuItem>\n )}\n {httpRoutesError && (\n <MenuItem value=\"\">Error loading routes</MenuItem>\n )}\n {!httpRoutesLoading && !httpRoutesError && httpRoutes && httpRoutes.length === 0 && (\n <MenuItem value=\"\">No HTTPRoutes available</MenuItem>\n )}\n {!httpRoutesLoading && !httpRoutesError && httpRoutes && httpRoutes\n .filter((route: any) => {\n if (!routeSearchTerm) return true;\n const routeNs = route.metadata.namespace;\n const routeName = route.metadata.name;\n const policyInfo = getPolicyInfoForRoute(routeNs, routeName);\n const searchLower = routeSearchTerm.toLowerCase();\n\n switch (routeSearchField) {\n case 'name':\n return routeName.toLowerCase().includes(searchLower);\n case 'namespace':\n return routeNs.toLowerCase().includes(searchLower);\n case 'planpolicy':\n return policyInfo.toLowerCase().includes(searchLower);\n default:\n return true;\n }\n })\n .map((route: any) => {\n const routeNs = route.metadata.namespace;\n const routeName = route.metadata.name;\n const policyInfo = getPolicyInfoForRoute(routeNs, routeName);\n return (\n <MenuItem\n key={`${routeNs}/${routeName}`}\n value={`${routeNs}/${routeName}`}\n >\n <Box>\n <Typography variant=\"body1\">{routeName}</Typography>\n <Typography variant=\"caption\" color=\"textSecondary\">\n Associated PlanPolicy: {policyInfo}\n </Typography>\n </Box>\n </MenuItem>\n );\n })}\n </TextField>\n </Grid>\n </Grid>\n\n {/* HTTPRoute policies section */}\n {selectedHTTPRoute && selectedPolicy && (\n <>\n <Box className={classes.sectionHeader}>\n <Typography variant=\"subtitle1\"><strong>HTTPRoute policies</strong></Typography>\n <Tooltip title=\"Shows the associated policies and rate limit tiers for the selected HTTPRoute\">\n <InfoOutlinedIcon className={classes.infoIcon} />\n </Tooltip>\n </Box>\n <PlanPolicyDetails\n discoveredPlans={selectedPolicy.plans}\n alertSeverity=\"warning\"\n alertMessage=\"No PlanPolicy found for this HTTPRoute. API keys and rate limiting may not be available.\"\n includeTopMargin={false}\n />\n </>\n )}\n\n <Box className={classes.sectionHeader}>\n <Typography variant=\"subtitle1\"><strong>Lifecycle and Visibility</strong></Typography>\n <Tooltip title=\"Control the lifecycle state and catalog visibility of this API product\">\n <InfoOutlinedIcon className={classes.infoIcon} />\n </Tooltip>\n </Box>\n <Grid container spacing={2}>\n <Grid item xs={6}>\n <TextField\n fullWidth\n select\n label=\"Lifecycle\"\n value={lifecycle}\n onChange={e => setLifecycle(e.target.value as Lifecycle)}\n margin=\"normal\"\n helperText=\"API lifecycle state\"\n disabled={creating}\n >\n <MenuItem value=\"experimental\">Experimental</MenuItem>\n <MenuItem value=\"production\">Production</MenuItem>\n <MenuItem value=\"deprecated\">Deprecated</MenuItem>\n <MenuItem value=\"retired\">Retired</MenuItem>\n </TextField>\n </Grid>\n <Grid item xs={6}>\n <TextField\n fullWidth\n select\n label=\"Publish Status\"\n value={publishStatus}\n onChange={e => setPublishStatus(e.target.value as 'Draft' | 'Published')}\n margin=\"normal\"\n helperText=\"Controls catalog visibility (Draft = hidden from consumers)\"\n disabled={creating}\n >\n <MenuItem value=\"Draft\">Draft</MenuItem>\n <MenuItem value=\"Published\">Published</MenuItem>\n </TextField>\n </Grid>\n </Grid>\n\n {/* API Key approval section */}\n <Box className={classes.sectionHeader}>\n <Typography variant=\"subtitle1\"><strong>API Key approval</strong></Typography>\n <Tooltip title=\"Choose how API key requests are handled for this product\">\n <InfoOutlinedIcon className={classes.infoIcon} />\n </Tooltip>\n </Box>\n <FormControl component=\"fieldset\" disabled={creating}>\n <RadioGroup\n row\n value={approvalMode}\n onChange={e => setApprovalMode(e.target.value as 'automatic' | 'manual')}\n >\n <FormControlLabel\n value=\"manual\"\n control={<Radio color=\"primary\" />}\n label={\n <Box>\n <Typography variant=\"body2\">Need manual approval</Typography>\n <Typography variant=\"caption\" color=\"textSecondary\">\n Requires approval for requesting this API\n </Typography>\n </Box>\n }\n />\n <FormControlLabel\n value=\"automatic\"\n control={<Radio color=\"primary\" />}\n label={\n <Box>\n <Typography variant=\"body2\">Automatic</Typography>\n <Typography variant=\"caption\" color=\"textSecondary\">\n Keys are created without need to be approved\n </Typography>\n </Box>\n }\n />\n </RadioGroup>\n </FormControl>\n </DialogContent>\n <DialogActions>\n <Button onClick={handleClose} disabled={creating}>Cancel</Button>\n <Button\n onClick={handleCreate}\n color=\"primary\"\n variant=\"contained\"\n disabled={creating || !name || !displayName || !description || !selectedHTTPRoute || hasValidationErrors}\n startIcon={creating ? <CircularProgress size={16} color=\"inherit\" /> : undefined}\n >\n {creating ? 'Creating...' : 'Create'}\n </Button>\n </DialogActions>\n </Dialog>\n );\n};\n"],"names":["error","name"],"mappings":"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"}
1
+ {"version":3,"file":"CreateAPIProductDialog.esm.js","sources":["../../../src/components/CreateAPIProductDialog/CreateAPIProductDialog.tsx"],"sourcesContent":["import React, { useEffect, useState } from 'react';\nimport {\n Dialog,\n DialogTitle,\n DialogContent,\n DialogActions,\n Button,\n TextField,\n Box,\n Typography,\n Chip,\n Grid,\n MenuItem,\n CircularProgress,\n makeStyles,\n FormControl,\n RadioGroup,\n FormControlLabel,\n Radio,\n Tooltip,\n IconButton,\n InputAdornment,\n} from '@material-ui/core';\nimport InfoOutlinedIcon from '@material-ui/icons/InfoOutlined';\nimport AddIcon from '@material-ui/icons/Add';\nimport { useApi } from '@backstage/core-plugin-api';\nimport { kuadrantApiRef } from '../../api';\nimport { Alert } from '@material-ui/lab';\nimport useAsync from 'react-use/lib/useAsync';\nimport { ApiProductPolicies } from '../ApiProductPolicies';\nimport { validateKubernetesName, validateURL } from '../../utils/validation';\nimport { APIProduct } from \"../../types/api-management.ts\";\nimport { Lifecycle } from '../../types/api-management';\nimport { getPolicyForRoute } from '../../utils/policies';\n\nconst useStyles = makeStyles((theme) => ({\n asterisk: {\n color: '#f44336',\n },\n sectionHeader: {\n display: 'flex',\n alignItems: 'center',\n gap: theme.spacing(0.5),\n marginTop: theme.spacing(2),\n marginBottom: theme.spacing(1),\n },\n infoIcon: {\n fontSize: 18,\n color: theme.palette.text.secondary,\n },\n tagChip: {\n marginRight: theme.spacing(0.5),\n marginBottom: theme.spacing(0.5),\n },\n}));\n\ninterface CreateAPIProductDialogProps {\n open: boolean;\n onClose: () => void;\n onSuccess: (productInfo: { namespace: string; name: string; displayName: string }) => void;\n}\n\nexport const CreateAPIProductDialog = ({ open, onClose, onSuccess }: CreateAPIProductDialogProps) => {\n const classes = useStyles();\n const kuadrantApi = useApi(kuadrantApiRef);\n\n const [name, setName] = useState('');\n const [displayName, setDisplayName] = useState('');\n const [description, setDescription] = useState('');\n const [version, setVersion] = useState('v1');\n const [approvalMode, setApprovalMode] = useState<'automatic' | 'manual'>('manual');\n const [publishStatus, setPublishStatus] = useState<'Draft' | 'Published'>('Published');\n const [lifecycle, setLifecycle] = useState<Lifecycle>('production');\n const [tags, setTags] = useState<string[]>([]);\n const [tagInput, setTagInput] = useState('');\n const [selectedHTTPRoute, setSelectedHTTPRoute] = useState('');\n const [contactEmail, setContactEmail] = useState('');\n const [contactTeam, setContactTeam] = useState('');\n const [docsURL, setDocsURL] = useState('');\n const [openAPISpec, setOpenAPISpec] = useState('');\n const [error, setError] = useState('');\n const [creating, setCreating] = useState(false);\n const [httpRoutesRetry, setHttpRoutesRetry] = useState(0);\n const [nameError, setNameError] = useState<string | null>(null);\n const [openAPISpecError, setOpenAPISpecError] = useState<string | null>(null);\n const [routeSearchTerm, setRouteSearchTerm] = useState('');\n const [routeSearchField, setRouteSearchField] = useState<'name' | 'namespace' | 'planpolicy'>('name');\n const {\n value: httpRoutes,\n loading: httpRoutesLoading,\n error: httpRoutesError\n } = useAsync(async () => {\n const data = await kuadrantApi.getHttpRoutes();\n return data.items || [];\n }, [kuadrantApi, open, httpRoutesRetry]);\n\n // load planpolicies with full details to show associated plans\n const {\n value: planPolicies,\n error: planPoliciesError\n } = useAsync(async () => {\n return await kuadrantApi.getPlanPolicies();\n }, [kuadrantApi, open]);\n\n // load authpolicies\n const {\n value: authPolicies,\n error: authPoliciesError\n } = useAsync(async () => {\n return await kuadrantApi.getAuthPolicies();\n }, [kuadrantApi, open]);\n\n // load ratelimitpolicies\n const {\n value: rateLimitPolicies,\n error: rateLimitPoliciesError\n } = useAsync(async () => {\n return await kuadrantApi.getRateLimitPolicies();\n }, [kuadrantApi, open]);\n\n // find planpolicy associated with selected httproute\n const getPlanPolicyForRoute = (routeNamespace: string, routeName: string) => {\n return getPolicyForRoute(planPolicies?.items, routeNamespace, routeName);\n };\n\n // find authpolicy associated with selected httproute\n const getAuthPolicyForRoute = (routeNamespace: string, routeName: string) => {\n return getPolicyForRoute(authPolicies?.items, routeNamespace, routeName);\n };\n\n // find ratelimitpolicy associated with selected httproute\n const getRateLimitPolicyForRoute = (routeNamespace: string, routeName: string) => {\n return getPolicyForRoute(rateLimitPolicies?.items, routeNamespace, routeName);\n };\n\n const selectedRouteInfo = selectedHTTPRoute ? selectedHTTPRoute.split('/') : null;\n const selectedPlanPolicy = selectedRouteInfo\n ? getPlanPolicyForRoute(selectedRouteInfo[0], selectedRouteInfo[1])\n : null;\n const planPolicyAcceptedCondition = selectedPlanPolicy?.status?.conditions?.find(\n (c: any) => c.type === \"Accepted\"\n );\n const selectedAuthPolicy = selectedRouteInfo\n ? getAuthPolicyForRoute(selectedRouteInfo[0], selectedRouteInfo[1])\n : null;\n const authPolicyAcceptedCondition = selectedAuthPolicy?.status?.conditions?.find(\n (c: any) => c.type === \"Accepted\"\n );\n const selectedRateLimitPolicy = selectedRouteInfo\n ? getRateLimitPolicyForRoute(selectedRouteInfo[0], selectedRouteInfo[1])\n : null;\n const rateLimitPolicyAcceptedCondition = selectedRateLimitPolicy?.status?.conditions?.find(\n (c: any) => c.type === \"Accepted\"\n );\n const planPolicyProps = {\n statusCondition: planPolicyAcceptedCondition,\n discoveredPlans: selectedPlanPolicy?.spec.plans,\n }\n const authPolicyProps = {\n namespacedName: {\n namespace: selectedAuthPolicy?.metadata.namespace,\n name: selectedAuthPolicy?.metadata.name,\n },\n statusCondition: authPolicyAcceptedCondition,\n }\n const rateLimitPolicyProps = {\n namespacedName: {\n namespace: selectedRateLimitPolicy?.metadata.namespace,\n name: selectedRateLimitPolicy?.metadata.name,\n },\n statusCondition: rateLimitPolicyAcceptedCondition,\n }\n\n // format tier info for dropdown display\n const formatTierInfo = (policy: any): string => {\n if (!policy?.spec?.plans) return '';\n const tiers = Object.entries(policy.spec.plans)\n .map(([name, plan]: [string, any]) => {\n const limit = plan?.limits?.requests;\n if (!limit) return name;\n return `${name}: ${limit.count}/${limit.period}`;\n })\n .join('; ');\n return tiers ? ` (${tiers})` : '';\n };\n\n // get policy info for a route (for dropdown display)\n const getPolicyInfoForRoute = (routeNamespace: string, routeName: string): string => {\n const policy = getPlanPolicyForRoute(routeNamespace, routeName);\n if (!policy) return 'N/A';\n return `${policy.metadata.name}${formatTierInfo(policy)}`;\n };\n\n useEffect(() => {\n if (open) {\n setNameError(null);\n setOpenAPISpecError(null);\n }\n }, [open]);\n\n // validate handlers\n const handleNameChange = (value: string) => {\n setName(value);\n setNameError(validateKubernetesName(value));\n };\n\n const handleDisplayNameChange = (value: string) => {\n setDisplayName(value);\n // Auto-generate Kubernetes resource name from display name with random hex suffix\n if (!name || name.match(/-[a-f0-9]{6}$/)) {\n const baseName = value.toLowerCase().replace(/[^a-z0-9-]/g, '-').replace(/-+/g, '-').replace(/^-|-$/g, '');\n const randomHex = Math.floor(Math.random() * 16777215).toString(16).padStart(6, '0');\n const autoName = `${baseName}-${randomHex}`;\n setName(autoName);\n setNameError(validateKubernetesName(autoName));\n }\n };\n\n const handleOpenAPISpecChange = (value: string) => {\n setOpenAPISpec(value);\n setOpenAPISpecError(validateURL(value));\n };\n\n const handleAddTag = () => {\n if (tagInput.trim() && !tags.includes(tagInput.trim())) {\n setTags([...tags, tagInput.trim()]);\n setTagInput('');\n }\n };\n\n const handleDeleteTag = (tagToDelete: string) => {\n setTags(tags.filter(tag => tag !== tagToDelete));\n };\n\n const handleClose = () => {\n setName('');\n setDisplayName('');\n setDescription('');\n setVersion('v1');\n setApprovalMode('manual');\n setPublishStatus('Published');\n setLifecycle('production');\n setTags([]);\n setTagInput('');\n setSelectedHTTPRoute('');\n setContactEmail('');\n setContactTeam('');\n setDocsURL('');\n setOpenAPISpec('');\n setError('');\n setNameError(null);\n setOpenAPISpecError(null);\n onClose();\n };\n\n const handleCreate = async () => {\n setError('');\n setCreating(true);\n\n try {\n if (!selectedHTTPRoute) {\n throw new Error('Please select an HTTPRoute');\n }\n\n const [selectedRouteNamespace, selectedRouteName] = selectedHTTPRoute.split('/');\n\n // derive namespace from selected httproute\n const namespace = selectedRouteNamespace;\n\n const apiProduct: APIProduct = {\n apiVersion: 'devportal.kuadrant.io/v1alpha1',\n kind: 'APIProduct',\n metadata: {\n name,\n namespace,\n labels: {\n lifecycle,\n },\n },\n spec: {\n displayName,\n description,\n version,\n approvalMode,\n publishStatus,\n tags,\n targetRef: {\n group: 'gateway.networking.k8s.io',\n kind: 'HTTPRoute',\n name: selectedRouteName,\n namespace: selectedRouteNamespace,\n },\n ...(contactEmail || contactTeam ? {\n contact: {\n ...(contactEmail && { email: contactEmail }),\n ...(contactTeam && { team: contactTeam }),\n },\n } : {}),\n ...(docsURL || openAPISpec ? {\n documentation: {\n ...(docsURL && { docsURL }),\n ...(openAPISpec && { openAPISpecURL: openAPISpec }),\n },\n } : {}),\n },\n };\n\n await kuadrantApi.createApiProduct(apiProduct);\n onSuccess({ namespace, name, displayName });\n handleClose();\n } catch (err) {\n setError(err instanceof Error ? err.message : String(err));\n } finally {\n setCreating(false);\n }\n };\n\n const hasValidationErrors = !!nameError || !!openAPISpecError;\n\n return (\n <Dialog open={open} onClose={handleClose} maxWidth=\"md\" fullWidth>\n <DialogTitle>Create API Product</DialogTitle>\n <DialogContent>\n {error && (\n <Alert severity=\"error\" style={{ marginBottom: 16 }}>\n {error}\n </Alert>\n )}\n {httpRoutesError && (\n <Alert severity=\"error\" style={{ marginBottom: 16 }}>\n <strong>Failed to load HTTPRoutes:</strong> {httpRoutesError.message}\n <Box mt={1}>\n <Button\n size=\"small\"\n variant=\"outlined\"\n onClick={() => setHttpRoutesRetry(prev => prev + 1)}\n >\n Retry\n </Button>\n </Box>\n </Alert>\n )}\n\n {planPoliciesError && (\n <Alert severity=\"warning\" style={{ marginBottom: 16 }}>\n <strong>Failed to load PlanPolicies:</strong> {planPoliciesError.message}\n <Typography variant=\"body2\" style={{ marginTop: 8 }}>\n You can still create the API Product, but plan information may be incomplete.\n </Typography>\n </Alert>\n )}\n {authPoliciesError && (\n <Alert severity=\"warning\" style={{ marginBottom: 16 }}>\n <strong>Failed to load AuthPolicies:</strong> {authPoliciesError.message}\n </Alert>\n )}\n {rateLimitPoliciesError && (\n <Alert severity=\"warning\" style={{ marginBottom: 16 }}>\n <strong>Failed to load RateLimitPolicies:</strong> {rateLimitPoliciesError.message}\n </Alert>\n )}\n {/* API product info section */}\n <Box className={classes.sectionHeader}>\n <Typography variant=\"subtitle1\"><strong>API product info</strong></Typography>\n </Box>\n <Grid container spacing={2}>\n <Grid item xs={6}>\n <TextField\n fullWidth\n label=\"API product name\"\n value={displayName}\n onChange={e => handleDisplayNameChange(e.target.value)}\n placeholder=\"My API\"\n helperText=\"Display name for your API product (shown to users)\"\n margin=\"normal\"\n required\n disabled={creating}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n />\n </Grid>\n <Grid item xs={6}>\n <TextField\n fullWidth\n label=\"Kubernetes resource name\"\n value={name}\n onChange={e => handleNameChange(e.target.value)}\n placeholder=\"my-api\"\n helperText={nameError || \"Auto-generated from product name. Only lowercase, numbers, and hyphens allowed.\"}\n error={!!nameError}\n margin=\"normal\"\n required\n disabled={creating}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n />\n </Grid>\n <Grid item xs={6}>\n <TextField\n fullWidth\n label=\"Version\"\n value={version}\n onChange={e => setVersion(e.target.value)}\n placeholder=\"v1\"\n helperText=\"Give a version to your API product\"\n margin=\"normal\"\n required\n disabled={creating}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n />\n </Grid>\n <Grid item xs={6}>\n <TextField\n fullWidth\n label=\"Tag\"\n value={tagInput}\n onChange={e => setTagInput(e.target.value)}\n onKeyPress={e => {\n if (e.key === 'Enter') {\n e.preventDefault();\n handleAddTag();\n }\n }}\n placeholder=\"Add tag\"\n helperText=\"Add a tag to your API product\"\n margin=\"normal\"\n disabled={creating}\n InputProps={{\n endAdornment: tagInput ? (\n <InputAdornment position=\"end\">\n <IconButton size=\"small\" onClick={handleAddTag} disabled={creating}>\n <AddIcon fontSize=\"small\" />\n </IconButton>\n </InputAdornment>\n ) : undefined,\n }}\n />\n </Grid>\n {tags.length > 0 && (\n <Grid item xs={12}>\n <Box display=\"flex\" flexWrap=\"wrap\">\n {tags.map(tag => (\n <Chip\n key={tag}\n label={tag}\n onDelete={creating ? undefined : () => handleDeleteTag(tag)}\n size=\"small\"\n className={classes.tagChip}\n disabled={creating}\n />\n ))}\n </Box>\n </Grid>\n )}\n <Grid item xs={12}>\n <TextField\n fullWidth\n label=\"Description\"\n value={description}\n onChange={e => setDescription(e.target.value)}\n placeholder=\"API description\"\n margin=\"normal\"\n multiline\n rows={2}\n required\n disabled={creating}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n />\n </Grid>\n </Grid>\n\n {/* Add API and Associate route section */}\n <Box className={classes.sectionHeader}>\n <Typography variant=\"subtitle1\"><strong>Add API and Associate route</strong></Typography>\n <Tooltip title=\"Register an existing API and associate HTTPRoute for your API product\">\n <InfoOutlinedIcon className={classes.infoIcon} />\n </Tooltip>\n </Box>\n <Grid container spacing={2}>\n <Grid item xs={12}>\n <TextField\n fullWidth\n label=\"OpenAPI Spec URL\"\n value={openAPISpec}\n onChange={e => handleOpenAPISpecChange(e.target.value)}\n placeholder=\"https://api.example.com/openapi.json\"\n helperText={openAPISpecError || \"Enter the full path to your API spec file\"}\n error={!!openAPISpecError}\n margin=\"normal\"\n required\n disabled={creating}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n />\n </Grid>\n <Grid item xs={12}>\n <TextField\n fullWidth\n label=\"Documentation URL\"\n value={docsURL}\n onChange={e => setDocsURL(e.target.value)}\n placeholder=\"https://docs.example.com/api\"\n helperText=\"Link to external documentation for this API\"\n margin=\"normal\"\n disabled={creating}\n />\n </Grid>\n <Grid item xs={12}>\n <TextField\n fullWidth\n select\n label=\"HTTPRoute\"\n value={selectedHTTPRoute}\n onChange={e => setSelectedHTTPRoute(e.target.value)}\n margin=\"normal\"\n required\n helperText={\n httpRoutesError\n ? \"Unable to load HTTPRoutes. Please retry.\"\n : \"Select an HTTPRoute. APIProduct will be created in the same namespace.\"\n }\n error={!!httpRoutesError}\n disabled={httpRoutesLoading || creating || !!httpRoutesError}\n InputLabelProps={{\n classes: {\n asterisk: classes.asterisk,\n },\n }}\n SelectProps={{\n 'data-testid': 'httproute-select',\n MenuProps: {\n PaperProps: {\n style: { maxHeight: 400 },\n },\n anchorOrigin: {\n vertical: 'bottom',\n horizontal: 'left',\n },\n transformOrigin: {\n vertical: 'top',\n horizontal: 'left',\n },\n getContentAnchorEl: null,\n },\n } as any}\n >\n {/* Search bar inside dropdown */}\n <Box px={2} pt={1} pb={1} style={{ position: 'sticky', top: 0, zIndex: 1 }}>\n <TextField\n fullWidth\n size=\"small\"\n placeholder=\"Search...\"\n value={routeSearchTerm}\n onChange={e => setRouteSearchTerm(e.target.value)}\n onKeyDown={e => e.stopPropagation()}\n onClick={e => e.stopPropagation()}\n InputProps={{\n endAdornment: (\n <InputAdornment position=\"end\">\n <TextField\n select\n size=\"small\"\n value={routeSearchField}\n onChange={e => setRouteSearchField(e.target.value as 'name' | 'namespace' | 'planpolicy')}\n onKeyDown={e => e.stopPropagation()}\n onClick={e => e.stopPropagation()}\n style={{ minWidth: 120 }}\n variant=\"standard\"\n >\n <MenuItem value=\"name\">Name</MenuItem>\n <MenuItem value=\"namespace\">Namespace</MenuItem>\n <MenuItem value=\"planpolicy\">PlanPolicy</MenuItem>\n </TextField>\n </InputAdornment>\n ),\n }}\n />\n </Box>\n {httpRoutesLoading && (\n <MenuItem value=\"\">Loading...</MenuItem>\n )}\n {httpRoutesError && (\n <MenuItem value=\"\">Error loading routes</MenuItem>\n )}\n {!httpRoutesLoading && !httpRoutesError && httpRoutes && httpRoutes.length === 0 && (\n <MenuItem value=\"\">No HTTPRoutes available</MenuItem>\n )}\n {!httpRoutesLoading && !httpRoutesError && httpRoutes && httpRoutes\n .filter((route: any) => {\n if (!routeSearchTerm) return true;\n const routeNs = route.metadata.namespace;\n const routeName = route.metadata.name;\n const policyInfo = getPolicyInfoForRoute(routeNs, routeName);\n const searchLower = routeSearchTerm.toLowerCase();\n\n switch (routeSearchField) {\n case 'name':\n return routeName.toLowerCase().includes(searchLower);\n case 'namespace':\n return routeNs.toLowerCase().includes(searchLower);\n case 'planpolicy':\n return policyInfo.toLowerCase().includes(searchLower);\n default:\n return true;\n }\n })\n .map((route: any) => {\n const routeNs = route.metadata.namespace;\n const routeName = route.metadata.name;\n const policyInfo = getPolicyInfoForRoute(routeNs, routeName);\n return (\n <MenuItem\n key={`${routeNs}/${routeName}`}\n value={`${routeNs}/${routeName}`}\n >\n <Box>\n <Typography variant=\"body1\">{routeName}</Typography>\n <Typography variant=\"caption\" color=\"textSecondary\">\n Associated PlanPolicy: {policyInfo}\n </Typography>\n </Box>\n </MenuItem>\n );\n })}\n </TextField>\n </Grid>\n </Grid>\n\n {/* HTTPRoute policies section */}\n {selectedHTTPRoute && (\n <>\n <Box className={classes.sectionHeader}>\n <Typography variant=\"subtitle1\"><strong>HTTPRoute policies</strong></Typography>\n <Tooltip title=\"Shows the associated policies and rate limit tiers for the selected HTTPRoute\">\n <InfoOutlinedIcon className={classes.infoIcon} />\n </Tooltip>\n </Box>\n <ApiProductPolicies\n planPolicy={planPolicyProps}\n authPolicy={authPolicyProps}\n rateLimitPolicy={rateLimitPolicyProps}\n includeTopMargin={false}\n />\n </>\n )}\n\n <Box className={classes.sectionHeader}>\n <Typography variant=\"subtitle1\"><strong>Lifecycle and Visibility</strong></Typography>\n <Tooltip title=\"Control the lifecycle state and catalog visibility of this API product\">\n <InfoOutlinedIcon className={classes.infoIcon} />\n </Tooltip>\n </Box>\n <Grid container spacing={2}>\n <Grid item xs={6}>\n <TextField\n fullWidth\n select\n label=\"Lifecycle\"\n value={lifecycle}\n onChange={e => setLifecycle(e.target.value as Lifecycle)}\n margin=\"normal\"\n helperText=\"API lifecycle state\"\n disabled={creating}\n >\n <MenuItem value=\"experimental\">Experimental</MenuItem>\n <MenuItem value=\"production\">Production</MenuItem>\n <MenuItem value=\"deprecated\">Deprecated</MenuItem>\n <MenuItem value=\"retired\">Retired</MenuItem>\n </TextField>\n </Grid>\n <Grid item xs={6}>\n <TextField\n fullWidth\n select\n label=\"Publish Status\"\n value={publishStatus}\n onChange={e => setPublishStatus(e.target.value as 'Draft' | 'Published')}\n margin=\"normal\"\n helperText=\"Controls catalog visibility (Draft = hidden from consumers)\"\n disabled={creating}\n >\n <MenuItem value=\"Draft\">Draft</MenuItem>\n <MenuItem value=\"Published\">Published</MenuItem>\n </TextField>\n </Grid>\n </Grid>\n\n {/* API Key approval section */}\n <Box className={classes.sectionHeader}>\n <Typography variant=\"subtitle1\"><strong>API Key approval</strong></Typography>\n <Tooltip title=\"Choose how API key requests are handled for this product\">\n <InfoOutlinedIcon className={classes.infoIcon} />\n </Tooltip>\n </Box>\n <FormControl component=\"fieldset\" disabled={creating}>\n <RadioGroup\n row\n value={approvalMode}\n onChange={e => setApprovalMode(e.target.value as 'automatic' | 'manual')}\n >\n <FormControlLabel\n value=\"manual\"\n control={<Radio color=\"primary\" />}\n label={\n <Box>\n <Typography variant=\"body2\">Need manual approval</Typography>\n <Typography variant=\"caption\" color=\"textSecondary\">\n Requires approval for requesting this API\n </Typography>\n </Box>\n }\n />\n <FormControlLabel\n value=\"automatic\"\n control={<Radio color=\"primary\" />}\n label={\n <Box>\n <Typography variant=\"body2\">Automatic</Typography>\n <Typography variant=\"caption\" color=\"textSecondary\">\n Keys are created without need to be approved\n </Typography>\n </Box>\n }\n />\n </RadioGroup>\n </FormControl>\n </DialogContent>\n <DialogActions>\n <Button onClick={handleClose} disabled={creating}>Cancel</Button>\n <Button\n onClick={handleCreate}\n color=\"primary\"\n variant=\"contained\"\n disabled={creating || !name || !displayName || !description || !selectedHTTPRoute || hasValidationErrors}\n startIcon={creating ? <CircularProgress size={16} color=\"inherit\" /> : undefined}\n >\n {creating ? 'Creating...' : 'Create'}\n </Button>\n </DialogActions>\n </Dialog>\n );\n};\n"],"names":["name"],"mappings":"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"}
@@ -1,7 +1,7 @@
1
1
  import React, { useState, useEffect } from 'react';
2
2
  import { Dialog, DialogTitle, DialogContent, Box, Typography, FormControl, InputLabel, Select, MenuItem, TextField, DialogActions, Button, CircularProgress } from '@material-ui/core';
3
- import { useApi, configApiRef, fetchApiRef } from '@backstage/core-plugin-api';
4
- import { handleFetchError } from '../../utils/errors.esm.js';
3
+ import { useApi } from '@backstage/core-plugin-api';
4
+ import { kuadrantApiRef } from '../../api.esm.js';
5
5
 
6
6
  const EditAPIKeyDialog = ({
7
7
  open,
@@ -10,9 +10,7 @@ const EditAPIKeyDialog = ({
10
10
  request,
11
11
  availablePlans
12
12
  }) => {
13
- const config = useApi(configApiRef);
14
- const fetchApi = useApi(fetchApiRef);
15
- const backendUrl = config.getString("backend.baseUrl");
13
+ const kuadrantApi = useApi(kuadrantApiRef);
16
14
  const [planTier, setPlanTier] = useState("");
17
15
  const [useCase, setUseCase] = useState("");
18
16
  const [saving, setSaving] = useState(false);
@@ -38,20 +36,12 @@ const EditAPIKeyDialog = ({
38
36
  useCase: useCase.trim()
39
37
  }
40
38
  };
41
- const response = await fetchApi.fetch(
42
- `${backendUrl}/api/kuadrant/requests/${request.metadata.namespace}/${request.metadata.name}`,
43
- {
44
- method: "PATCH",
45
- headers: {
46
- "Content-Type": "application/json"
47
- },
48
- body: JSON.stringify(patch)
49
- }
39
+ await kuadrantApi.updateRequest(
40
+ request.metadata.name,
41
+ request.metadata.namespace,
42
+ // @ts-ignore Applying a partial obj
43
+ patch
50
44
  );
51
- if (!response.ok) {
52
- const err = await handleFetchError(response);
53
- throw new Error(`Failed to update request: ${response.status}. ${err}`);
54
- }
55
45
  onSuccess();
56
46
  onClose();
57
47
  } catch (err) {
@@ -1 +1 @@
1
- {"version":3,"file":"EditAPIKeyDialog.esm.js","sources":["../../../src/components/EditAPIKeyDialog/EditAPIKeyDialog.tsx"],"sourcesContent":["import React, { useState, useEffect } from \"react\";\nimport {\n Dialog,\n DialogTitle,\n DialogContent,\n DialogActions,\n Button,\n TextField,\n Box,\n Typography,\n FormControl,\n InputLabel,\n Select,\n MenuItem,\n CircularProgress,\n} from \"@material-ui/core\";\nimport { useApi, configApiRef, fetchApiRef } from \"@backstage/core-plugin-api\";\nimport { APIKey } from \"../../types/api-management\";\nimport {handleFetchError} from \"../../utils/errors.ts\";\n\ninterface EditAPIKeyDialogProps {\n open: boolean;\n onClose: () => void;\n onSuccess: () => void;\n request: APIKey;\n availablePlans: Array<{\n tier: string;\n description?: string;\n limits?: any;\n }>;\n}\n\nexport const EditAPIKeyDialog = ({\n open,\n onClose,\n onSuccess,\n request,\n availablePlans,\n}: EditAPIKeyDialogProps) => {\n const config = useApi(configApiRef);\n const fetchApi = useApi(fetchApiRef);\n const backendUrl = config.getString(\"backend.baseUrl\");\n\n const [planTier, setPlanTier] = useState(\"\");\n const [useCase, setUseCase] = useState(\"\");\n const [saving, setSaving] = useState(false);\n const [error, setError] = useState(\"\");\n\n useEffect(() => {\n if (open && request) {\n setPlanTier(request.spec.planTier || \"\");\n setUseCase(request.spec.useCase || \"\");\n setError(\"\");\n }\n }, [open, request]);\n\n const handleSave = async () => {\n if (!planTier) {\n setError(\"Please select a tier\");\n return;\n }\n\n setError(\"\");\n setSaving(true);\n\n try {\n const patch = {\n spec: {\n planTier,\n useCase: useCase.trim(),\n },\n };\n\n const response = await fetchApi.fetch(\n `${backendUrl}/api/kuadrant/requests/${request.metadata.namespace}/${request.metadata.name}`,\n {\n method: \"PATCH\",\n headers: {\n \"Content-Type\": \"application/json\",\n },\n body: JSON.stringify(patch),\n },\n );\n\n if (!response.ok) {\n const err = await handleFetchError(response);\n throw new Error(`Failed to update request: ${response.status}. ${err}`);\n }\n\n onSuccess();\n onClose();\n } catch (err) {\n console.error(\"Error updating API key request:\", err);\n setError(err instanceof Error ? err.message : \"Unknown error occurred\");\n } finally {\n setSaving(false);\n }\n };\n\n const handleClose = () => {\n if (!saving) {\n setError(\"\");\n onClose();\n }\n };\n\n return (\n <Dialog open={open} onClose={handleClose} maxWidth=\"sm\" fullWidth>\n <DialogTitle>Edit API Key</DialogTitle>\n <DialogContent>\n {error && (\n <Box\n mb={2}\n p={2}\n bgcolor=\"error.main\"\n color=\"error.contrastText\"\n borderRadius={1}\n >\n <Typography variant=\"body2\">{error}</Typography>\n </Box>\n )}\n\n <FormControl fullWidth margin=\"normal\">\n <InputLabel>Tier</InputLabel>\n <Select\n value={planTier}\n onChange={(e) => setPlanTier(e.target.value as string)}\n disabled={saving}\n >\n {availablePlans.map((plan) => {\n const limitDesc = Object.entries(plan.limits || {})\n .map(([key, val]) => `${val} per ${key}`)\n .join(\", \");\n return (\n <MenuItem key={plan.tier} value={plan.tier}>\n {plan.tier} {limitDesc ? `(${limitDesc})` : \"\"}\n </MenuItem>\n );\n })}\n </Select>\n </FormControl>\n\n <TextField\n label=\"Use Case\"\n placeholder=\"Describe how you plan to use this API\"\n multiline\n rows={3}\n fullWidth\n margin=\"normal\"\n value={useCase}\n onChange={(e) => setUseCase(e.target.value)}\n disabled={saving}\n helperText=\"Explain your intended use of this API for admin review\"\n />\n </DialogContent>\n <DialogActions>\n <Button onClick={handleClose} disabled={saving}>\n Cancel\n </Button>\n <Button\n onClick={handleSave}\n color=\"primary\"\n variant=\"contained\"\n disabled={!planTier || saving}\n startIcon={\n saving ? <CircularProgress size={16} color=\"inherit\" /> : undefined\n }\n >\n {saving ? \"Saving...\" : \"Save Changes\"}\n </Button>\n </DialogActions>\n </Dialog>\n );\n};\n"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"EditAPIKeyDialog.esm.js","sources":["../../../src/components/EditAPIKeyDialog/EditAPIKeyDialog.tsx"],"sourcesContent":["import React, { useState, useEffect } from \"react\";\nimport {\n Dialog,\n DialogTitle,\n DialogContent,\n DialogActions,\n Button,\n TextField,\n Box,\n Typography,\n FormControl,\n InputLabel,\n Select,\n MenuItem,\n CircularProgress,\n} from \"@material-ui/core\";\nimport { useApi } from \"@backstage/core-plugin-api\";\nimport { kuadrantApiRef } from '../../api';\nimport { APIKey } from \"../../types/api-management\";\n\ninterface EditAPIKeyDialogProps {\n open: boolean;\n onClose: () => void;\n onSuccess: () => void;\n request: APIKey;\n availablePlans: Array<{\n tier: string;\n description?: string;\n limits?: any;\n }>;\n}\n\nexport const EditAPIKeyDialog = ({\n open,\n onClose,\n onSuccess,\n request,\n availablePlans,\n}: EditAPIKeyDialogProps) => {\n const kuadrantApi = useApi(kuadrantApiRef);\n\n const [planTier, setPlanTier] = useState(\"\");\n const [useCase, setUseCase] = useState(\"\");\n const [saving, setSaving] = useState(false);\n const [error, setError] = useState(\"\");\n\n useEffect(() => {\n if (open && request) {\n setPlanTier(request.spec.planTier || \"\");\n setUseCase(request.spec.useCase || \"\");\n setError(\"\");\n }\n }, [open, request]);\n\n const handleSave = async () => {\n if (!planTier) {\n setError(\"Please select a tier\");\n return;\n }\n\n setError(\"\");\n setSaving(true);\n\n try {\n const patch = {\n spec: {\n planTier,\n useCase: useCase.trim(),\n },\n };\n\n await kuadrantApi.updateRequest(\n request.metadata.name,\n request.metadata.namespace,\n // @ts-ignore Applying a partial obj\n patch,\n );\n\n onSuccess();\n onClose();\n } catch (err) {\n console.error(\"Error updating API key request:\", err);\n setError(err instanceof Error ? err.message : \"Unknown error occurred\");\n } finally {\n setSaving(false);\n }\n };\n\n const handleClose = () => {\n if (!saving) {\n setError(\"\");\n onClose();\n }\n };\n\n return (\n <Dialog open={open} onClose={handleClose} maxWidth=\"sm\" fullWidth>\n <DialogTitle>Edit API Key</DialogTitle>\n <DialogContent>\n {error && (\n <Box\n mb={2}\n p={2}\n bgcolor=\"error.main\"\n color=\"error.contrastText\"\n borderRadius={1}\n >\n <Typography variant=\"body2\">{error}</Typography>\n </Box>\n )}\n\n <FormControl fullWidth margin=\"normal\">\n <InputLabel>Tier</InputLabel>\n <Select\n value={planTier}\n onChange={(e) => setPlanTier(e.target.value as string)}\n disabled={saving}\n >\n {availablePlans.map((plan) => {\n const limitDesc = Object.entries(plan.limits || {})\n .map(([key, val]) => `${val} per ${key}`)\n .join(\", \");\n return (\n <MenuItem key={plan.tier} value={plan.tier}>\n {plan.tier} {limitDesc ? `(${limitDesc})` : \"\"}\n </MenuItem>\n );\n })}\n </Select>\n </FormControl>\n\n <TextField\n label=\"Use Case\"\n placeholder=\"Describe how you plan to use this API\"\n multiline\n rows={3}\n fullWidth\n margin=\"normal\"\n value={useCase}\n onChange={(e) => setUseCase(e.target.value)}\n disabled={saving}\n helperText=\"Explain your intended use of this API for admin review\"\n />\n </DialogContent>\n <DialogActions>\n <Button onClick={handleClose} disabled={saving}>\n Cancel\n </Button>\n <Button\n onClick={handleSave}\n color=\"primary\"\n variant=\"contained\"\n disabled={!planTier || saving}\n startIcon={\n saving ? <CircularProgress size={16} color=\"inherit\" /> : undefined\n }\n >\n {saving ? \"Saving...\" : \"Save Changes\"}\n </Button>\n </DialogActions>\n </Dialog>\n );\n};\n"],"names":[],"mappings":"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"}