diff --git a/services/frontend/src/components/Modal/Service/Create.tsx b/services/frontend/src/components/Modal/Service/Create.tsx index eb51dd7..4b7d59b 100644 --- a/services/frontend/src/components/Modal/Service/Create.tsx +++ b/services/frontend/src/components/Modal/Service/Create.tsx @@ -6,7 +6,11 @@ import Environment from "./Environment"; import Volumes from "./Volumes"; import Labels from "./Labels"; import { CallbackFunction } from "../../../types"; -import { getInitialValues, transform, validationSchema } from "./form-utils"; +import { + getInitialValues, + getFinalValues, + validationSchema +} from "./form-utils"; interface IModalServiceProps { onHide: CallbackFunction; @@ -45,7 +49,7 @@ const ModalServiceCreate = (props: IModalServiceProps) => { const [openTab, setOpenTab] = useState("General"); const handleCreate = (values: any, formik: any) => { // TODO: This modal should not be aware of endpoints. Seperation of concerns. - onAddEndpoint(transform(values)); + onAddEndpoint(getFinalValues(values)); formik.resetForm(); }; diff --git a/services/frontend/src/components/Modal/Service/Edit.tsx b/services/frontend/src/components/Modal/Service/Edit.tsx index 557aef1..4d0768b 100644 --- a/services/frontend/src/components/Modal/Service/Edit.tsx +++ b/services/frontend/src/components/Modal/Service/Edit.tsx @@ -7,7 +7,11 @@ import Environment from "./Environment"; import Volumes from "./Volumes"; import Labels from "./Labels"; import type { CallbackFunction, IServiceNodeItem } from "../../../types"; -import { getInitialValues, transform, validationSchema } from "./form-utils"; +import { + getInitialValues, + getFinalValues, + validationSchema +} from "./form-utils"; export interface IModalServiceProps { node: IServiceNodeItem; @@ -48,7 +52,7 @@ const ModalServiceEdit = (props: IModalServiceProps) => { const [selectedNode, setSelectedNode] = useState(); const handleUpdate = (values: any) => { - onUpdateEndpoint(transform(values, selectedNode)); + onUpdateEndpoint(getFinalValues(values, selectedNode)); }; const initialValues = useMemo( diff --git a/services/frontend/src/components/Modal/Service/form-utils.ts b/services/frontend/src/components/Modal/Service/form-utils.ts index aeef6d6..d98b600 100644 --- a/services/frontend/src/components/Modal/Service/form-utils.ts +++ b/services/frontend/src/components/Modal/Service/form-utils.ts @@ -50,15 +50,82 @@ export const validationSchema = yup.object({ ) }); -export const getInitialValues = ( - node?: IServiceNodeItem -): IEditServiceForm => ({ - ...initialValues, - serviceName: node?.canvasConfig.node_name || "", - containerName: node?.serviceConfig.container_name || "" -}); +export const getInitialValues = (node?: IServiceNodeItem): IEditServiceForm => { + if (!node) { + return { + ...initialValues + }; + } + + const { canvasConfig, serviceConfig } = node; + const { node_name = "" } = canvasConfig; + const { + container_name = "", + environment, + volumes, + ports, + labels + } = serviceConfig; + + const checkArray = (array: any, name: string): T => { + if (!Array.isArray(array)) { + throw new Error( + `Looks like we encountered a bug. The current implementation expects "${name}" to be an array.` + ); + } + return array as unknown as T; + }; + + const environment0: string[] = checkArray(environment, "environment"); + const volumes0: string[] = checkArray(volumes, "volumes"); + const ports0: string[] = checkArray(ports, "ports"); + const labels0: string[] = checkArray(labels, "labels"); + + return { + ...initialValues, + serviceName: node_name, + containerName: container_name, + environmentVariables: environment0.map((variable) => { + const [key, value] = variable.split(":"); + return { + key, + value + }; + }), + volumes: volumes0.map((volume) => { + const [name, containerPath, accessMode] = volume.split(":"); + return { + name, + containerPath, + accessMode + }; + }), + ports: ports0.map((port) => { + const slashIndex = port.lastIndexOf("/"); + const protocol = slashIndex >= 0 ? port.substring(slashIndex + 1) : ""; + const [hostPort, containerPort] = port + .substring(0, slashIndex) + .split(":"); + + if (!["tcp", "udp"].includes(protocol)) { + throw new Error( + `Invalid protocol "${protocol}" found while deserializing.` + ); + } + + return { hostPort, containerPort, protocol } as any; + }), + labels: labels0.map((label) => { + const [key, value] = label.split(":"); + return { + key, + value + }; + }) + }; +}; -export const transform = ( +export const getFinalValues = ( values: IEditServiceForm, previous?: IServiceNodeItem ): IServiceNodeItem => { @@ -74,8 +141,7 @@ export const transform = ( }, { canvasConfig: { - node_name: values.serviceName, - node_icon: "" + node_name: values.serviceName }, serviceConfig: { container_name: values.containerName,