From 0d1a25d922b003057210c4f73ed37dcbcd68fc62 Mon Sep 17 00:00:00 2001 From: John Kim Date: Tue, 1 Oct 2024 13:08:00 -0400 Subject: [PATCH 1/5] handle empty --- webui/react/src/components/ConfigPolicies.tsx | 2 ++ 1 file changed, 2 insertions(+) diff --git a/webui/react/src/components/ConfigPolicies.tsx b/webui/react/src/components/ConfigPolicies.tsx index dbd296f2893..e5ff91dd189 100644 --- a/webui/react/src/components/ConfigPolicies.tsx +++ b/webui/react/src/components/ConfigPolicies.tsx @@ -9,6 +9,7 @@ import { useToast } from 'hew/Toast'; import useConfirm from 'hew/useConfirm'; import { Loadable, NotLoaded } from 'hew/utils/loadable'; import yaml from 'js-yaml'; +import { isEmpty } from 'lodash'; import { useState } from 'react'; import { useAsync } from 'hooks/useAsync'; @@ -75,6 +76,7 @@ const ConfigPolicies: React.FC = ({ workspaceId }: Props) => { workloadType: 'NTSC', workspaceId, }); + if (isEmpty(response.configPolicies)) return undefined; return response.configPolicies; } return NotLoaded; From 16fb02e87efc87876cc15b7b186d41df68572ffb Mon Sep 17 00:00:00 2001 From: John Kim Date: Wed, 2 Oct 2024 10:35:20 -0400 Subject: [PATCH 2/5] workloadType tabs --- webui/react/src/components/ConfigPolicies.tsx | 63 +++++++++++++++---- 1 file changed, 52 insertions(+), 11 deletions(-) diff --git a/webui/react/src/components/ConfigPolicies.tsx b/webui/react/src/components/ConfigPolicies.tsx index e5ff91dd189..e2cb72d4964 100644 --- a/webui/react/src/components/ConfigPolicies.tsx +++ b/webui/react/src/components/ConfigPolicies.tsx @@ -3,6 +3,7 @@ import Button from 'hew/Button'; import CodeEditor from 'hew/CodeEditor'; import Column from 'hew/Column'; import Form, { hasErrors } from 'hew/Form'; +import Pivot, { PivotProps } from 'hew/Pivot'; import Row from 'hew/Row'; import Spinner from 'hew/Spinner'; import { useToast } from 'hew/Toast'; @@ -21,11 +22,51 @@ interface Props { workspaceId?: number; } +type ConfigPoliciesType = 'experiments' | 'tasks'; + +interface ConfigPoliciesValues { + label: string; + workloadType: 'NTSC' | 'EXPERIMENT'; +} + +const ConfigPoliciesValues: Record = { + experiments: { + label: 'Experiments', + workloadType: 'EXPERIMENT', + }, + tasks: { + label: 'Tasks', + workloadType: 'NTSC', + }, +}; + +interface TabProps { + workspaceId?: number; + type: ConfigPoliciesType; +} + type FormInputs = { - task: string; + configPolicies: string; }; const ConfigPolicies: React.FC = ({ workspaceId }: Props) => { + const tabItems: PivotProps['items'] = [ + { + children: , + key: 'experiments', + label: ConfigPoliciesValues.experiments.label, + }, + { + children: , + key: 'tasks', + label: ConfigPoliciesValues.tasks.label, + }, + ]; + + return ; +}; + +const ConfigPoliciesTab: React.FC = ({ workspaceId, type }: TabProps) => { const confirm = useConfirm(); const { openToast } = useToast(); const { canModifyWorkspaceConfigPolicies, loading: rbacLoading } = usePermissions(); @@ -40,8 +81,8 @@ const ConfigPolicies: React.FC = ({ workspaceId }: Props) => { if (workspaceId) { try { await updateWorkspaceConfigPolicies({ - configPolicies: form.getFieldValue('task'), - workloadType: 'NTSC', + configPolicies: form.getFieldValue('configPolicies'), + workloadType: ConfigPoliciesValues[type].workloadType, workspaceId, }); openToast({ title: 'Config policies updated' }); @@ -70,22 +111,22 @@ const ConfigPolicies: React.FC = ({ workspaceId }: Props) => { }); }; - const loadableTaskConfigPolicies: Loadable = useAsync(async () => { + const loadableConfigPolicies: Loadable = useAsync(async () => { if (workspaceId) { const response = await getWorkspaceConfigPolicies({ - workloadType: 'NTSC', + workloadType: ConfigPoliciesValues[type].workloadType, workspaceId, }); if (isEmpty(response.configPolicies)) return undefined; return response.configPolicies; } return NotLoaded; - }, [workspaceId]); + }, [workspaceId, type]); - const initialTaskYAML = yaml.dump(loadableTaskConfigPolicies.getOrElse(undefined)); + const initialConfigPoliciesYAML = yaml.dump(loadableConfigPolicies.getOrElse(undefined)); const handleChange = () => { - setDisabled(hasErrors(form) || form.getFieldValue('task') === initialTaskYAML); + setDisabled(hasErrors(form) || form.getFieldValue('configPolicies') === initialConfigPoliciesYAML); }; if (rbacLoading) return ; @@ -113,7 +154,7 @@ const ConfigPolicies: React.FC = ({ workspaceId }: Props) => {
{ @@ -131,8 +172,8 @@ const ConfigPolicies: React.FC = ({ workspaceId }: Props) => { }, ]}> { handleError(error); }} From 9e69c6fdc33f4ac36f643f042277920fdf1d9766 Mon Sep 17 00:00:00 2001 From: John Kim Date: Wed, 2 Oct 2024 11:34:41 -0400 Subject: [PATCH 3/5] delete if empty --- webui/react/src/components/ConfigPolicies.tsx | 34 +++++++++++++------ webui/react/src/services/api.ts | 6 ++++ webui/react/src/services/apiConfig.ts | 11 ++++++ webui/react/src/services/types.ts | 5 +++ 4 files changed, 46 insertions(+), 10 deletions(-) diff --git a/webui/react/src/components/ConfigPolicies.tsx b/webui/react/src/components/ConfigPolicies.tsx index e2cb72d4964..116b1c56b92 100644 --- a/webui/react/src/components/ConfigPolicies.tsx +++ b/webui/react/src/components/ConfigPolicies.tsx @@ -15,7 +15,7 @@ import { useState } from 'react'; import { useAsync } from 'hooks/useAsync'; import usePermissions from 'hooks/usePermissions'; -import { getWorkspaceConfigPolicies, updateWorkspaceConfigPolicies } from 'services/api'; +import { deleteWorkspaceConfigPolicies, getWorkspaceConfigPolicies, updateWorkspaceConfigPolicies } from 'services/api'; import handleError from 'utils/error'; interface Props { @@ -76,18 +76,32 @@ const ConfigPoliciesTab: React.FC = ({ workspaceId, type }: TabProps) const APPLY_MESSAGE = "You're about to apply these config policies to this workspace."; const VIEW_MESSAGE = 'An admin applied these config policies to this workspace.'; + const CONFIRMATION_MESSAGE = 'Config policies updated'; const updatePolicies = async () => { if (workspaceId) { - try { - await updateWorkspaceConfigPolicies({ - configPolicies: form.getFieldValue('configPolicies'), - workloadType: ConfigPoliciesValues[type].workloadType, - workspaceId, - }); - openToast({ title: 'Config policies updated' }); - } catch (error) { - handleError(error); + const configPolicies = form.getFieldValue('configPolicies'); + if (configPolicies.length) { + try { + await updateWorkspaceConfigPolicies({ + configPolicies, + workloadType: ConfigPoliciesValues[type].workloadType, + workspaceId, + }); + openToast({ title: CONFIRMATION_MESSAGE }); + } catch (error) { + handleError(error); + } + } else { + try { + await deleteWorkspaceConfigPolicies({ + workloadType: ConfigPoliciesValues[type].workloadType, + workspaceId, + }); + openToast({ title: CONFIRMATION_MESSAGE }); + } catch (error) { + handleError(error); + } } } }; diff --git a/webui/react/src/services/api.ts b/webui/react/src/services/api.ts index ec6dc0bd551..f2a707d436f 100644 --- a/webui/react/src/services/api.ts +++ b/webui/react/src/services/api.ts @@ -1006,3 +1006,9 @@ export const updateWorkspaceConfigPolicies = generateDetApi< Api.V1PutWorkspaceConfigPoliciesResponse, Api.V1PutWorkspaceConfigPoliciesResponse >(Config.updateWorkspaceConfigPolicies); + +export const deleteWorkspaceConfigPolicies = generateDetApi< + Service.DeleteWorkspaceConfigPolicies, + Api.V1DeleteWorkspaceConfigPoliciesResponse, + Api.V1DeleteWorkspaceConfigPoliciesResponse +>(Config.deleteWorkspaceConfigPolicies); diff --git a/webui/react/src/services/apiConfig.ts b/webui/react/src/services/apiConfig.ts index 030d2749dfc..c7c2bea6515 100644 --- a/webui/react/src/services/apiConfig.ts +++ b/webui/react/src/services/apiConfig.ts @@ -2192,6 +2192,17 @@ export const getWorkspaceConfigPolicies: DetApi< detApi.Alpha.getWorkspaceConfigPolicies(params.workspaceId, params.workloadType, options), }; +export const deleteWorkspaceConfigPolicies: DetApi< + Service.DeleteWorkspaceConfigPolicies, + Api.V1DeleteWorkspaceConfigPoliciesResponse, + Api.V1DeleteWorkspaceConfigPoliciesResponse +> = { + name: 'deleteWorkspaceConfigPolicies', + postProcess: identity, + request: (params: Service.DeleteWorkspaceConfigPolicies, options) => + detApi.Alpha.deleteWorkspaceConfigPolicies(params.workspaceId, params.workloadType, options), +}; + export const updateWorkspaceConfigPolicies: DetApi< Service.UpdateWorkspaceConfigPolicies, Api.V1PutWorkspaceConfigPoliciesResponse, diff --git a/webui/react/src/services/types.ts b/webui/react/src/services/types.ts index fc6b33de166..580eb9e6658 100644 --- a/webui/react/src/services/types.ts +++ b/webui/react/src/services/types.ts @@ -574,3 +574,8 @@ export interface UpdateWorkspaceConfigPolicies { workloadType: 'NTSC' | 'EXPERIMENT'; configPolicies: string; } + +export interface DeleteWorkspaceConfigPolicies { + workspaceId: number; + workloadType: 'NTSC' | 'EXPERIMENT'; +} From acec4210df7dd5b8bd4d04579ef2c3b1b8b37cbe Mon Sep 17 00:00:00 2001 From: John Kim Date: Wed, 2 Oct 2024 11:39:59 -0400 Subject: [PATCH 4/5] fmt --- webui/react/src/components/ConfigPolicies.tsx | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/webui/react/src/components/ConfigPolicies.tsx b/webui/react/src/components/ConfigPolicies.tsx index 116b1c56b92..ee584705868 100644 --- a/webui/react/src/components/ConfigPolicies.tsx +++ b/webui/react/src/components/ConfigPolicies.tsx @@ -15,7 +15,11 @@ import { useState } from 'react'; import { useAsync } from 'hooks/useAsync'; import usePermissions from 'hooks/usePermissions'; -import { deleteWorkspaceConfigPolicies, getWorkspaceConfigPolicies, updateWorkspaceConfigPolicies } from 'services/api'; +import { + deleteWorkspaceConfigPolicies, + getWorkspaceConfigPolicies, + updateWorkspaceConfigPolicies, +} from 'services/api'; import handleError from 'utils/error'; interface Props { @@ -140,7 +144,9 @@ const ConfigPoliciesTab: React.FC = ({ workspaceId, type }: TabProps) const initialConfigPoliciesYAML = yaml.dump(loadableConfigPolicies.getOrElse(undefined)); const handleChange = () => { - setDisabled(hasErrors(form) || form.getFieldValue('configPolicies') === initialConfigPoliciesYAML); + setDisabled( + hasErrors(form) || form.getFieldValue('configPolicies') === initialConfigPoliciesYAML, + ); }; if (rbacLoading) return ; From 0fa8e1b2552bcc8614f472776788165dd0362aec Mon Sep 17 00:00:00 2001 From: John Kim Date: Wed, 2 Oct 2024 12:29:54 -0400 Subject: [PATCH 5/5] readonly --- webui/react/src/components/ConfigPolicies.tsx | 1 + 1 file changed, 1 insertion(+) diff --git a/webui/react/src/components/ConfigPolicies.tsx b/webui/react/src/components/ConfigPolicies.tsx index ee584705868..db34c557e87 100644 --- a/webui/react/src/components/ConfigPolicies.tsx +++ b/webui/react/src/components/ConfigPolicies.tsx @@ -194,6 +194,7 @@ const ConfigPoliciesTab: React.FC = ({ workspaceId, type }: TabProps) { handleError(error); }}